1 /************************************************************** 2 * 3 * Licensed to the Apache Software Foundation (ASF) under one 4 * or more contributor license agreements. See the NOTICE file 5 * distributed with this work for additional information 6 * regarding copyright ownership. The ASF licenses this file 7 * to you under the Apache License, Version 2.0 (the 8 * "License"); you may not use this file except in compliance 9 * with the License. You may obtain a copy of the License at 10 * 11 * http://www.apache.org/licenses/LICENSE-2.0 12 * 13 * Unless required by applicable law or agreed to in writing, 14 * software distributed under the License is distributed on an 15 * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 16 * KIND, either express or implied. See the License for the 17 * specific language governing permissions and limitations 18 * under the License. 19 * 20 *************************************************************/ 21 22 23 24 // MARKER(update_precomp.py): autogen include statement, do not remove 25 #include "precompiled_io.hxx" 26 27 28 // streams 29 #include <hash_map> 30 #include <vector> 31 32 #include <com/sun/star/io/XObjectInputStream.hpp> 33 #include <com/sun/star/io/XObjectOutputStream.hpp> 34 #include <com/sun/star/io/XActiveDataSource.hpp> 35 #include <com/sun/star/io/XActiveDataSink.hpp> 36 #include <com/sun/star/io/XMarkableStream.hpp> 37 #include <com/sun/star/io/XConnectable.hpp> 38 #include <com/sun/star/io/UnexpectedEOFException.hpp> 39 #include <com/sun/star/io/WrongFormatException.hpp> 40 #include <com/sun/star/lang/XServiceInfo.hpp> 41 42 #include <cppuhelper/weak.hxx> // OWeakObject 43 #include <cppuhelper/factory.hxx> 44 #include <cppuhelper/implbase4.hxx> 45 #include <cppuhelper/typeprovider.hxx> 46 #include <cppuhelper/queryinterface.hxx> 47 48 #include <osl/mutex.hxx> 49 50 #include <string.h> 51 52 53 using namespace ::cppu; 54 using namespace ::osl; 55 using namespace ::std; 56 using namespace ::rtl; 57 using namespace ::com::sun::star::io; 58 using namespace ::com::sun::star::uno; 59 using namespace ::com::sun::star::lang; 60 61 #include "factreg.hxx" 62 63 namespace io_stm { 64 65 class ODataInputStream : 66 public WeakImplHelper4 < 67 XDataInputStream, 68 XActiveDataSink, 69 XConnectable, 70 XServiceInfo 71 > 72 { 73 public: 74 ODataInputStream( ) 75 : m_bValidStream( sal_False ) 76 { 77 g_moduleCount.modCnt.acquire( &g_moduleCount.modCnt ); 78 } 79 80 ~ODataInputStream(); 81 public: // XInputStream 82 virtual sal_Int32 SAL_CALL readBytes(Sequence< sal_Int8 >& aData, sal_Int32 nBytesToRead); 83 virtual sal_Int32 SAL_CALL readSomeBytes(Sequence< sal_Int8 >& aData, sal_Int32 nMaxBytesToRead); 84 virtual void SAL_CALL skipBytes(sal_Int32 nBytesToSkip); 85 virtual sal_Int32 SAL_CALL available(void); 86 virtual void SAL_CALL closeInput(void); 87 88 public: // XDataInputStream 89 virtual sal_Int8 SAL_CALL readBoolean(void); 90 virtual sal_Int8 SAL_CALL readByte(void); 91 virtual sal_Unicode SAL_CALL readChar(void); 92 virtual sal_Int16 SAL_CALL readShort(void); 93 virtual sal_Int32 SAL_CALL readLong(void); 94 virtual sal_Int64 SAL_CALL readHyper(void); 95 virtual float SAL_CALL readFloat(void); 96 virtual double SAL_CALL readDouble(void); 97 virtual OUString SAL_CALL readUTF(void); 98 99 100 101 public: // XActiveDataSink 102 virtual void SAL_CALL setInputStream(const Reference< XInputStream > & aStream); 103 virtual Reference< XInputStream > SAL_CALL getInputStream(void); 104 105 public: // XConnectable 106 virtual void SAL_CALL setPredecessor(const Reference < XConnectable >& aPredecessor); 107 virtual Reference < XConnectable > SAL_CALL getPredecessor(void); 108 virtual void SAL_CALL setSuccessor(const Reference < XConnectable >& aSuccessor); 109 virtual Reference < XConnectable > SAL_CALL getSuccessor(void) ; 110 111 112 public: // XServiceInfo 113 OUString SAL_CALL getImplementationName() throw (); 114 Sequence< OUString > SAL_CALL getSupportedServiceNames(void) throw (); 115 sal_Bool SAL_CALL supportsService(const OUString& ServiceName) throw (); 116 117 protected: 118 119 Reference < XConnectable > m_pred; 120 Reference < XConnectable > m_succ; 121 Reference < XInputStream > m_input; 122 sal_Bool m_bValidStream; 123 }; 124 125 ODataInputStream::~ODataInputStream() 126 { 127 g_moduleCount.modCnt.release( &g_moduleCount.modCnt ); 128 } 129 130 // XInputStream 131 sal_Int32 ODataInputStream::readBytes(Sequence< sal_Int8 >& aData, sal_Int32 nBytesToRead) 132 { 133 sal_Int32 nRead; 134 135 if( m_bValidStream ) 136 { 137 nRead = m_input->readBytes( aData , nBytesToRead ); 138 } 139 else 140 { 141 throw NotConnectedException( ); 142 } 143 144 return nRead; 145 } 146 147 sal_Int32 ODataInputStream::readSomeBytes(Sequence< sal_Int8 >& aData, sal_Int32 nMaxBytesToRead) 148 { 149 sal_Int32 nRead; 150 if( m_bValidStream ) { 151 nRead = m_input->readSomeBytes( aData , nMaxBytesToRead ); 152 } 153 else { 154 throw NotConnectedException( ); 155 } 156 157 return nRead; 158 } 159 void ODataInputStream::skipBytes(sal_Int32 nBytesToSkip) 160 { 161 if( m_bValidStream ) { 162 m_input->skipBytes( nBytesToSkip ); 163 } 164 else 165 { 166 throw NotConnectedException( ); 167 } 168 } 169 170 171 sal_Int32 ODataInputStream::available(void) 172 { 173 sal_Int32 nAvail; 174 175 if( m_bValidStream ) 176 { 177 nAvail = m_input->available( ); 178 } 179 else 180 { 181 throw NotConnectedException( ); 182 } 183 return nAvail; 184 } 185 186 void ODataInputStream::closeInput(void ) 187 { 188 if( m_bValidStream ) { 189 m_input->closeInput( ); 190 setInputStream( Reference< XInputStream > () ); 191 setPredecessor( Reference < XConnectable >() ); 192 setSuccessor( Reference < XConnectable >() ); 193 m_bValidStream = sal_False; 194 } 195 else 196 { 197 throw NotConnectedException( ); 198 } 199 } 200 201 202 203 204 //== XDataInputStream =========================================== 205 206 // XDataInputStream 207 sal_Int8 ODataInputStream::readBoolean(void) 208 { 209 return readByte(); 210 } 211 212 sal_Int8 ODataInputStream::readByte(void) 213 { 214 Sequence<sal_Int8> aTmp(1); 215 if( 1 != readBytes( aTmp, 1 ) ) 216 { 217 throw UnexpectedEOFException(); 218 } 219 return aTmp.getArray()[0]; 220 } 221 222 sal_Unicode ODataInputStream::readChar(void) 223 { 224 Sequence<sal_Int8> aTmp(2); 225 if( 2 != readBytes( aTmp, 2 ) ) 226 { 227 throw UnexpectedEOFException(); 228 } 229 230 const sal_uInt8 * pBytes = ( const sal_uInt8 * )aTmp.getConstArray(); 231 return ((sal_Unicode)pBytes[0] << 8) + pBytes[1]; 232 } 233 234 sal_Int16 ODataInputStream::readShort(void) 235 { 236 Sequence<sal_Int8> aTmp(2); 237 if( 2 != readBytes( aTmp, 2 ) ) 238 { 239 throw UnexpectedEOFException(); 240 } 241 242 const sal_uInt8 * pBytes = ( const sal_uInt8 * ) aTmp.getConstArray(); 243 return ((sal_Int16)pBytes[0] << 8) + pBytes[1]; 244 } 245 246 247 sal_Int32 ODataInputStream::readLong(void) 248 { 249 Sequence<sal_Int8> aTmp(4); 250 if( 4 != readBytes( aTmp, 4 ) ) 251 { 252 throw UnexpectedEOFException( ); 253 } 254 255 const sal_uInt8 * pBytes = ( const sal_uInt8 * ) aTmp.getConstArray(); 256 return ((sal_Int32)pBytes[0] << 24) + ((sal_Int32)pBytes[1] << 16) + ((sal_Int32)pBytes[2] << 8) + pBytes[3]; 257 } 258 259 260 sal_Int64 ODataInputStream::readHyper(void) 261 { 262 Sequence<sal_Int8> aTmp(8); 263 if( 8 != readBytes( aTmp, 8 ) ) 264 { 265 throw UnexpectedEOFException( ); 266 } 267 268 const sal_uInt8 * pBytes = ( const sal_uInt8 * ) aTmp.getConstArray(); 269 return 270 (((sal_Int64)pBytes[0]) << 56) + 271 (((sal_Int64)pBytes[1]) << 48) + 272 (((sal_Int64)pBytes[2]) << 40) + 273 (((sal_Int64)pBytes[3]) << 32) + 274 (((sal_Int64)pBytes[4]) << 24) + 275 (((sal_Int64)pBytes[5]) << 16) + 276 (((sal_Int64)pBytes[6]) << 8) + 277 pBytes[7]; 278 } 279 280 float ODataInputStream::readFloat(void) 281 { 282 union { float f; sal_uInt32 n; } a; 283 a.n = readLong(); 284 return a.f; 285 } 286 287 double ODataInputStream::readDouble(void) 288 { 289 sal_uInt32 n = 1; 290 union { double d; struct { sal_uInt32 n1; sal_uInt32 n2; } ad; } a; 291 if( *(sal_uInt8 *)&n == 1 ) 292 { 293 // little endian 294 a.ad.n2 = readLong(); 295 a.ad.n1 = readLong(); 296 } 297 else 298 { 299 // big endian 300 a.ad.n1 = readLong(); 301 a.ad.n2 = readLong(); 302 } 303 return a.d; 304 } 305 306 OUString ODataInputStream::readUTF(void) 307 { 308 sal_uInt16 nShortLen = (sal_uInt16)readShort(); 309 sal_Int32 nUTFLen; 310 311 if( ((sal_uInt16)0xffff) == nShortLen ) 312 { 313 // is interpreted as a sign, that string is longer than 64k 314 // incompatible to older XDataInputStream-routines, when strings are exactly 64k 315 nUTFLen = readLong(); 316 } 317 else 318 { 319 nUTFLen = ( sal_Int32 ) nShortLen; 320 } 321 322 Sequence<sal_Unicode> aBuffer( nUTFLen ); 323 sal_Unicode * pStr = aBuffer.getArray(); 324 325 sal_Int32 nCount = 0; 326 sal_Int32 nStrLen = 0; 327 while( nCount < nUTFLen ) 328 { 329 sal_uInt8 c = (sal_uInt8)readByte(); 330 sal_uInt8 char2, char3; 331 switch( c >> 4 ) 332 { 333 case 0: case 1: case 2: case 3: case 4: case 5: case 6: case 7: 334 // 0xxxxxxx 335 nCount++; 336 pStr[nStrLen++] = c; 337 break; 338 339 case 12: case 13: 340 // 110x xxxx 10xx xxxx 341 nCount += 2; 342 if( ! ( nCount <= nUTFLen ) ) 343 { 344 throw WrongFormatException( ); 345 } 346 347 char2 = (sal_uInt8)readByte(); 348 if( ! ( (char2 & 0xC0) == 0x80 ) ) 349 { 350 throw WrongFormatException( ); 351 } 352 353 pStr[nStrLen++] = (sal_Unicode(c & 0x1F) << 6) | (char2 & 0x3F); 354 break; 355 356 case 14: 357 // 1110 xxxx 10xx xxxx 10xx xxxx 358 nCount += 3; 359 if( !( nCount <= nUTFLen) ) 360 { 361 throw WrongFormatException( ); 362 } 363 364 char2 = (sal_uInt8)readByte(); 365 char3 = (sal_uInt8)readByte(); 366 367 if( (((char2 & 0xC0) != 0x80) || ((char3 & 0xC0) != 0x80)) ) { 368 throw WrongFormatException( ); 369 } 370 pStr[nStrLen++] = (sal_Unicode(c & 0x0F) << 12) | 371 (sal_Unicode(char2 & 0x3F) << 6) | 372 (char3 & 0x3F); 373 break; 374 375 default: 376 // 10xx xxxx, 1111 xxxx 377 throw WrongFormatException(); 378 //throw new UTFDataFormatException(); 379 } 380 } 381 return OUString( pStr, nStrLen ); 382 } 383 384 385 386 // XActiveDataSource 387 void ODataInputStream::setInputStream(const Reference< XInputStream > & aStream) 388 { 389 390 if( m_input != aStream ) { 391 m_input = aStream; 392 393 Reference < XConnectable > pred( m_input , UNO_QUERY ); 394 setPredecessor( pred ); 395 } 396 397 m_bValidStream = m_input.is(); 398 } 399 400 Reference< XInputStream > ODataInputStream::getInputStream(void) 401 { 402 return m_input; 403 } 404 405 406 407 // XDataSink 408 void ODataInputStream::setSuccessor( const Reference < XConnectable > &r ) 409 { 410 /// if the references match, nothing needs to be done 411 if( m_succ != r ) { 412 /// store the reference for later use 413 m_succ = r; 414 415 if( m_succ.is() ) { 416 /// set this instance as the sink ! 417 m_succ->setPredecessor( Reference< XConnectable > ( 418 SAL_STATIC_CAST( XConnectable * , this ) ) ); 419 } 420 } 421 } 422 423 Reference < XConnectable > ODataInputStream::getSuccessor() 424 { 425 return m_succ; 426 } 427 428 429 // XDataSource 430 void ODataInputStream::setPredecessor( const Reference < XConnectable > &r ) 431 { 432 if( r != m_pred ) { 433 m_pred = r; 434 if( m_pred.is() ) { 435 m_pred->setSuccessor( Reference< XConnectable > ( 436 SAL_STATIC_CAST( XConnectable * , this ) ) ); 437 } 438 } 439 } 440 Reference < XConnectable > ODataInputStream::getPredecessor() 441 { 442 return m_pred; 443 } 444 445 // XServiceInfo 446 OUString ODataInputStream::getImplementationName() throw () 447 { 448 return ODataInputStream_getImplementationName(); 449 } 450 451 // XServiceInfo 452 sal_Bool ODataInputStream::supportsService(const OUString& ServiceName) throw () 453 { 454 Sequence< OUString > aSNL = getSupportedServiceNames(); 455 const OUString * pArray = aSNL.getConstArray(); 456 457 for( sal_Int32 i = 0; i < aSNL.getLength(); i++ ) 458 if( pArray[i] == ServiceName ) 459 return sal_True; 460 461 return sal_False; 462 } 463 464 // XServiceInfo 465 Sequence< OUString > ODataInputStream::getSupportedServiceNames(void) throw () 466 { 467 return ODataInputStream_getSupportedServiceNames(); 468 } 469 470 /*** 471 * 472 * registration information 473 * 474 * 475 ****/ 476 477 Reference< XInterface > SAL_CALL ODataInputStream_CreateInstance( const Reference < XComponentContext > & ) 478 { 479 ODataInputStream *p = new ODataInputStream; 480 return Reference< XInterface > ( (OWeakObject * ) p ); 481 } 482 483 OUString ODataInputStream_getImplementationName() 484 { 485 return OUString( RTL_CONSTASCII_USTRINGPARAM( "com.sun.star.comp.io.stm.DataInputStream" ) ); 486 } 487 488 Sequence<OUString> ODataInputStream_getSupportedServiceNames(void) 489 { 490 Sequence<OUString> aRet(1); 491 aRet.getArray()[0] = OUString( RTL_CONSTASCII_USTRINGPARAM( "com.sun.star.io.DataInputStream" ) ); 492 return aRet; 493 } 494 495 496 497 498 class ODataOutputStream : 499 public WeakImplHelper4 < 500 XDataOutputStream, 501 XActiveDataSource, 502 XConnectable, 503 XServiceInfo > 504 { 505 public: 506 ODataOutputStream() 507 : m_bValidStream( sal_False ) 508 { 509 g_moduleCount.modCnt.acquire( &g_moduleCount.modCnt ); 510 } 511 ~ODataOutputStream(); 512 513 public: // XOutputStream 514 virtual void SAL_CALL writeBytes(const Sequence< sal_Int8 >& aData); 515 virtual void SAL_CALL flush(void); 516 virtual void SAL_CALL closeOutput(void); 517 518 public: // XDataOutputStream 519 virtual void SAL_CALL writeBoolean(sal_Bool Value); 520 virtual void SAL_CALL writeByte(sal_Int8 Value); 521 virtual void SAL_CALL writeChar(sal_Unicode Value); 522 virtual void SAL_CALL writeShort(sal_Int16 Value); 523 virtual void SAL_CALL writeLong(sal_Int32 Value); 524 virtual void SAL_CALL writeHyper(sal_Int64 Value); 525 virtual void SAL_CALL writeFloat(float Value); 526 virtual void SAL_CALL writeDouble(double Value); 527 virtual void SAL_CALL writeUTF(const OUString& Value); 528 529 public: // XActiveDataSource 530 virtual void SAL_CALL setOutputStream(const Reference< XOutputStream > & aStream); 531 virtual Reference < XOutputStream > SAL_CALL getOutputStream(void); 532 533 public: // XConnectable 534 virtual void SAL_CALL setPredecessor(const Reference < XConnectable >& aPredecessor); 535 virtual Reference < XConnectable > SAL_CALL getPredecessor(void); 536 virtual void SAL_CALL setSuccessor(const Reference < XConnectable >& aSuccessor); 537 virtual Reference < XConnectable > SAL_CALL getSuccessor(void); 538 539 public: // XServiceInfo 540 OUString SAL_CALL getImplementationName() throw (); 541 Sequence< OUString > SAL_CALL getSupportedServiceNames(void) throw (); 542 sal_Bool SAL_CALL supportsService(const OUString& ServiceName) throw (); 543 544 protected: 545 Reference < XConnectable > m_succ; 546 Reference < XConnectable > m_pred; 547 Reference< XOutputStream > m_output; 548 sal_Bool m_bValidStream; 549 }; 550 551 ODataOutputStream::~ODataOutputStream() 552 { 553 g_moduleCount.modCnt.release( &g_moduleCount.modCnt ); 554 } 555 556 557 // XOutputStream 558 void ODataOutputStream::writeBytes(const Sequence< sal_Int8 >& aData) 559 { 560 if( m_bValidStream ) 561 { 562 m_output->writeBytes( aData ); 563 } 564 else { 565 throw NotConnectedException( ); 566 } 567 } 568 569 void ODataOutputStream::flush(void) 570 { 571 if( m_bValidStream ) 572 { 573 m_output->flush(); 574 } 575 else 576 { 577 throw NotConnectedException(); 578 } 579 580 } 581 582 583 void ODataOutputStream::closeOutput(void) 584 { 585 if( m_bValidStream ) 586 { 587 m_output->closeOutput(); 588 setOutputStream( Reference< XOutputStream > () ); 589 setPredecessor( Reference < XConnectable >() ); 590 setSuccessor( Reference < XConnectable >() ); 591 } 592 else 593 { 594 throw NotConnectedException(); 595 } 596 } 597 598 // XDataOutputStream 599 void ODataOutputStream::writeBoolean(sal_Bool Value) 600 { 601 if( Value ) 602 { 603 writeByte( 1 ); 604 } 605 else 606 { 607 writeByte( 0 ); 608 } 609 } 610 611 612 void ODataOutputStream::writeByte(sal_Int8 Value) 613 { 614 Sequence<sal_Int8> aTmp( 1 ); 615 aTmp.getArray()[0] = Value; 616 writeBytes( aTmp ); 617 } 618 619 void ODataOutputStream::writeChar(sal_Unicode Value) 620 { 621 Sequence<sal_Int8> aTmp( 2 ); 622 sal_Int8 * pBytes = ( sal_Int8 * ) aTmp.getArray(); 623 pBytes[0] = sal_Int8(Value >> 8); 624 pBytes[1] = sal_Int8(Value); 625 writeBytes( aTmp ); 626 } 627 628 629 void ODataOutputStream::writeShort(sal_Int16 Value) 630 { 631 Sequence<sal_Int8> aTmp( 2 ); 632 sal_Int8 * pBytes = aTmp.getArray(); 633 pBytes[0] = sal_Int8(Value >> 8); 634 pBytes[1] = sal_Int8(Value); 635 writeBytes( aTmp ); 636 } 637 638 void ODataOutputStream::writeLong(sal_Int32 Value) 639 { 640 Sequence<sal_Int8> aTmp( 4 ); 641 sal_Int8 * pBytes = aTmp.getArray(); 642 pBytes[0] = sal_Int8(Value >> 24); 643 pBytes[1] = sal_Int8(Value >> 16); 644 pBytes[2] = sal_Int8(Value >> 8); 645 pBytes[3] = sal_Int8(Value); 646 writeBytes( aTmp ); 647 } 648 649 void ODataOutputStream::writeHyper(sal_Int64 Value) 650 { 651 Sequence<sal_Int8> aTmp( 8 ); 652 sal_Int8 * pBytes = aTmp.getArray(); 653 pBytes[0] = sal_Int8(Value >> 56); 654 pBytes[1] = sal_Int8(Value >> 48); 655 pBytes[2] = sal_Int8(Value >> 40); 656 pBytes[3] = sal_Int8(Value >> 32); 657 pBytes[4] = sal_Int8(Value >> 24); 658 pBytes[5] = sal_Int8(Value >> 16); 659 pBytes[6] = sal_Int8(Value >> 8); 660 pBytes[7] = sal_Int8(Value); 661 writeBytes( aTmp ); 662 } 663 664 665 void ODataOutputStream::writeFloat(float Value) 666 { 667 union { float f; sal_uInt32 n; } a; 668 a.f = Value; 669 writeLong( a.n ); 670 } 671 672 void ODataOutputStream::writeDouble(double Value) 673 { 674 sal_uInt32 n = 1; 675 union { double d; struct { sal_uInt32 n1; sal_uInt32 n2; } ad; } a; 676 a.d = Value; 677 if( *(sal_Int8 *)&n == 1 ) 678 { 679 // little endian 680 writeLong( a.ad.n2 ); 681 writeLong( a.ad.n1 ); 682 } 683 else 684 { 685 // big endian 686 writeLong( a.ad.n1 ); 687 writeLong( a.ad.n2 ); 688 } 689 } 690 691 void ODataOutputStream::writeUTF(const OUString& Value) 692 { 693 sal_Int32 nStrLen = Value.getLength(); 694 const sal_Unicode * pStr = Value.getStr(); 695 sal_Int32 nUTFLen = 0; 696 sal_Int32 i; 697 698 for( i = 0 ; i < nStrLen ; i++ ) 699 { 700 sal_uInt16 c = pStr[i]; 701 if( (c >= 0x0001) && (c <= 0x007F) ) 702 { 703 nUTFLen++; 704 } 705 else if( c > 0x07FF ) 706 { 707 nUTFLen += 3; 708 } 709 else 710 { 711 nUTFLen += 2; 712 } 713 } 714 715 716 // compatibility mode for older implementations, where it was not possible 717 // to write blocks bigger than 64 k. Note that there is a tradeoff. Blocks, 718 // that are exactly 64k long can not be read by older routines when written 719 // with these routines and the other way round !!!!! 720 if( nUTFLen >= 0xFFFF ) { 721 writeShort( (sal_Int16)-1 ); 722 writeLong( nUTFLen ); 723 } 724 else { 725 writeShort( ((sal_uInt16)nUTFLen) ); 726 } 727 for( i = 0 ; i < nStrLen ; i++ ) 728 { 729 sal_uInt16 c = pStr[i]; 730 if( (c >= 0x0001) && (c <= 0x007F) ) 731 { 732 writeByte(sal_Int8(c)); 733 } 734 else if( c > 0x07FF ) 735 { 736 writeByte(sal_Int8(0xE0 | ((c >> 12) & 0x0F))); 737 writeByte(sal_Int8(0x80 | ((c >> 6) & 0x3F))); 738 writeByte(sal_Int8(0x80 | ((c >> 0) & 0x3F))); 739 //written += 2; 740 } 741 else 742 { 743 writeByte(sal_Int8(0xC0 | ((c >> 6) & 0x1F))); 744 writeByte(sal_Int8(0x80 | ((c >> 0) & 0x3F))); 745 //written += 1; 746 } 747 } 748 //written += strlen + 2; 749 } 750 751 // XActiveDataSource 752 void ODataOutputStream::setOutputStream(const Reference< XOutputStream > & aStream) 753 { 754 if( m_output != aStream ) { 755 m_output = aStream; 756 m_bValidStream = m_output.is(); 757 758 Reference < XConnectable > succ( m_output , UNO_QUERY ); 759 setSuccessor( succ ); 760 } 761 } 762 763 Reference< XOutputStream > ODataOutputStream::getOutputStream(void) 764 { 765 return m_output; 766 } 767 768 769 770 771 // XDataSink 772 void ODataOutputStream::setSuccessor( const Reference < XConnectable > &r ) 773 { 774 /// if the references match, nothing needs to be done 775 if( m_succ != r ) 776 { 777 /// store the reference for later use 778 m_succ = r; 779 780 if( m_succ.is() ) 781 { 782 /// set this instance as the sink ! 783 m_succ->setPredecessor( Reference < XConnectable > ( 784 SAL_STATIC_CAST( XConnectable * , this ) )); 785 } 786 } 787 } 788 Reference < XConnectable > ODataOutputStream::getSuccessor() 789 { 790 return m_succ; 791 } 792 793 794 // XDataSource 795 void ODataOutputStream::setPredecessor( const Reference < XConnectable > &r ) 796 { 797 if( r != m_pred ) { 798 m_pred = r; 799 if( m_pred.is() ) { 800 m_pred->setSuccessor( Reference< XConnectable > ( 801 SAL_STATIC_CAST( XConnectable * , this ) )); 802 } 803 } 804 } 805 Reference < XConnectable > ODataOutputStream::getPredecessor() 806 { 807 return m_pred; 808 } 809 810 811 812 // XServiceInfo 813 OUString ODataOutputStream::getImplementationName() throw () 814 { 815 return ODataOutputStream_getImplementationName(); 816 } 817 818 // XServiceInfo 819 sal_Bool ODataOutputStream::supportsService(const OUString& ServiceName) throw () 820 { 821 Sequence< OUString > aSNL = getSupportedServiceNames(); 822 const OUString * pArray = aSNL.getConstArray(); 823 824 for( sal_Int32 i = 0; i < aSNL.getLength(); i++ ) 825 if( pArray[i] == ServiceName ) 826 return sal_True; 827 828 return sal_False; 829 } 830 831 // XServiceInfo 832 Sequence< OUString > ODataOutputStream::getSupportedServiceNames(void) throw () 833 { 834 return ODataOutputStream_getSupportedServiceNames(); 835 } 836 837 838 839 840 Reference< XInterface > SAL_CALL ODataOutputStream_CreateInstance( const Reference < XComponentContext > & ) 841 { 842 ODataOutputStream *p = new ODataOutputStream; 843 Reference< XInterface > xService = *p; 844 return xService; 845 } 846 847 848 OUString ODataOutputStream_getImplementationName() 849 { 850 return OUString(RTL_CONSTASCII_USTRINGPARAM( "com.sun.star.comp.io.stm.DataOutputStream" ) ); 851 } 852 853 Sequence<OUString> ODataOutputStream_getSupportedServiceNames(void) 854 { 855 Sequence<OUString> aRet(1); 856 aRet.getArray()[0] = OUString( RTL_CONSTASCII_USTRINGPARAM( "com.sun.star.io.DataOutputStream" ) ); 857 return aRet; 858 } 859 860 //-------------------------------------- 861 struct equalObjectContainer_Impl 862 { 863 sal_Int32 operator()(const Reference< XInterface > & s1, 864 const Reference< XInterface > & s2) const 865 { 866 return s1 == s2; 867 } 868 }; 869 870 //----------------------------------------------------------------------------- 871 struct hashObjectContainer_Impl 872 { 873 size_t operator()(const Reference< XInterface > & xRef) const 874 { 875 return (size_t)xRef.get(); 876 } 877 }; 878 879 typedef hash_map 880 < 881 Reference< XInterface >, 882 sal_Int32, 883 hashObjectContainer_Impl, 884 equalObjectContainer_Impl 885 > ObjectContainer_Impl; 886 887 /*--------------------------------------------- 888 * 889 * 890 * 891 * 892 *--------------------------------------------*/ 893 class OObjectOutputStream : 894 public ODataOutputStream, 895 public XObjectOutputStream, 896 public XMarkableStream 897 { 898 public: 899 OObjectOutputStream() 900 : m_nMaxId(0) , 901 m_bValidMarkable(sal_False) 902 { 903 g_moduleCount.modCnt.acquire( &g_moduleCount.modCnt ); 904 } 905 906 ~OObjectOutputStream(); 907 908 public: 909 Any SAL_CALL queryInterface( const Type &type ); 910 void SAL_CALL acquire() throw() { ODataOutputStream::acquire(); } 911 void SAL_CALL release() throw() { ODataOutputStream::release(); } 912 913 public: 914 // XOutputStream 915 virtual void SAL_CALL writeBytes(const Sequence< sal_Int8 >& aData) 916 { ODataOutputStream::writeBytes( aData ); } 917 918 virtual void SAL_CALL flush(void) 919 { ODataOutputStream::flush(); } 920 921 virtual void SAL_CALL closeOutput(void) 922 { ODataOutputStream::closeOutput(); } 923 924 public: 925 // XDataOutputStream 926 virtual void SAL_CALL writeBoolean(sal_Bool Value) 927 { ODataOutputStream::writeBoolean( Value ); } 928 virtual void SAL_CALL writeByte(sal_Int8 Value) 929 { ODataOutputStream::writeByte( Value ); } 930 virtual void SAL_CALL writeChar(sal_Unicode Value) 931 { ODataOutputStream::writeChar( Value ); } 932 virtual void SAL_CALL writeShort(sal_Int16 Value) 933 { ODataOutputStream::writeShort( Value ); } 934 virtual void SAL_CALL writeLong(sal_Int32 Value) 935 { ODataOutputStream::writeLong( Value ); } 936 virtual void SAL_CALL writeHyper(sal_Int64 Value) 937 { ODataOutputStream::writeHyper( Value ); } 938 virtual void SAL_CALL writeFloat(float Value) 939 { ODataOutputStream::writeFloat( Value ); } 940 virtual void SAL_CALL writeDouble(double Value) 941 { ODataOutputStream::writeDouble( Value ); } 942 virtual void SAL_CALL writeUTF(const OUString& Value) 943 { ODataOutputStream::writeUTF( Value );} 944 945 // XObjectOutputStream 946 virtual void SAL_CALL writeObject( const Reference< XPersistObject > & r ); 947 948 public: // XMarkableStream 949 virtual sal_Int32 SAL_CALL createMark(void); 950 virtual void SAL_CALL deleteMark(sal_Int32 Mark); 951 virtual void SAL_CALL jumpToMark(sal_Int32 nMark); 952 virtual void SAL_CALL jumpToFurthest(void); 953 virtual sal_Int32 SAL_CALL offsetToMark(sal_Int32 nMark); 954 955 public: //XTypeProvider 956 virtual ::com::sun::star::uno::Sequence< ::com::sun::star::uno::Type > SAL_CALL 957 getTypes( ); 958 virtual ::com::sun::star::uno::Sequence< sal_Int8 > SAL_CALL 959 getImplementationId( ); 960 961 public: // XServiceInfo 962 OUString SAL_CALL getImplementationName() throw (); 963 Sequence< OUString > SAL_CALL getSupportedServiceNames(void) throw (); 964 sal_Bool SAL_CALL supportsService(const OUString& ServiceName) throw (); 965 966 private: 967 void connectToMarkable(); 968 private: 969 ObjectContainer_Impl m_mapObject; 970 sal_Int32 m_nMaxId; 971 Reference< XMarkableStream > m_rMarkable; 972 sal_Bool m_bValidMarkable; 973 }; 974 975 OObjectOutputStream::~OObjectOutputStream() 976 { 977 g_moduleCount.modCnt.release( &g_moduleCount.modCnt ); 978 } 979 980 Any OObjectOutputStream::queryInterface( const Type &aType ) 981 { 982 Any a = ::cppu::queryInterface( 983 aType , 984 SAL_STATIC_CAST( XMarkableStream * , this ), 985 SAL_STATIC_CAST( XObjectOutputStream * , this ) ); 986 if( a.hasValue() ) 987 { 988 return a; 989 } 990 991 return ODataOutputStream::queryInterface( aType ); 992 993 } 994 void OObjectOutputStream::writeObject( const Reference< XPersistObject > & xPObj ) 995 { 996 997 connectToMarkable(); 998 sal_Bool bWriteObj = sal_False; 999 // create Mark to write length of info 1000 sal_uInt32 nInfoLenMark = m_rMarkable->createMark(); 1001 1002 // length of the info data (is later rewritten) 1003 OObjectOutputStream::writeShort( 0 ); 1004 1005 // write the object identifier 1006 if( xPObj.is() ) 1007 { 1008 Reference< XInterface > rX( xPObj , UNO_QUERY ); 1009 1010 ObjectContainer_Impl::const_iterator aIt 1011 = m_mapObject.find( rX ); 1012 if( aIt == m_mapObject.end() ) 1013 { 1014 // insert new object in hash table 1015 m_mapObject[ rX ] = ++m_nMaxId; 1016 ODataOutputStream::writeLong( m_nMaxId ); 1017 ODataOutputStream::writeUTF( xPObj->getServiceName() ); 1018 bWriteObj = sal_True; 1019 } 1020 else 1021 { 1022 ODataOutputStream::writeLong( (*aIt).second ); 1023 OUString aName; 1024 ODataOutputStream::writeUTF( aName ); 1025 } 1026 } 1027 else 1028 { 1029 ODataOutputStream::writeLong( 0 ); 1030 OUString aName; 1031 ODataOutputStream::writeUTF( aName ); 1032 } 1033 1034 sal_uInt32 nObjLenMark = m_rMarkable->createMark(); 1035 ODataOutputStream::writeLong( 0 ); 1036 1037 sal_Int32 nInfoLen = m_rMarkable->offsetToMark( nInfoLenMark ); 1038 m_rMarkable->jumpToMark( nInfoLenMark ); 1039 // write length of the info data 1040 ODataOutputStream::writeShort( (sal_Int16)nInfoLen ); 1041 // jump to the end of the stream 1042 m_rMarkable->jumpToFurthest(); 1043 1044 if( bWriteObj ) 1045 xPObj->write( Reference< XObjectOutputStream > ( 1046 SAL_STATIC_CAST( XObjectOutputStream * , this ) ) ); 1047 1048 sal_Int32 nObjLen = m_rMarkable->offsetToMark( nObjLenMark ) -4; 1049 m_rMarkable->jumpToMark( nObjLenMark ); 1050 // write length of the info data 1051 ODataOutputStream::writeLong( nObjLen ); 1052 // jump to the end of the stream 1053 m_rMarkable->jumpToFurthest(); 1054 1055 m_rMarkable->deleteMark( nObjLenMark ); 1056 m_rMarkable->deleteMark( nInfoLenMark ); 1057 } 1058 1059 1060 1061 void OObjectOutputStream::connectToMarkable(void) 1062 { 1063 if( ! m_bValidMarkable ) { 1064 if( ! m_bValidStream ) 1065 { 1066 throw NotConnectedException(); 1067 } 1068 1069 // find the markable stream ! 1070 Reference< XInterface > rTry(m_output); 1071 while( sal_True ) { 1072 if( ! rTry.is() ) 1073 { 1074 throw NotConnectedException(); 1075 } 1076 Reference < XMarkableStream > markable( rTry , UNO_QUERY ); 1077 if( markable.is() ) 1078 { 1079 m_rMarkable = markable; 1080 break; 1081 } 1082 Reference < XActiveDataSource > source( rTry , UNO_QUERY ); 1083 rTry = source; 1084 } 1085 m_bValidMarkable = sal_True; 1086 } 1087 } 1088 1089 1090 sal_Int32 OObjectOutputStream::createMark(void) 1091 { 1092 connectToMarkable(); // throws an exception, if a markable is not connected ! 1093 1094 return m_rMarkable->createMark(); 1095 } 1096 1097 void OObjectOutputStream::deleteMark(sal_Int32 Mark) 1098 { 1099 if( ! m_bValidMarkable ) 1100 { 1101 throw NotConnectedException(); 1102 } 1103 m_rMarkable->deleteMark( Mark ); 1104 } 1105 1106 void OObjectOutputStream::jumpToMark(sal_Int32 nMark) 1107 { 1108 if( ! m_bValidMarkable ) 1109 { 1110 throw NotConnectedException(); 1111 } 1112 m_rMarkable->jumpToMark( nMark ); 1113 } 1114 1115 1116 void OObjectOutputStream::jumpToFurthest(void) 1117 { 1118 connectToMarkable(); 1119 m_rMarkable->jumpToFurthest(); 1120 } 1121 1122 sal_Int32 OObjectOutputStream::offsetToMark(sal_Int32 nMark) 1123 { 1124 if( ! m_bValidMarkable ) 1125 { 1126 throw NotConnectedException(); 1127 } 1128 return m_rMarkable->offsetToMark( nMark ); 1129 } 1130 1131 1132 1133 1134 Reference< XInterface > SAL_CALL OObjectOutputStream_CreateInstance( const Reference < XComponentContext > & ) 1135 { 1136 OObjectOutputStream *p = new OObjectOutputStream; 1137 return Reference< XInterface > ( SAL_STATIC_CAST( OWeakObject * , p ) ); 1138 } 1139 1140 OUString OObjectOutputStream_getImplementationName() 1141 { 1142 return OUString( RTL_CONSTASCII_USTRINGPARAM( "com.sun.star.comp.io.stm.ObjectOutputStream" ) ); 1143 } 1144 1145 Sequence<OUString> OObjectOutputStream_getSupportedServiceNames(void) 1146 { 1147 Sequence<OUString> aRet(1); 1148 aRet.getArray()[0] = OUString( RTL_CONSTASCII_USTRINGPARAM( "com.sun.star.io.ObjectOutputStream" ) ); 1149 return aRet; 1150 } 1151 1152 Sequence< Type > SAL_CALL OObjectOutputStream::getTypes(void) 1153 { 1154 static OTypeCollection *pCollection = 0; 1155 if( ! pCollection ) 1156 { 1157 MutexGuard guard( Mutex::getGlobalMutex() ); 1158 if( ! pCollection ) 1159 { 1160 static OTypeCollection collection( 1161 getCppuType( (Reference< XMarkableStream > * ) 0 ), 1162 getCppuType( (Reference< XObjectOutputStream > * ) 0 ), 1163 ODataOutputStream::getTypes() ); 1164 pCollection = &collection; 1165 } 1166 } 1167 return (*pCollection).getTypes(); 1168 } 1169 1170 Sequence< sal_Int8 > SAL_CALL OObjectOutputStream::getImplementationId( ) 1171 { 1172 static OImplementationId *pId = 0; 1173 if( ! pId ) 1174 { 1175 MutexGuard guard( Mutex::getGlobalMutex() ); 1176 if( ! pId ) 1177 { 1178 static OImplementationId id( sal_False ); 1179 pId = &id; 1180 } 1181 } 1182 return (*pId).getImplementationId(); 1183 } 1184 1185 1186 // XServiceInfo 1187 OUString OObjectOutputStream::getImplementationName() throw () 1188 { 1189 return ODataInputStream_getImplementationName(); 1190 } 1191 1192 // XServiceInfo 1193 sal_Bool OObjectOutputStream::supportsService(const OUString& ServiceName) throw () 1194 { 1195 Sequence< OUString > aSNL = getSupportedServiceNames(); 1196 const OUString * pArray = aSNL.getConstArray(); 1197 1198 for( sal_Int32 i = 0; i < aSNL.getLength(); i++ ) 1199 if( pArray[i] == ServiceName ) 1200 return sal_True; 1201 1202 return sal_False; 1203 } 1204 1205 // XServiceInfo 1206 Sequence< OUString > OObjectOutputStream::getSupportedServiceNames(void) throw () 1207 { 1208 return OObjectOutputStream_getSupportedServiceNames(); 1209 } 1210 1211 1212 1213 1214 1215 class OObjectInputStream : 1216 public ODataInputStream, 1217 public XObjectInputStream, 1218 public XMarkableStream 1219 { 1220 public: 1221 OObjectInputStream( const Reference < XComponentContext > &r) 1222 : m_rSMgr( r->getServiceManager() ) 1223 , m_rCxt( r ) 1224 , m_bValidMarkable(sal_False) 1225 { 1226 g_moduleCount.modCnt.acquire( &g_moduleCount.modCnt ); 1227 } 1228 ~OObjectInputStream(); 1229 1230 public: 1231 Any SAL_CALL queryInterface( const Type &type ) throw(); 1232 void SAL_CALL acquire() throw() { ODataInputStream::acquire(); } 1233 void SAL_CALL release() throw() { ODataInputStream::release(); } 1234 1235 public: // XInputStream 1236 virtual sal_Int32 SAL_CALL readBytes(Sequence< sal_Int8 >& aData, sal_Int32 nBytesToRead) 1237 { return ODataInputStream::readBytes( aData , nBytesToRead ); } 1238 1239 virtual sal_Int32 SAL_CALL readSomeBytes(Sequence< sal_Int8 >& aData, sal_Int32 nMaxBytesToRead) 1240 { return ODataInputStream::readSomeBytes( aData, nMaxBytesToRead ); } 1241 1242 virtual void SAL_CALL skipBytes(sal_Int32 nBytesToSkip) 1243 { ODataInputStream::skipBytes( nBytesToSkip ); } 1244 1245 virtual sal_Int32 SAL_CALL available(void) 1246 { return ODataInputStream::available(); } 1247 1248 virtual void SAL_CALL closeInput(void) 1249 { ODataInputStream::closeInput(); } 1250 1251 public: // XDataInputStream 1252 virtual sal_Int8 SAL_CALL readBoolean(void) 1253 { return ODataInputStream::readBoolean(); } 1254 virtual sal_Int8 SAL_CALL readByte(void) 1255 { return ODataInputStream::readByte(); } 1256 virtual sal_Unicode SAL_CALL readChar(void) 1257 { return ODataInputStream::readChar(); } 1258 virtual sal_Int16 SAL_CALL readShort(void) 1259 { return ODataInputStream::readShort(); } 1260 virtual sal_Int32 SAL_CALL readLong(void) 1261 { return ODataInputStream::readLong(); } 1262 virtual sal_Int64 SAL_CALL readHyper(void) 1263 { return ODataInputStream::readHyper(); } 1264 virtual float SAL_CALL readFloat(void) 1265 { return ODataInputStream::readFloat(); } 1266 virtual double SAL_CALL readDouble(void) 1267 { return ODataInputStream::readDouble(); } 1268 virtual OUString SAL_CALL readUTF(void) 1269 { return ODataInputStream::readUTF(); } 1270 1271 public: // XObjectInputStream 1272 virtual Reference< XPersistObject > SAL_CALL readObject( ); 1273 1274 public: // XMarkableStream 1275 virtual sal_Int32 SAL_CALL createMark(void); 1276 virtual void SAL_CALL deleteMark(sal_Int32 Mark); 1277 virtual void SAL_CALL jumpToMark(sal_Int32 nMark); 1278 virtual void SAL_CALL jumpToFurthest(void); 1279 virtual sal_Int32 SAL_CALL offsetToMark(sal_Int32 nMark); 1280 1281 public: //XTypeProvider 1282 virtual ::com::sun::star::uno::Sequence< ::com::sun::star::uno::Type > SAL_CALL 1283 getTypes( ); 1284 virtual ::com::sun::star::uno::Sequence< sal_Int8 > SAL_CALL 1285 getImplementationId( ); 1286 1287 public: // XServiceInfo 1288 OUString SAL_CALL getImplementationName() throw (); 1289 Sequence< OUString > SAL_CALL getSupportedServiceNames(void) throw (); 1290 sal_Bool SAL_CALL supportsService(const OUString& ServiceName) throw (); 1291 1292 private: 1293 void connectToMarkable(); 1294 private: 1295 Reference < XMultiComponentFactory > m_rSMgr; 1296 Reference < XComponentContext > m_rCxt; 1297 sal_Bool m_bValidMarkable; 1298 Reference < XMarkableStream > m_rMarkable; 1299 vector < Reference< XPersistObject > > m_aPersistVector; 1300 1301 }; 1302 1303 OObjectInputStream::~OObjectInputStream() 1304 { 1305 g_moduleCount.modCnt.release( &g_moduleCount.modCnt ); 1306 } 1307 1308 Any OObjectInputStream::queryInterface( const Type &aType ) throw () 1309 { 1310 Any a = ::cppu::queryInterface( 1311 aType , 1312 SAL_STATIC_CAST( XMarkableStream * , this ), 1313 SAL_STATIC_CAST( XObjectInputStream * , this ) ); 1314 if( a.hasValue() ) 1315 { 1316 return a; 1317 } 1318 1319 return ODataInputStream::queryInterface( aType ); 1320 1321 } 1322 1323 Reference< XPersistObject > OObjectInputStream::readObject() 1324 { 1325 // check if chain contains a XMarkableStream 1326 connectToMarkable(); 1327 1328 Reference< XPersistObject > xLoadedObj; 1329 1330 // create Mark to skip newer versions 1331 sal_uInt32 nMark = m_rMarkable->createMark(); 1332 // length of the data 1333 sal_Int32 nLen = (sal_uInt16) ODataInputStream::readShort(); 1334 if( nLen < 0xc ) 1335 { 1336 throw WrongFormatException(); 1337 } 1338 1339 // read the object identifier 1340 sal_uInt32 nId = readLong(); 1341 1342 // the name of the persist model 1343 // MM ??? 1344 OUString aName = readUTF(); 1345 1346 // Read the length of the object 1347 sal_Int32 nObjLen = readLong(); 1348 if( ( 0 == nId && 0 != nObjLen ) ) 1349 { 1350 throw WrongFormatException(); 1351 } 1352 1353 // skip data of new version 1354 skipBytes( nLen - m_rMarkable->offsetToMark( nMark ) ); 1355 1356 sal_Bool bLoadSuccesfull = sal_True; 1357 if( nId ) 1358 { 1359 if( aName.getLength() ) 1360 { 1361 // load the object 1362 Reference< XInterface > x = m_rSMgr->createInstanceWithContext( aName, m_rCxt ); 1363 xLoadedObj = Reference< XPersistObject >( x, UNO_QUERY ); 1364 if( xLoadedObj.is() ) 1365 { 1366 sal_uInt32 nSize = m_aPersistVector.size(); 1367 if( nSize <= nId ) 1368 { 1369 // grow to the right size 1370 Reference< XPersistObject > xEmpty; 1371 m_aPersistVector.insert( m_aPersistVector.end(), (long)(nId - nSize + 1), xEmpty ); 1372 } 1373 1374 m_aPersistVector[nId] = xLoadedObj; 1375 xLoadedObj->read( Reference< XObjectInputStream >( 1376 SAL_STATIC_CAST( XObjectInputStream *, this ) ) ); 1377 } 1378 else 1379 { 1380 // no service with this name could be instantiated 1381 bLoadSuccesfull = sal_False; 1382 } 1383 } 1384 else { 1385 if( m_aPersistVector.size() < nId ) 1386 { 1387 // id unknown, load failure ! 1388 bLoadSuccesfull = sal_False; 1389 } 1390 else 1391 { 1392 // Object has alread been read, 1393 xLoadedObj = m_aPersistVector[nId]; 1394 } 1395 } 1396 } 1397 1398 // skip to the position behind the object 1399 skipBytes( nObjLen + nLen - m_rMarkable->offsetToMark( nMark ) ); 1400 m_rMarkable->deleteMark( nMark ); 1401 1402 if( ! bLoadSuccesfull ) 1403 { 1404 throw WrongFormatException(); 1405 } 1406 return xLoadedObj; 1407 } 1408 1409 1410 void OObjectInputStream::connectToMarkable() 1411 { 1412 if( ! m_bValidMarkable ) { 1413 if( ! m_bValidStream ) 1414 { 1415 throw NotConnectedException( ); 1416 } 1417 1418 // find the markable stream ! 1419 Reference< XInterface > rTry(m_input); 1420 while( sal_True ) { 1421 if( ! rTry.is() ) 1422 { 1423 throw NotConnectedException( ); 1424 } 1425 Reference< XMarkableStream > markable( rTry , UNO_QUERY ); 1426 if( markable.is() ) 1427 { 1428 m_rMarkable = markable; 1429 break; 1430 } 1431 Reference < XActiveDataSink > sink( rTry , UNO_QUERY ); 1432 rTry = sink; 1433 } 1434 m_bValidMarkable = sal_True; 1435 } 1436 } 1437 1438 sal_Int32 OObjectInputStream::createMark(void) 1439 { 1440 connectToMarkable(); // throws an exception, if a markable is not connected ! 1441 1442 return m_rMarkable->createMark(); 1443 } 1444 1445 void OObjectInputStream::deleteMark(sal_Int32 Mark) 1446 { 1447 if( ! m_bValidMarkable ) 1448 { 1449 throw NotConnectedException(); 1450 } 1451 m_rMarkable->deleteMark( Mark ); 1452 } 1453 1454 void OObjectInputStream::jumpToMark(sal_Int32 nMark) 1455 { 1456 if( ! m_bValidMarkable ) 1457 { 1458 throw NotConnectedException(); 1459 } 1460 m_rMarkable->jumpToMark( nMark ); 1461 } 1462 void OObjectInputStream::jumpToFurthest(void) 1463 { 1464 connectToMarkable(); 1465 m_rMarkable->jumpToFurthest(); 1466 } 1467 1468 sal_Int32 OObjectInputStream::offsetToMark(sal_Int32 nMark) 1469 { 1470 if( ! m_bValidMarkable ) 1471 { 1472 throw NotConnectedException(); 1473 } 1474 return m_rMarkable->offsetToMark( nMark ); 1475 } 1476 1477 1478 Sequence< Type > SAL_CALL OObjectInputStream::getTypes(void) 1479 { 1480 static OTypeCollection *pCollection = 0; 1481 if( ! pCollection ) 1482 { 1483 MutexGuard guard( Mutex::getGlobalMutex() ); 1484 if( ! pCollection ) 1485 { 1486 static OTypeCollection collection( 1487 getCppuType( (Reference< XMarkableStream > * ) 0 ), 1488 getCppuType( (Reference< XObjectInputStream > * ) 0 ), 1489 ODataInputStream::getTypes() ); 1490 pCollection = &collection; 1491 } 1492 } 1493 return (*pCollection).getTypes(); 1494 } 1495 1496 Sequence< sal_Int8 > SAL_CALL OObjectInputStream::getImplementationId( ) 1497 { 1498 static OImplementationId *pId = 0; 1499 if( ! pId ) 1500 { 1501 MutexGuard guard( Mutex::getGlobalMutex() ); 1502 if( ! pId ) 1503 { 1504 static OImplementationId id( sal_False ); 1505 pId = &id; 1506 } 1507 } 1508 return (*pId).getImplementationId(); 1509 } 1510 1511 1512 // XServiceInfo 1513 OUString OObjectInputStream::getImplementationName() throw () 1514 { 1515 return OObjectInputStream_getImplementationName(); 1516 } 1517 1518 // XServiceInfo 1519 sal_Bool OObjectInputStream::supportsService(const OUString& ServiceName) throw () 1520 { 1521 Sequence< OUString > aSNL = getSupportedServiceNames(); 1522 const OUString * pArray = aSNL.getConstArray(); 1523 1524 for( sal_Int32 i = 0; i < aSNL.getLength(); i++ ) 1525 if( pArray[i] == ServiceName ) 1526 return sal_True; 1527 1528 return sal_False; 1529 } 1530 1531 // XServiceInfo 1532 Sequence< OUString > OObjectInputStream::getSupportedServiceNames(void) throw () 1533 { 1534 return OObjectInputStream_getSupportedServiceNames(); 1535 } 1536 1537 1538 1539 1540 Reference< XInterface > SAL_CALL OObjectInputStream_CreateInstance( const Reference < XComponentContext > & rCtx ) 1541 { 1542 OObjectInputStream *p = new OObjectInputStream( rCtx ); 1543 return Reference< XInterface> ( SAL_STATIC_CAST( OWeakObject *, p ) ); 1544 } 1545 1546 OUString OObjectInputStream_getImplementationName() 1547 { 1548 return OUString( RTL_CONSTASCII_USTRINGPARAM( "com.sun.star.comp.io.stm.ObjectInputStream" ) ); 1549 } 1550 1551 Sequence<OUString> OObjectInputStream_getSupportedServiceNames(void) 1552 { 1553 Sequence<OUString> aRet(1); 1554 aRet.getArray()[0] = OUString( RTL_CONSTASCII_USTRINGPARAM( "com.sun.star.io.ObjectInputStream" ) ); 1555 return aRet; 1556 } 1557 1558 } 1559