1 /************************************************************************* 2 * 3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. 4 * 5 * Copyright 2000, 2010 Oracle and/or its affiliates. 6 * 7 * OpenOffice.org - a multi-platform office productivity suite 8 * 9 * This file is part of OpenOffice.org. 10 * 11 * OpenOffice.org is free software: you can redistribute it and/or modify 12 * it under the terms of the GNU Lesser General Public License version 3 13 * only, as published by the Free Software Foundation. 14 * 15 * OpenOffice.org is distributed in the hope that it will be useful, 16 * but WITHOUT ANY WARRANTY; without even the implied warranty of 17 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 18 * GNU Lesser General Public License version 3 for more details 19 * (a copy is included in the LICENSE file that accompanied this code). 20 * 21 * You should have received a copy of the GNU Lesser General Public License 22 * version 3 along with OpenOffice.org. If not, see 23 * <http://www.openoffice.org/license.html> 24 * for a copy of the LGPLv3 License. 25 * 26 ************************************************************************/ 27 28 // MARKER(update_precomp.py): autogen include statement, do not remove 29 #include "precompiled_ucb.hxx" 30 31 /************************************************************************** 32 TODO 33 ************************************************************************** 34 35 - remove root storage access workaround 36 37 *************************************************************************/ 38 39 #include "com/sun/star/lang/DisposedException.hpp" 40 #include "com/sun/star/reflection/XProxyFactory.hpp" 41 42 #include "tdoc_uri.hxx" 43 44 #include "tdoc_stgelems.hxx" 45 46 using namespace com::sun::star; 47 using namespace tdoc_ucp; 48 49 //========================================================================= 50 //========================================================================= 51 // 52 // ParentStorageHolder Implementation. 53 // 54 //========================================================================= 55 //========================================================================= 56 57 ParentStorageHolder::ParentStorageHolder( 58 const uno::Reference< embed::XStorage > & xParentStorage, 59 const rtl::OUString & rUri ) 60 : m_xParentStorage( xParentStorage ), 61 m_bParentIsRootStorage( false ) 62 { 63 Uri aUri( rUri ); 64 if ( aUri.isDocument() ) 65 m_bParentIsRootStorage = true; 66 } 67 68 //========================================================================= 69 //========================================================================= 70 // 71 // Storage Implementation. 72 // 73 //========================================================================= 74 //========================================================================= 75 76 Storage::Storage( const uno::Reference< lang::XMultiServiceFactory > & xSMgr, 77 const rtl::Reference< StorageElementFactory > & xFactory, 78 const rtl::OUString & rUri, 79 const uno::Reference< embed::XStorage > & xParentStorage, 80 const uno::Reference< embed::XStorage > & xStorageToWrap ) 81 : ParentStorageHolder( xParentStorage, Uri( rUri ).getParentUri() ), 82 m_xFactory( xFactory ), 83 m_xWrappedStorage( xStorageToWrap ), 84 m_xWrappedTransObj( xStorageToWrap, uno::UNO_QUERY ), // optional interface 85 m_xWrappedComponent( xStorageToWrap, uno::UNO_QUERY ), 86 m_xWrappedTypeProv( xStorageToWrap, uno::UNO_QUERY ), 87 m_bIsDocumentStorage( Uri( rUri ).isDocument() ) 88 { 89 OSL_ENSURE( m_xWrappedStorage.is(), 90 "Storage::Storage: No storage to wrap!" ); 91 92 OSL_ENSURE( m_xWrappedComponent.is(), 93 "Storage::Storage: No component to wrap!" ); 94 95 OSL_ENSURE( m_xWrappedTypeProv.is(), 96 "Storage::Storage: No Type Provider!" ); 97 98 // Use proxy factory service to create aggregatable proxy. 99 try 100 { 101 uno::Reference< reflection::XProxyFactory > xProxyFac( 102 xSMgr->createInstance( 103 rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( 104 "com.sun.star.reflection.ProxyFactory" ) ) ), 105 uno::UNO_QUERY ); 106 if ( xProxyFac.is() ) 107 { 108 m_xAggProxy = xProxyFac->createProxy( m_xWrappedStorage ); 109 } 110 } 111 catch ( uno::Exception const & ) 112 { 113 OSL_ENSURE( false, "Storage::Storage: Caught exception!" ); 114 } 115 116 OSL_ENSURE( m_xAggProxy.is(), 117 "Storage::Storage: Wrapped storage cannot be aggregated!" ); 118 119 if ( m_xAggProxy.is() ) 120 { 121 osl_incrementInterlockedCount( &m_refCount ); 122 { 123 // Solaris compiler problem: 124 // Extra block to enforce destruction of temporary object created 125 // in next statement _before_ osl_decrementInterlockedCount is 126 // called. Otherwise 'this' will destroy itself even before ctor 127 // is completed (See impl. of XInterface::release())! 128 129 m_xAggProxy->setDelegator( 130 static_cast< cppu::OWeakObject * >( this ) ); 131 } 132 osl_decrementInterlockedCount( &m_refCount ); 133 } 134 } 135 136 //========================================================================= 137 // virtual 138 Storage::~Storage() 139 { 140 if ( m_xAggProxy.is() ) 141 m_xAggProxy->setDelegator( uno::Reference< uno::XInterface >() ); 142 143 // Never dispose a document storage. Not owner! 144 if ( !isDocumentStorage() ) 145 { 146 if ( m_xWrappedComponent.is() ) 147 { 148 // "Auto-dispose"... 149 try 150 { 151 m_xWrappedComponent->dispose(); 152 } 153 catch ( lang::DisposedException const & ) 154 { 155 // might happen. 156 } 157 catch ( ... ) 158 { 159 OSL_ENSURE( false, "Storage::~Storage - Caught exception!" ); 160 } 161 } 162 } 163 } 164 165 //========================================================================= 166 // 167 // uno::XInterface 168 // 169 //========================================================================= 170 171 // virtual 172 uno::Any SAL_CALL Storage::queryInterface( const uno::Type& aType ) 173 throw ( uno::RuntimeException ) 174 { 175 // First, try to use interfaces implemented by myself and base class(es) 176 uno::Any aRet = StorageUNOBase::queryInterface( aType ); 177 178 if ( aRet.hasValue() ) 179 return aRet; 180 181 // Try to use requested interface from aggregated storage 182 return m_xAggProxy->queryAggregation( aType ); 183 } 184 185 //========================================================================= 186 // virtual 187 void SAL_CALL Storage::acquire() 188 throw () 189 { 190 osl_incrementInterlockedCount( &m_refCount ); 191 } 192 193 //========================================================================= 194 // virtual 195 void SAL_CALL Storage::release() 196 throw () 197 { 198 if ( osl_decrementInterlockedCount( &m_refCount ) == 0 ) 199 { 200 m_xFactory->releaseElement( this ); 201 delete this; 202 } 203 } 204 205 //========================================================================= 206 // 207 // lang::XTypeProvider 208 // 209 //========================================================================= 210 211 // virtual 212 uno::Sequence< uno::Type > SAL_CALL Storage::getTypes() 213 throw ( uno::RuntimeException ) 214 { 215 return m_xWrappedTypeProv->getTypes(); 216 } 217 218 //========================================================================= 219 // virtual 220 uno::Sequence< sal_Int8 > SAL_CALL Storage::getImplementationId() 221 throw ( uno::RuntimeException ) 222 { 223 return m_xWrappedTypeProv->getImplementationId(); 224 } 225 226 //========================================================================= 227 // 228 // lang::XComponent (base of embed::XStorage) 229 // 230 //========================================================================= 231 // virtual 232 void SAL_CALL Storage::dispose() 233 throw ( uno::RuntimeException ) 234 { 235 m_xWrappedStorage->dispose(); 236 } 237 238 //========================================================================= 239 // virtual 240 void SAL_CALL Storage::addEventListener( 241 const uno::Reference< lang::XEventListener >& xListener ) 242 throw ( uno::RuntimeException ) 243 { 244 m_xWrappedStorage->addEventListener( xListener ); 245 } 246 //========================================================================= 247 // virtual 248 void SAL_CALL Storage::removeEventListener( 249 const uno::Reference< lang::XEventListener >& aListener ) 250 throw (uno::RuntimeException) 251 { 252 m_xWrappedStorage->removeEventListener( aListener ); 253 } 254 255 //========================================================================= 256 // 257 // container::XElementAccess (base of container::XNameAccess) 258 // 259 //========================================================================= 260 261 // virtual 262 uno::Type SAL_CALL Storage::getElementType() 263 throw ( uno::RuntimeException ) 264 { 265 return m_xWrappedStorage->getElementType(); 266 } 267 268 //========================================================================= 269 // virtual 270 ::sal_Bool SAL_CALL Storage::hasElements() 271 throw ( uno::RuntimeException ) 272 { 273 return m_xWrappedStorage->hasElements(); 274 } 275 276 //========================================================================= 277 // 278 // container::XNameAccess (base of embed::XStorage) 279 // 280 //========================================================================= 281 282 // virtual 283 uno::Any SAL_CALL Storage::getByName( const ::rtl::OUString& aName ) 284 throw ( container::NoSuchElementException, 285 lang::WrappedTargetException, 286 uno::RuntimeException ) 287 { 288 return m_xWrappedStorage->getByName( aName ); 289 } 290 291 //========================================================================= 292 // virtual 293 uno::Sequence< ::rtl::OUString > SAL_CALL Storage::getElementNames() 294 throw ( uno::RuntimeException ) 295 { 296 return m_xWrappedStorage->getElementNames(); 297 } 298 299 //========================================================================= 300 // virtual 301 ::sal_Bool SAL_CALL Storage::hasByName( const ::rtl::OUString& aName ) 302 throw ( uno::RuntimeException ) 303 { 304 return m_xWrappedStorage->hasByName( aName ); 305 } 306 307 //========================================================================= 308 // 309 // embed::XStorage 310 // 311 //========================================================================= 312 313 // virtual 314 void SAL_CALL Storage::copyToStorage( 315 const uno::Reference< embed::XStorage >& xDest ) 316 throw ( embed::InvalidStorageException, 317 lang::IllegalArgumentException, 318 io::IOException, 319 embed::StorageWrappedTargetException, 320 uno::RuntimeException ) 321 { 322 m_xWrappedStorage->copyToStorage( xDest ); 323 } 324 325 //========================================================================= 326 // virtual 327 uno::Reference< io::XStream > SAL_CALL Storage::openStreamElement( 328 const ::rtl::OUString& aStreamName, sal_Int32 nOpenMode ) 329 throw ( embed::InvalidStorageException, 330 lang::IllegalArgumentException, 331 packages::WrongPasswordException, 332 io::IOException, 333 embed::StorageWrappedTargetException, 334 uno::RuntimeException ) 335 { 336 return m_xWrappedStorage->openStreamElement( aStreamName, nOpenMode ); 337 } 338 339 //========================================================================= 340 // virtual 341 uno::Reference< io::XStream > SAL_CALL Storage::openEncryptedStreamElement( 342 const ::rtl::OUString& aStreamName, 343 sal_Int32 nOpenMode, 344 const ::rtl::OUString& aPassword ) 345 throw ( embed::InvalidStorageException, 346 lang::IllegalArgumentException, 347 packages::NoEncryptionException, 348 packages::WrongPasswordException, 349 io::IOException, 350 embed::StorageWrappedTargetException, 351 uno::RuntimeException ) 352 { 353 return m_xWrappedStorage->openEncryptedStreamElement( 354 aStreamName, nOpenMode, aPassword ); 355 } 356 357 //========================================================================= 358 // virtual 359 uno::Reference< embed::XStorage > SAL_CALL Storage::openStorageElement( 360 const ::rtl::OUString& aStorName, sal_Int32 nOpenMode ) 361 throw ( embed::InvalidStorageException, 362 lang::IllegalArgumentException, 363 io::IOException, 364 embed::StorageWrappedTargetException, 365 uno::RuntimeException ) 366 { 367 return m_xWrappedStorage->openStorageElement( aStorName, nOpenMode ); 368 } 369 370 //========================================================================= 371 // virtual 372 uno::Reference< io::XStream > SAL_CALL Storage::cloneStreamElement( 373 const ::rtl::OUString& aStreamName ) 374 throw ( embed::InvalidStorageException, 375 lang::IllegalArgumentException, 376 packages::WrongPasswordException, 377 io::IOException, 378 embed::StorageWrappedTargetException, 379 uno::RuntimeException ) 380 { 381 return m_xWrappedStorage->cloneStreamElement( aStreamName ); 382 } 383 384 //========================================================================= 385 // virtual 386 uno::Reference< io::XStream > SAL_CALL Storage::cloneEncryptedStreamElement( 387 const ::rtl::OUString& aStreamName, 388 const ::rtl::OUString& aPassword ) 389 throw ( embed::InvalidStorageException, 390 lang::IllegalArgumentException, 391 packages::NoEncryptionException, 392 packages::WrongPasswordException, 393 io::IOException, 394 embed::StorageWrappedTargetException, 395 uno::RuntimeException ) 396 { 397 return m_xWrappedStorage->cloneEncryptedStreamElement( aStreamName, 398 aPassword ); 399 } 400 401 //========================================================================= 402 // virtual 403 void SAL_CALL Storage::copyLastCommitTo( 404 const uno::Reference< embed::XStorage >& xTargetStorage ) 405 throw ( embed::InvalidStorageException, 406 lang::IllegalArgumentException, 407 io::IOException, 408 embed::StorageWrappedTargetException, 409 uno::RuntimeException) 410 { 411 m_xWrappedStorage->copyLastCommitTo( xTargetStorage ); 412 } 413 414 //========================================================================= 415 // virtual 416 void SAL_CALL Storage::copyStorageElementLastCommitTo( 417 const ::rtl::OUString& aStorName, 418 const uno::Reference< embed::XStorage >& xTargetStorage ) 419 throw ( embed::InvalidStorageException, 420 lang::IllegalArgumentException, 421 io::IOException, 422 embed::StorageWrappedTargetException, 423 uno::RuntimeException) 424 { 425 m_xWrappedStorage->copyStorageElementLastCommitTo( aStorName, xTargetStorage ); 426 } 427 428 //========================================================================= 429 // virtual 430 sal_Bool SAL_CALL Storage::isStreamElement( 431 const ::rtl::OUString& aElementName ) 432 throw ( container::NoSuchElementException, 433 lang::IllegalArgumentException, 434 embed::InvalidStorageException, 435 uno::RuntimeException ) 436 { 437 return m_xWrappedStorage->isStreamElement( aElementName ); 438 } 439 440 //========================================================================= 441 // virtual 442 sal_Bool SAL_CALL Storage::isStorageElement( 443 const ::rtl::OUString& aElementName ) 444 throw ( container::NoSuchElementException, 445 lang::IllegalArgumentException, 446 embed::InvalidStorageException, 447 uno::RuntimeException ) 448 { 449 return m_xWrappedStorage->isStorageElement( aElementName ); 450 } 451 452 //========================================================================= 453 // virtual 454 void SAL_CALL Storage::removeElement( const ::rtl::OUString& aElementName ) 455 throw ( embed::InvalidStorageException, 456 lang::IllegalArgumentException, 457 container::NoSuchElementException, 458 io::IOException, 459 embed::StorageWrappedTargetException, 460 uno::RuntimeException ) 461 { 462 m_xWrappedStorage->removeElement( aElementName ); 463 } 464 465 //========================================================================= 466 // virtual 467 void SAL_CALL Storage::renameElement( const ::rtl::OUString& aEleName, 468 const ::rtl::OUString& aNewName ) 469 throw ( embed::InvalidStorageException, 470 lang::IllegalArgumentException, 471 container::NoSuchElementException, 472 container::ElementExistException, 473 io::IOException, 474 embed::StorageWrappedTargetException, 475 uno::RuntimeException ) 476 { 477 m_xWrappedStorage->renameElement( aEleName, aNewName ); 478 } 479 480 //========================================================================= 481 // virtual 482 void SAL_CALL Storage::copyElementTo( 483 const ::rtl::OUString& aElementName, 484 const uno::Reference< embed::XStorage >& xDest, 485 const ::rtl::OUString& aNewName ) 486 throw ( embed::InvalidStorageException, 487 lang::IllegalArgumentException, 488 container::NoSuchElementException, 489 container::ElementExistException, 490 io::IOException, 491 embed::StorageWrappedTargetException, 492 uno::RuntimeException ) 493 { 494 m_xWrappedStorage->copyElementTo( aElementName, xDest, aNewName ); 495 } 496 497 //========================================================================= 498 // virtual 499 void SAL_CALL Storage::moveElementTo( 500 const ::rtl::OUString& aElementName, 501 const uno::Reference< embed::XStorage >& xDest, 502 const ::rtl::OUString& rNewName ) 503 throw ( embed::InvalidStorageException, 504 lang::IllegalArgumentException, 505 container::NoSuchElementException, 506 container::ElementExistException, 507 io::IOException, 508 embed::StorageWrappedTargetException, 509 uno::RuntimeException ) 510 { 511 m_xWrappedStorage->moveElementTo( aElementName, xDest, rNewName ); 512 } 513 514 //========================================================================= 515 // 516 // embed::XTransactedObject 517 // 518 //========================================================================= 519 520 // virtual 521 void SAL_CALL Storage::commit() 522 throw ( io::IOException, 523 lang::WrappedTargetException, 524 uno::RuntimeException ) 525 { 526 // Never commit a root storage (-> has no parent)! 527 // Would lead in writing the whole document to disk. 528 529 uno::Reference< embed::XStorage > xParentStorage = getParentStorage(); 530 if ( xParentStorage.is() ) 531 { 532 OSL_ENSURE( m_xWrappedTransObj.is(), "No XTransactedObject interface!" ); 533 534 if ( m_xWrappedTransObj.is() ) 535 { 536 m_xWrappedTransObj->commit(); 537 538 if ( !isParentARootStorage() ) 539 { 540 uno::Reference< embed::XTransactedObject > xParentTA( 541 xParentStorage, uno::UNO_QUERY ); 542 OSL_ENSURE( xParentTA.is(), "No XTransactedObject interface!" ); 543 544 if ( xParentTA.is() ) 545 xParentTA->commit(); 546 } 547 } 548 } 549 } 550 551 //========================================================================= 552 // virtual 553 void SAL_CALL Storage::revert() 554 throw ( io::IOException, 555 lang::WrappedTargetException, 556 uno::RuntimeException ) 557 { 558 uno::Reference< embed::XStorage > xParentStorage = getParentStorage(); 559 if ( xParentStorage.is() ) 560 { 561 OSL_ENSURE( m_xWrappedTransObj.is(), "No XTransactedObject interface!" ); 562 563 if ( m_xWrappedTransObj.is() ) 564 { 565 m_xWrappedTransObj->revert(); 566 567 if ( !isParentARootStorage() ) 568 { 569 uno::Reference< embed::XTransactedObject > xParentTA( 570 xParentStorage, uno::UNO_QUERY ); 571 OSL_ENSURE( xParentTA.is(), "No XTransactedObject interface!" ); 572 573 if ( xParentTA.is() ) 574 xParentTA->revert(); 575 } 576 } 577 } 578 } 579 580 //========================================================================= 581 //========================================================================= 582 // 583 // OutputStream Implementation. 584 // 585 //========================================================================= 586 //========================================================================= 587 588 OutputStream::OutputStream( 589 const uno::Reference< lang::XMultiServiceFactory > & xSMgr, 590 const rtl::OUString & rUri, 591 const uno::Reference< embed::XStorage > & xParentStorage, 592 const uno::Reference< io::XOutputStream > & xStreamToWrap ) 593 : ParentStorageHolder( xParentStorage, Uri( rUri ).getParentUri() ), 594 m_xWrappedStream( xStreamToWrap ), 595 m_xWrappedComponent( xStreamToWrap, uno::UNO_QUERY ), 596 m_xWrappedTypeProv( xStreamToWrap, uno::UNO_QUERY ) 597 { 598 OSL_ENSURE( m_xWrappedStream.is(), 599 "OutputStream::OutputStream: No stream to wrap!" ); 600 601 OSL_ENSURE( m_xWrappedComponent.is(), 602 "OutputStream::OutputStream: No component to wrap!" ); 603 604 OSL_ENSURE( m_xWrappedTypeProv.is(), 605 "OutputStream::OutputStream: No Type Provider!" ); 606 607 // Use proxy factory service to create aggregatable proxy. 608 try 609 { 610 uno::Reference< reflection::XProxyFactory > xProxyFac( 611 xSMgr->createInstance( 612 rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( 613 "com.sun.star.reflection.ProxyFactory" ) ) ), 614 uno::UNO_QUERY ); 615 if ( xProxyFac.is() ) 616 { 617 m_xAggProxy = xProxyFac->createProxy( m_xWrappedStream ); 618 } 619 } 620 catch ( uno::Exception const & ) 621 { 622 OSL_ENSURE( false, "OutputStream::OutputStream: Caught exception!" ); 623 } 624 625 OSL_ENSURE( m_xAggProxy.is(), 626 "OutputStream::OutputStream: Wrapped stream cannot be aggregated!" ); 627 628 if ( m_xAggProxy.is() ) 629 { 630 osl_incrementInterlockedCount( &m_refCount ); 631 { 632 // Solaris compiler problem: 633 // Extra block to enforce destruction of temporary object created 634 // in next statement _before_ osl_decrementInterlockedCount is 635 // called. Otherwise 'this' will destroy itself even before ctor 636 // is completed (See impl. of XInterface::release())! 637 638 m_xAggProxy->setDelegator( 639 static_cast< cppu::OWeakObject * >( this ) ); 640 } 641 osl_decrementInterlockedCount( &m_refCount ); 642 } 643 } 644 645 //========================================================================= 646 // virtual 647 OutputStream::~OutputStream() 648 { 649 if ( m_xAggProxy.is() ) 650 m_xAggProxy->setDelegator( uno::Reference< uno::XInterface >() ); 651 } 652 653 //========================================================================= 654 // 655 // uno::XInterface 656 // 657 //========================================================================= 658 659 // virtual 660 uno::Any SAL_CALL OutputStream::queryInterface( const uno::Type& aType ) 661 throw ( uno::RuntimeException ) 662 { 663 uno::Any aRet = OutputStreamUNOBase::queryInterface( aType ); 664 665 if ( aRet.hasValue() ) 666 return aRet; 667 668 if ( m_xAggProxy.is() ) 669 return m_xAggProxy->queryAggregation( aType ); 670 else 671 return uno::Any(); 672 } 673 674 //========================================================================= 675 // 676 // lang::XTypeProvider 677 // 678 //========================================================================= 679 680 // virtual 681 uno::Sequence< uno::Type > SAL_CALL OutputStream::getTypes() 682 throw ( uno::RuntimeException ) 683 { 684 return m_xWrappedTypeProv->getTypes(); 685 } 686 687 //========================================================================= 688 // virtual 689 uno::Sequence< sal_Int8 > SAL_CALL OutputStream::getImplementationId() 690 throw ( uno::RuntimeException ) 691 { 692 return m_xWrappedTypeProv->getImplementationId(); 693 } 694 695 //========================================================================= 696 // 697 // io::XOutputStream 698 // 699 //========================================================================= 700 701 // virtual 702 void SAL_CALL 703 OutputStream::writeBytes( const uno::Sequence< sal_Int8 >& aData ) 704 throw ( io::NotConnectedException, 705 io::BufferSizeExceededException, 706 io::IOException, 707 uno::RuntimeException ) 708 { 709 m_xWrappedStream->writeBytes( aData ); 710 } 711 712 //========================================================================= 713 // virtual 714 void SAL_CALL 715 OutputStream::flush() 716 throw ( io::NotConnectedException, 717 io::BufferSizeExceededException, 718 io::IOException, 719 uno::RuntimeException ) 720 { 721 m_xWrappedStream->flush(); 722 } 723 724 //========================================================================= 725 // virtual 726 void SAL_CALL 727 OutputStream::closeOutput( ) 728 throw ( io::NotConnectedException, 729 io::BufferSizeExceededException, 730 io::IOException, 731 uno::RuntimeException ) 732 { 733 m_xWrappedStream->closeOutput(); 734 735 // Release parent storage. 736 // Now, that the stream is closed/disposed it is not needed any longer. 737 setParentStorage( uno::Reference< embed::XStorage >() ); 738 } 739 740 //========================================================================= 741 // 742 // lang::XComponent 743 // 744 //========================================================================= 745 746 // virtual 747 void SAL_CALL 748 OutputStream::dispose() 749 throw ( uno::RuntimeException ) 750 { 751 m_xWrappedComponent->dispose(); 752 753 // Release parent storage. 754 // Now, that the stream is closed/disposed it is not needed any longer. 755 setParentStorage( uno::Reference< embed::XStorage >() ); 756 } 757 758 //========================================================================= 759 // virtual 760 void SAL_CALL 761 OutputStream::addEventListener( 762 const uno::Reference< lang::XEventListener >& xListener ) 763 throw ( uno::RuntimeException ) 764 { 765 m_xWrappedComponent->addEventListener( xListener ); 766 } 767 768 //========================================================================= 769 // virtual 770 void SAL_CALL 771 OutputStream::removeEventListener( 772 const uno::Reference< lang::XEventListener >& aListener ) 773 throw ( uno::RuntimeException ) 774 { 775 m_xWrappedComponent->removeEventListener( aListener ); 776 } 777 778 //========================================================================= 779 //========================================================================= 780 // 781 // Stream Implementation. 782 // 783 //========================================================================= 784 //========================================================================= 785 786 Stream::Stream( 787 const uno::Reference< lang::XMultiServiceFactory > & xSMgr, 788 const rtl::OUString & rUri, 789 const uno::Reference< embed::XStorage > & xParentStorage, 790 const uno::Reference< io::XStream > & xStreamToWrap ) 791 : ParentStorageHolder( xParentStorage, Uri( rUri ).getParentUri() ), 792 m_xWrappedStream( xStreamToWrap ), 793 m_xWrappedOutputStream( xStreamToWrap->getOutputStream() ), // might be empty 794 m_xWrappedTruncate( m_xWrappedOutputStream, uno::UNO_QUERY ), // might be empty 795 m_xWrappedInputStream( xStreamToWrap->getInputStream(), uno::UNO_QUERY ), 796 m_xWrappedComponent( xStreamToWrap, uno::UNO_QUERY ), 797 m_xWrappedTypeProv( xStreamToWrap, uno::UNO_QUERY ) 798 { 799 OSL_ENSURE( m_xWrappedStream.is(), 800 "OutputStream::OutputStream: No stream to wrap!" ); 801 802 OSL_ENSURE( m_xWrappedComponent.is(), 803 "OutputStream::OutputStream: No component to wrap!" ); 804 805 OSL_ENSURE( m_xWrappedTypeProv.is(), 806 "OutputStream::OutputStream: No Type Provider!" ); 807 808 // Use proxy factory service to create aggregatable proxy. 809 try 810 { 811 uno::Reference< reflection::XProxyFactory > xProxyFac( 812 xSMgr->createInstance( 813 rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( 814 "com.sun.star.reflection.ProxyFactory" ) ) ), 815 uno::UNO_QUERY ); 816 if ( xProxyFac.is() ) 817 { 818 m_xAggProxy = xProxyFac->createProxy( m_xWrappedStream ); 819 } 820 } 821 catch ( uno::Exception const & ) 822 { 823 OSL_ENSURE( false, "OutputStream::OutputStream: Caught exception!" ); 824 } 825 826 OSL_ENSURE( m_xAggProxy.is(), 827 "OutputStream::OutputStream: Wrapped stream cannot be aggregated!" ); 828 829 if ( m_xAggProxy.is() ) 830 { 831 osl_incrementInterlockedCount( &m_refCount ); 832 { 833 // Solaris compiler problem: 834 // Extra block to enforce destruction of temporary object created 835 // in next statement _before_ osl_decrementInterlockedCount is 836 // called. Otherwise 'this' will destroy itself even before ctor 837 // is completed (See impl. of XInterface::release())! 838 839 m_xAggProxy->setDelegator( 840 static_cast< cppu::OWeakObject * >( this ) ); 841 } 842 osl_decrementInterlockedCount( &m_refCount ); 843 } 844 } 845 846 //========================================================================= 847 // virtual 848 Stream::~Stream() 849 { 850 if ( m_xAggProxy.is() ) 851 m_xAggProxy->setDelegator( uno::Reference< uno::XInterface >() ); 852 } 853 854 //========================================================================= 855 // 856 // uno::XInterface 857 // 858 //========================================================================= 859 860 // virtual 861 uno::Any SAL_CALL Stream::queryInterface( const uno::Type& aType ) 862 throw ( uno::RuntimeException ) 863 { 864 uno::Any aRet = StreamUNOBase::queryInterface( aType ); 865 866 if ( aRet.hasValue() ) 867 return aRet; 868 869 if ( m_xAggProxy.is() ) 870 return m_xAggProxy->queryAggregation( aType ); 871 else 872 return uno::Any(); 873 } 874 875 //========================================================================= 876 // 877 // lang::XTypeProvider 878 // 879 //========================================================================= 880 881 // virtual 882 uno::Sequence< uno::Type > SAL_CALL Stream::getTypes() 883 throw ( uno::RuntimeException ) 884 { 885 return m_xWrappedTypeProv->getTypes(); 886 } 887 888 //========================================================================= 889 // virtual 890 uno::Sequence< sal_Int8 > SAL_CALL Stream::getImplementationId() 891 throw ( uno::RuntimeException ) 892 { 893 return m_xWrappedTypeProv->getImplementationId(); 894 } 895 896 //========================================================================= 897 // 898 // io::XStream. 899 // 900 //========================================================================= 901 902 // virtual 903 uno::Reference< io::XInputStream > SAL_CALL Stream::getInputStream() 904 throw( uno::RuntimeException ) 905 { 906 return uno::Reference< io::XInputStream >( this ); 907 } 908 909 //========================================================================= 910 // virtual 911 uno::Reference< io::XOutputStream > SAL_CALL Stream::getOutputStream() 912 throw( uno::RuntimeException ) 913 { 914 return uno::Reference< io::XOutputStream >( this ); 915 } 916 917 //========================================================================= 918 // 919 // io::XOutputStream. 920 // 921 //========================================================================= 922 923 // virtual 924 void SAL_CALL Stream::writeBytes( const uno::Sequence< sal_Int8 >& aData ) 925 throw( io::NotConnectedException, 926 io::BufferSizeExceededException, 927 io::IOException, 928 uno::RuntimeException ) 929 { 930 if ( m_xWrappedOutputStream.is() ) 931 { 932 m_xWrappedOutputStream->writeBytes( aData ); 933 commitChanges(); 934 } 935 } 936 937 //========================================================================= 938 // virtual 939 void SAL_CALL Stream::flush() 940 throw( io::NotConnectedException, 941 io::BufferSizeExceededException, 942 io::IOException, 943 uno::RuntimeException ) 944 { 945 if ( m_xWrappedOutputStream.is() ) 946 { 947 m_xWrappedOutputStream->flush(); 948 commitChanges(); 949 } 950 } 951 952 //========================================================================= 953 // virtual 954 void SAL_CALL Stream::closeOutput() 955 throw( io::NotConnectedException, 956 io::IOException, 957 uno::RuntimeException ) 958 { 959 if ( m_xWrappedOutputStream.is() ) 960 { 961 m_xWrappedOutputStream->closeOutput(); 962 commitChanges(); 963 } 964 965 // Release parent storage. 966 // Now, that the stream is closed/disposed it is not needed any longer. 967 setParentStorage( uno::Reference< embed::XStorage >() ); 968 } 969 970 //========================================================================= 971 // 972 // io::XTruncate. 973 // 974 //========================================================================= 975 976 // virtual 977 void SAL_CALL Stream::truncate() 978 throw( io::IOException, 979 uno::RuntimeException ) 980 { 981 if ( m_xWrappedTruncate.is() ) 982 { 983 m_xWrappedTruncate->truncate(); 984 commitChanges(); 985 } 986 } 987 988 //========================================================================= 989 // 990 // io::XInputStream. 991 // 992 //========================================================================= 993 994 // virtual 995 sal_Int32 SAL_CALL Stream::readBytes( uno::Sequence< sal_Int8 >& aData, 996 sal_Int32 nBytesToRead ) 997 throw( io::NotConnectedException, 998 io::BufferSizeExceededException, 999 io::IOException, 1000 uno::RuntimeException ) 1001 { 1002 return m_xWrappedInputStream->readBytes( aData, nBytesToRead ); 1003 } 1004 1005 //========================================================================= 1006 // virtual 1007 sal_Int32 SAL_CALL Stream::readSomeBytes( uno::Sequence< sal_Int8 >& aData, 1008 sal_Int32 nMaxBytesToRead ) 1009 throw( io::NotConnectedException, 1010 io::BufferSizeExceededException, 1011 io::IOException, 1012 uno::RuntimeException ) 1013 { 1014 return m_xWrappedInputStream->readSomeBytes( aData, nMaxBytesToRead ); 1015 } 1016 1017 //========================================================================= 1018 // virtual 1019 void SAL_CALL Stream::skipBytes( sal_Int32 nBytesToSkip ) 1020 throw( io::NotConnectedException, 1021 io::BufferSizeExceededException, 1022 io::IOException, 1023 uno::RuntimeException ) 1024 { 1025 m_xWrappedInputStream->skipBytes( nBytesToSkip ); 1026 } 1027 1028 //========================================================================= 1029 // virtual 1030 sal_Int32 SAL_CALL Stream::available() 1031 throw( io::NotConnectedException, 1032 io::IOException, 1033 uno::RuntimeException ) 1034 { 1035 return m_xWrappedInputStream->available(); 1036 } 1037 1038 //========================================================================= 1039 // virtual 1040 void SAL_CALL Stream::closeInput() 1041 throw( io::NotConnectedException, 1042 io::IOException, 1043 uno::RuntimeException ) 1044 { 1045 m_xWrappedInputStream->closeInput(); 1046 } 1047 1048 //========================================================================= 1049 // 1050 // lang::XComponent 1051 // 1052 //========================================================================= 1053 1054 // virtual 1055 void SAL_CALL Stream::dispose() 1056 throw ( uno::RuntimeException ) 1057 { 1058 m_xWrappedComponent->dispose(); 1059 1060 // Release parent storage. 1061 // Now, that the stream is closed/disposed it is not needed any longer. 1062 setParentStorage( uno::Reference< embed::XStorage >() ); 1063 } 1064 1065 //========================================================================= 1066 // virtual 1067 void SAL_CALL Stream::addEventListener( 1068 const uno::Reference< lang::XEventListener >& xListener ) 1069 throw ( uno::RuntimeException ) 1070 { 1071 m_xWrappedComponent->addEventListener( xListener ); 1072 } 1073 1074 //========================================================================= 1075 // virtual 1076 void SAL_CALL Stream::removeEventListener( 1077 const uno::Reference< lang::XEventListener >& aListener ) 1078 throw ( uno::RuntimeException ) 1079 { 1080 m_xWrappedComponent->removeEventListener( aListener ); 1081 } 1082 1083 //========================================================================= 1084 // 1085 // Non-UNO 1086 // 1087 //========================================================================= 1088 1089 void Stream::commitChanges() 1090 throw( io::IOException ) 1091 { 1092 uno::Reference< embed::XTransactedObject > 1093 xParentTA( getParentStorage(), uno::UNO_QUERY ); 1094 OSL_ENSURE( xParentTA.is(), "No XTransactedObject interface!" ); 1095 1096 if ( xParentTA.is() ) 1097 { 1098 try 1099 { 1100 xParentTA->commit(); 1101 } 1102 catch ( lang::WrappedTargetException const & ) 1103 { 1104 throw io::IOException(); // @@@ 1105 } 1106 } 1107 } 1108 1109