LCOV - code coverage report
Current view: top level - libreoffice/dbaccess/source/core/dataaccess - ModelImpl.cxx (source / functions) Hit Total Coverage
Test: libreoffice_filtered.info Lines: 0 525 0.0 %
Date: 2012-12-27 Functions: 0 84 0.0 %
Legend: Lines: hit not hit

          Line data    Source code
       1             : /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
       2             : /*
       3             :  * This file is part of the LibreOffice project.
       4             :  *
       5             :  * This Source Code Form is subject to the terms of the Mozilla Public
       6             :  * License, v. 2.0. If a copy of the MPL was not distributed with this
       7             :  * file, You can obtain one at http://mozilla.org/MPL/2.0/.
       8             :  *
       9             :  * This file incorporates work covered by the following license notice:
      10             :  *
      11             :  *   Licensed to the Apache Software Foundation (ASF) under one or more
      12             :  *   contributor license agreements. See the NOTICE file distributed
      13             :  *   with this work for additional information regarding copyright
      14             :  *   ownership. The ASF licenses this file to you under the Apache
      15             :  *   License, Version 2.0 (the "License"); you may not use this file
      16             :  *   except in compliance with the License. You may obtain a copy of
      17             :  *   the License at http://www.apache.org/licenses/LICENSE-2.0 .
      18             :  */
      19             : 
      20             : 
      21             : #include "commandcontainer.hxx"
      22             : #include "connection.hxx"
      23             : #include "core_resource.hrc"
      24             : #include "core_resource.hxx"
      25             : #include "databasecontext.hxx"
      26             : #include "databasedocument.hxx"
      27             : #include "datasource.hxx"
      28             : #include "dbastrings.hrc"
      29             : #include "ModelImpl.hxx"
      30             : #include "userinformation.hxx"
      31             : #include "sdbcoretools.hxx"
      32             : 
      33             : #include <com/sun/star/container/XSet.hpp>
      34             : #include <com/sun/star/document/MacroExecMode.hpp>
      35             : #include <com/sun/star/frame/GlobalEventBroadcaster.hpp>
      36             : #include <com/sun/star/embed/XTransactedObject.hpp>
      37             : #include <com/sun/star/embed/XTransactionBroadcaster.hpp>
      38             : #include <com/sun/star/embed/StorageFactory.hpp>
      39             : #include <com/sun/star/sdb/BooleanComparisonMode.hpp>
      40             : #include <com/sun/star/script/DocumentScriptLibraryContainer.hpp>
      41             : #include <com/sun/star/script/DocumentDialogLibraryContainer.hpp>
      42             : #include <com/sun/star/lang/WrappedTargetRuntimeException.hpp>
      43             : #include <com/sun/star/form/XLoadable.hpp>
      44             : #include <com/sun/star/util/NumberFormatsSupplier.hpp>
      45             : 
      46             : #include <comphelper/interaction.hxx>
      47             : #include <comphelper/mediadescriptor.hxx>
      48             : #include <comphelper/seqstream.hxx>
      49             : #include <comphelper/sequence.hxx>
      50             : #include <connectivity/dbexception.hxx>
      51             : #include <cppuhelper/exc_hlp.hxx>
      52             : #include <cppuhelper/typeprovider.hxx>
      53             : #include <rtl/digest.h>
      54             : #include <sfx2/signaturestate.hxx>
      55             : #include <tools/debug.hxx>
      56             : #include <tools/diagnose_ex.h>
      57             : #include <osl/diagnose.h>
      58             : #include <tools/errcode.hxx>
      59             : #include <tools/urlobj.hxx>
      60             : #include <unotools/sharedunocomponent.hxx>
      61             : 
      62             : #include <algorithm>
      63             : 
      64             : using namespace ::com::sun::star::document;
      65             : using namespace ::com::sun::star::sdbc;
      66             : using namespace ::com::sun::star::sdbcx;
      67             : using namespace ::com::sun::star::sdb;
      68             : using namespace ::com::sun::star::beans;
      69             : using namespace ::com::sun::star::uno;
      70             : using namespace ::com::sun::star::lang;
      71             : using namespace ::com::sun::star::embed;
      72             : using namespace ::com::sun::star::container;
      73             : using namespace ::com::sun::star::util;
      74             : using namespace ::com::sun::star::io;
      75             : using namespace ::com::sun::star::task;
      76             : using namespace ::com::sun::star::ucb;
      77             : using namespace ::com::sun::star::frame;
      78             : using namespace ::com::sun::star::view;
      79             : using namespace ::com::sun::star::task;
      80             : using namespace ::com::sun::star::reflection;
      81             : using namespace ::com::sun::star::script;
      82             : using namespace ::cppu;
      83             : using namespace ::osl;
      84             : using namespace ::dbtools;
      85             : using namespace ::comphelper;
      86             : 
      87             : namespace dbaccess
      88             : {
      89             : 
      90             : //============================================================
      91             : //= VosMutexFacade
      92             : //============================================================
      93           0 : VosMutexFacade::VosMutexFacade( ::osl::Mutex& _rMutex )
      94           0 :     :m_rMutex( _rMutex )
      95             : {
      96           0 : }
      97             : 
      98           0 : void SAL_CALL VosMutexFacade::acquire()
      99             : {
     100           0 :     m_rMutex.acquire();
     101           0 : }
     102             : 
     103           0 : sal_Bool SAL_CALL VosMutexFacade::tryToAcquire()
     104             : {
     105           0 :     return m_rMutex.tryToAcquire();
     106             : }
     107             : 
     108           0 : void SAL_CALL VosMutexFacade::release()
     109             : {
     110           0 :     m_rMutex.release();
     111           0 : }
     112             : 
     113             : //============================================================
     114             : //= DocumentStorageAccess
     115             : //============================================================
     116             : DBG_NAME( DocumentStorageAccess )
     117             : class DocumentStorageAccess : public ::cppu::WeakImplHelper2<   XDocumentSubStorageSupplier
     118             :                                                             ,   XTransactionListener >
     119             : {
     120             :     typedef ::std::map< ::rtl::OUString, Reference< XStorage > >    NamedStorages;
     121             : 
     122             :     ::osl::Mutex        m_aMutex;
     123             :     /// all sub storages which we ever gave to the outer world
     124             :     NamedStorages       m_aExposedStorages;
     125             :     ODatabaseModelImpl* m_pModelImplementation;
     126             :     bool                m_bPropagateCommitToRoot;
     127             :     bool                m_bDisposingSubStorages;
     128             : 
     129             : public:
     130           0 :     DocumentStorageAccess( ODatabaseModelImpl& _rModelImplementation )
     131             :         :m_pModelImplementation( &_rModelImplementation )
     132             :         ,m_bPropagateCommitToRoot( true )
     133           0 :         ,m_bDisposingSubStorages( false )
     134             :     {
     135             :         DBG_CTOR( DocumentStorageAccess, NULL );
     136           0 :     }
     137             : 
     138             : protected:
     139           0 :     ~DocumentStorageAccess()
     140           0 :     {
     141             :         DBG_DTOR( DocumentStorageAccess, NULL );
     142           0 :     }
     143             : 
     144             : public:
     145             :     void dispose();
     146             : 
     147             :     // XDocumentSubStorageSupplier
     148             :     virtual Reference< XStorage > SAL_CALL getDocumentSubStorage( const ::rtl::OUString& aStorageName, ::sal_Int32 _nMode ) throw (RuntimeException);
     149             :     virtual Sequence< ::rtl::OUString > SAL_CALL getDocumentSubStoragesNames(  ) throw (IOException, RuntimeException);
     150             : 
     151             :     // XTransactionListener
     152             :     virtual void SAL_CALL preCommit( const ::com::sun::star::lang::EventObject& aEvent ) throw (::com::sun::star::uno::Exception, ::com::sun::star::uno::RuntimeException);
     153             :     virtual void SAL_CALL commited( const ::com::sun::star::lang::EventObject& aEvent ) throw (::com::sun::star::uno::RuntimeException);
     154             :     virtual void SAL_CALL preRevert( const ::com::sun::star::lang::EventObject& aEvent ) throw (::com::sun::star::uno::Exception, ::com::sun::star::uno::RuntimeException);
     155             :     virtual void SAL_CALL reverted( const ::com::sun::star::lang::EventObject& aEvent ) throw (::com::sun::star::uno::RuntimeException);
     156             : 
     157             :     // XEventListener
     158             :     virtual void SAL_CALL disposing( const ::com::sun::star::lang::EventObject& Source ) throw (::com::sun::star::uno::RuntimeException);
     159             : 
     160             :     /// disposes all storages managed by this instance
     161             :     void disposeStorages();
     162             : 
     163             :     /// disposes all known sub storages
     164             :     void commitStorages() SAL_THROW(( IOException, RuntimeException ));
     165             : 
     166             :     /// commits the dedicated "database" storage
     167             :     bool commitEmbeddedStorage( bool _bPreventRootCommits );
     168             : 
     169             : private:
     170             :     /** opens the sub storage with the given name, in the given mode
     171             :     */
     172             :     Reference< XStorage > impl_openSubStorage_nothrow( const ::rtl::OUString& _rStorageName, sal_Int32 _nMode );
     173             : 
     174           0 :     void impl_suspendCommitPropagation()
     175             :     {
     176             :         OSL_ENSURE( m_bPropagateCommitToRoot, "DocumentStorageAccess::impl_suspendCommitPropagation: already suspended" );
     177           0 :         m_bPropagateCommitToRoot = false;
     178           0 :     }
     179           0 :     void impl_resumeCommitPropagation()
     180             :     {
     181             :         OSL_ENSURE( !m_bPropagateCommitToRoot, "DocumentStorageAccess::impl_resumeCommitPropagation: not suspended" );
     182           0 :         m_bPropagateCommitToRoot = true;
     183           0 :     }
     184             : 
     185             : };
     186             : 
     187           0 : void DocumentStorageAccess::dispose()
     188             : {
     189           0 :     ::osl::MutexGuard aGuard( m_aMutex );
     190             : 
     191           0 :     for (   NamedStorages::iterator loop = m_aExposedStorages.begin();
     192           0 :             loop != m_aExposedStorages.end();
     193             :             ++loop
     194             :         )
     195             :     {
     196             :         try
     197             :         {
     198           0 :             Reference< XTransactionBroadcaster > xBroadcaster( loop->second, UNO_QUERY );
     199           0 :             if ( xBroadcaster.is() )
     200           0 :                 xBroadcaster->removeTransactionListener( this );
     201             :         }
     202           0 :         catch( const Exception& )
     203             :         {
     204             :             DBG_UNHANDLED_EXCEPTION();
     205             :         }
     206             :     }
     207             : 
     208           0 :     m_aExposedStorages.clear();
     209             : 
     210           0 :     m_pModelImplementation = NULL;
     211           0 : }
     212             : 
     213           0 : Reference< XStorage > DocumentStorageAccess::impl_openSubStorage_nothrow( const ::rtl::OUString& _rStorageName, sal_Int32 _nDesiredMode )
     214             : {
     215             :     OSL_ENSURE( !_rStorageName.isEmpty(),"ODatabaseModelImpl::impl_openSubStorage_nothrow: Invalid storage name!" );
     216             : 
     217           0 :     Reference< XStorage > xStorage;
     218             :     try
     219             :     {
     220           0 :         Reference< XStorage > xRootStorage( m_pModelImplementation->getOrCreateRootStorage() );
     221           0 :         if ( xRootStorage.is() )
     222             :         {
     223           0 :             sal_Int32 nRealMode = m_pModelImplementation->m_bDocumentReadOnly ? ElementModes::READ : _nDesiredMode;
     224           0 :             if ( nRealMode == ElementModes::READ )
     225             :             {
     226           0 :                 Reference< XNameAccess > xSubStorageNames( xRootStorage, UNO_QUERY );
     227           0 :                 if ( xSubStorageNames.is() && !xSubStorageNames->hasByName( _rStorageName ) )
     228           0 :                     return xStorage;
     229             :             }
     230             : 
     231           0 :             xStorage = xRootStorage->openStorageElement( _rStorageName, nRealMode );
     232             : 
     233           0 :             Reference< XTransactionBroadcaster > xBroad( xStorage, UNO_QUERY );
     234           0 :             if ( xBroad.is() )
     235           0 :                 xBroad->addTransactionListener( this );
     236           0 :         }
     237             :     }
     238           0 :     catch( const Exception& )
     239             :     {
     240             :         DBG_UNHANDLED_EXCEPTION();
     241             :     }
     242             : 
     243           0 :     return xStorage;
     244             : }
     245             : 
     246           0 : void DocumentStorageAccess::disposeStorages()
     247             : {
     248           0 :     m_bDisposingSubStorages = true;
     249             : 
     250           0 :     NamedStorages::iterator aEnd = m_aExposedStorages.end();
     251           0 :     for (   NamedStorages::iterator aIter = m_aExposedStorages.begin();
     252             :             aIter != aEnd ;
     253             :             ++aIter
     254             :         )
     255             :     {
     256             :         try
     257             :         {
     258           0 :             ::comphelper::disposeComponent( aIter->second );
     259             :         }
     260           0 :         catch( const Exception& )
     261             :         {
     262             :             DBG_UNHANDLED_EXCEPTION();
     263             :         }
     264             :     }
     265           0 :     m_aExposedStorages.clear();
     266             : 
     267           0 :     m_bDisposingSubStorages = false;
     268           0 : }
     269             : 
     270           0 : void DocumentStorageAccess::commitStorages() SAL_THROW(( IOException, RuntimeException ))
     271             : {
     272             :     try
     273             :     {
     274           0 :         for (   NamedStorages::const_iterator aIter = m_aExposedStorages.begin();
     275           0 :                 aIter != m_aExposedStorages.end();
     276             :                 ++aIter
     277             :             )
     278             :         {
     279           0 :             tools::stor::commitStorageIfWriteable( aIter->second );
     280             :         }
     281             :     }
     282           0 :     catch(const WrappedTargetException&)
     283             :     {
     284             :         // WrappedTargetException not allowed to leave
     285           0 :         throw IOException();
     286             :     }
     287           0 : }
     288             : 
     289           0 : bool DocumentStorageAccess::commitEmbeddedStorage( bool _bPreventRootCommits )
     290             : {
     291           0 :     if ( _bPreventRootCommits )
     292           0 :         impl_suspendCommitPropagation();
     293             : 
     294           0 :     bool bSuccess = false;
     295             :     try
     296             :     {
     297           0 :         NamedStorages::const_iterator pos = m_aExposedStorages.find( ::rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "database" ) ) );
     298           0 :         if ( pos != m_aExposedStorages.end() )
     299           0 :             bSuccess = tools::stor::commitStorageIfWriteable( pos->second );
     300             :     }
     301           0 :     catch( Exception& )
     302             :     {
     303             :         DBG_UNHANDLED_EXCEPTION();
     304             :     }
     305             : 
     306           0 :     if ( _bPreventRootCommits )
     307           0 :         impl_resumeCommitPropagation();
     308             : 
     309           0 :     return bSuccess;
     310             : 
     311             : }
     312             : 
     313           0 : Reference< XStorage > SAL_CALL DocumentStorageAccess::getDocumentSubStorage( const ::rtl::OUString& aStorageName, ::sal_Int32 _nDesiredMode ) throw (RuntimeException)
     314             : {
     315           0 :     ::osl::MutexGuard aGuard( m_aMutex );
     316           0 :     NamedStorages::iterator pos = m_aExposedStorages.find( aStorageName );
     317           0 :     if ( pos == m_aExposedStorages.end() )
     318             :     {
     319           0 :         Reference< XStorage > xResult = impl_openSubStorage_nothrow( aStorageName, _nDesiredMode );
     320           0 :         pos = m_aExposedStorages.insert( NamedStorages::value_type( aStorageName, xResult ) ).first;
     321             :     }
     322             : 
     323           0 :     return pos->second;
     324             : }
     325             : 
     326           0 : Sequence< ::rtl::OUString > SAL_CALL DocumentStorageAccess::getDocumentSubStoragesNames(  ) throw (IOException, RuntimeException)
     327             : {
     328           0 :     Reference< XStorage > xRootStor( m_pModelImplementation->getRootStorage() );
     329           0 :     if ( !xRootStor.is() )
     330           0 :         return Sequence< ::rtl::OUString >();
     331             : 
     332           0 :     ::std::vector< ::rtl::OUString > aNames;
     333             : 
     334           0 :     Reference< XNameAccess > xNames( xRootStor, UNO_QUERY_THROW );
     335           0 :     Sequence< ::rtl::OUString > aElementNames( xNames->getElementNames() );
     336           0 :     for ( sal_Int32 i=0; i<aElementNames.getLength(); ++i )
     337             :     {
     338           0 :         if ( xRootStor->isStorageElement( aElementNames[i] ) )
     339           0 :             aNames.push_back( aElementNames[i] );
     340             :     }
     341           0 :     return aNames.empty()
     342             :         ?  Sequence< ::rtl::OUString >()
     343           0 :         :  Sequence< ::rtl::OUString >( &aNames[0], aNames.size() );
     344             : }
     345             : 
     346           0 : void SAL_CALL DocumentStorageAccess::preCommit( const css::lang::EventObject& /*aEvent*/ ) throw (Exception, RuntimeException)
     347             : {
     348             :     // not interested in
     349           0 : }
     350             : 
     351           0 : void SAL_CALL DocumentStorageAccess::commited( const css::lang::EventObject& aEvent ) throw (RuntimeException)
     352             : {
     353           0 :     ::osl::MutexGuard aGuard( m_aMutex );
     354             : 
     355           0 :     if ( m_pModelImplementation )
     356           0 :         m_pModelImplementation->setModified( sal_True );
     357             : 
     358           0 :     if ( m_pModelImplementation && m_bPropagateCommitToRoot )
     359             :     {
     360           0 :         Reference< XStorage > xStorage( aEvent.Source, UNO_QUERY );
     361             : 
     362             :         // check if this is the dedicated "database" sub storage
     363           0 :         NamedStorages::const_iterator pos = m_aExposedStorages.find( ::rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "database" ) ) );
     364           0 :         if  (   ( pos != m_aExposedStorages.end() )
     365           0 :             &&  ( pos->second == xStorage )
     366             :             )
     367             :         {
     368             :             // if so, also commit the root storage
     369           0 :             m_pModelImplementation->commitRootStorage();
     370           0 :         }
     371           0 :     }
     372           0 : }
     373             : 
     374           0 : void SAL_CALL DocumentStorageAccess::preRevert( const css::lang::EventObject& /*aEvent*/ ) throw (Exception, RuntimeException)
     375             : {
     376             :     // not interested in
     377           0 : }
     378             : 
     379           0 : void SAL_CALL DocumentStorageAccess::reverted( const css::lang::EventObject& /*aEvent*/ ) throw (RuntimeException)
     380             : {
     381             :     // not interested in
     382           0 : }
     383             : 
     384           0 : void SAL_CALL DocumentStorageAccess::disposing( const css::lang::EventObject& Source ) throw ( RuntimeException )
     385             : {
     386             :     OSL_ENSURE( Reference< XStorage >( Source.Source, UNO_QUERY ).is(), "DocumentStorageAccess::disposing: No storage? What's this?" );
     387             : 
     388           0 :     if ( m_bDisposingSubStorages )
     389           0 :         return;
     390             : 
     391           0 :     for (   NamedStorages::iterator find = m_aExposedStorages.begin();
     392           0 :             find != m_aExposedStorages.end();
     393             :             ++find
     394             :         )
     395           0 :         if ( find->second == Source.Source )
     396             :         {
     397           0 :             m_aExposedStorages.erase( find );
     398           0 :             break;
     399             :         }
     400             : }
     401             : 
     402             : //============================================================
     403             : //= ODatabaseModelImpl
     404             : //============================================================
     405             : DBG_NAME(ODatabaseModelImpl)
     406             : 
     407           0 : ODatabaseModelImpl::ODatabaseModelImpl( const Reference< XMultiServiceFactory >& _rxFactory, ODatabaseContext& _rDBContext )
     408             :             :m_xModel()
     409             :             ,m_xDataSource()
     410             :             ,m_pStorageAccess( NULL )
     411             :             ,m_aMutex()
     412             :             ,m_aMutexFacade( m_aMutex )
     413             :             ,m_aContainer(4)
     414             :             ,m_aMacroMode( *this )
     415             :             ,m_nImposedMacroExecMode( MacroExecMode::NEVER_EXECUTE )
     416             :             ,m_pDBContext( &_rDBContext )
     417             :             ,m_refCount(0)
     418             :             ,m_aEmbeddedMacros()
     419             :             ,m_bModificationLock( false )
     420             :             ,m_bDocumentInitialized( false )
     421             :             ,m_aContext( _rxFactory )
     422             :             ,m_nLoginTimeout(0)
     423             :             ,m_bReadOnly(sal_False)
     424             :             ,m_bPasswordRequired(sal_False)
     425             :             ,m_bSuppressVersionColumns(sal_True)
     426             :             ,m_bModified(sal_False)
     427             :             ,m_bDocumentReadOnly(sal_False)
     428             :             ,m_pSharedConnectionManager(NULL)
     429           0 :             ,m_nControllerLockCount(0)
     430             : {
     431             :     // some kind of default
     432             :     DBG_CTOR(ODatabaseModelImpl,NULL);
     433           0 :     m_sConnectURL = ::rtl::OUString(RTL_CONSTASCII_USTRINGPARAM("jdbc:"));
     434           0 :     m_aTableFilter.realloc(1);
     435           0 :     m_aTableFilter[0] = ::rtl::OUString(RTL_CONSTASCII_USTRINGPARAM("%"));
     436           0 :     impl_construct_nothrow();
     437           0 : }
     438             : 
     439           0 : ODatabaseModelImpl::ODatabaseModelImpl(
     440             :                     const ::rtl::OUString& _rRegistrationName,
     441             :                     const Reference< XMultiServiceFactory >& _rxFactory,
     442             :                     ODatabaseContext& _rDBContext
     443             :                     )
     444             :             :m_xModel()
     445             :             ,m_xDataSource()
     446             :             ,m_pStorageAccess( NULL )
     447             :             ,m_aMutex()
     448             :             ,m_aMutexFacade( m_aMutex )
     449             :             ,m_aContainer(4)
     450             :             ,m_aMacroMode( *this )
     451             :             ,m_nImposedMacroExecMode( MacroExecMode::NEVER_EXECUTE )
     452             :             ,m_pDBContext( &_rDBContext )
     453             :             ,m_refCount(0)
     454             :             ,m_aEmbeddedMacros()
     455             :             ,m_bModificationLock( false )
     456             :             ,m_bDocumentInitialized( false )
     457             :             ,m_aContext( _rxFactory )
     458             :             ,m_sName(_rRegistrationName)
     459             :             ,m_nLoginTimeout(0)
     460             :             ,m_bReadOnly(sal_False)
     461             :             ,m_bPasswordRequired(sal_False)
     462             :             ,m_bSuppressVersionColumns(sal_True)
     463             :             ,m_bModified(sal_False)
     464             :             ,m_bDocumentReadOnly(sal_False)
     465             :             ,m_pSharedConnectionManager(NULL)
     466           0 :             ,m_nControllerLockCount(0)
     467             : {
     468             :     DBG_CTOR(ODatabaseModelImpl,NULL);
     469           0 :     impl_construct_nothrow();
     470           0 : }
     471             : 
     472           0 : ODatabaseModelImpl::~ODatabaseModelImpl()
     473             : {
     474             :     DBG_DTOR(ODatabaseModelImpl,NULL);
     475           0 : }
     476             : 
     477           0 : void ODatabaseModelImpl::impl_construct_nothrow()
     478             : {
     479             :     // create the property bag to hold the settings (also known as "Info" property)
     480             :     try
     481             :     {
     482             :         // the set of property value types in the bag is limited:
     483           0 :         Sequence< Type > aAllowedTypes(6);
     484           0 :         Type* pAllowedType = aAllowedTypes.getArray();
     485           0 :         *pAllowedType++ = ::getCppuType( static_cast< sal_Bool* >( NULL ) );
     486           0 :         *pAllowedType++ = ::getCppuType( static_cast< double* >( NULL ) );
     487           0 :         *pAllowedType++ = ::getCppuType( static_cast< ::rtl::OUString* >( NULL ) );
     488           0 :         *pAllowedType++ = ::getCppuType( static_cast< sal_Int32* >( NULL ) );
     489           0 :         *pAllowedType++ = ::getCppuType( static_cast< sal_Int16* >( NULL ) );
     490           0 :         *pAllowedType++ = ::getCppuType( static_cast< Sequence< Any >* >( NULL ) );
     491             : 
     492           0 :         Sequence< Any > aInitArgs( 2 );
     493           0 :         aInitArgs[0] <<= NamedValue(
     494             :             ::rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "AutomaticAddition" ) ),
     495             :             makeAny( (sal_Bool)sal_True )
     496           0 :         );
     497           0 :         aInitArgs[1] <<= NamedValue(
     498             :             ::rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "AllowedTypes" ) ),
     499             :             makeAny( aAllowedTypes )
     500           0 :         );
     501             : 
     502           0 :         m_xSettings.set( m_aContext.createComponentWithArguments( "com.sun.star.beans.PropertyBag", aInitArgs ), UNO_QUERY_THROW );
     503             : 
     504             :         // insert the default settings
     505           0 :         Reference< XPropertyContainer > xContainer( m_xSettings, UNO_QUERY_THROW );
     506           0 :         Reference< XSet > xSettingsSet( m_xSettings, UNO_QUERY_THROW );
     507           0 :         const AsciiPropertyValue* pSettings = getDefaultDataSourceSettings();
     508           0 :         for ( ; pSettings->AsciiName; ++pSettings )
     509             :         {
     510           0 :             if ( !pSettings->DefaultValue.hasValue() )
     511             :             {
     512             :                 Property aProperty(
     513             :                     ::rtl::OUString::createFromAscii( pSettings->AsciiName ),
     514             :                     -1,
     515             :                     pSettings->ValueType,
     516             :                     PropertyAttribute::BOUND | PropertyAttribute::MAYBEDEFAULT | PropertyAttribute::MAYBEVOID
     517           0 :                 );
     518           0 :                 xSettingsSet->insert( makeAny( aProperty ) );
     519             :             }
     520             :             else
     521             :             {
     522           0 :                 xContainer->addProperty(
     523             :                     ::rtl::OUString::createFromAscii( pSettings->AsciiName ),
     524             :                     PropertyAttribute::BOUND | PropertyAttribute::MAYBEDEFAULT,
     525             :                     pSettings->DefaultValue
     526           0 :                 );
     527             :             }
     528           0 :         }
     529             :     }
     530           0 :     catch( const Exception& )
     531             :     {
     532             :         DBG_UNHANDLED_EXCEPTION();
     533             :     }
     534           0 :     m_pDBContext->appendAtTerminateListener(*this);
     535           0 : }
     536             : 
     537             : namespace
     538             : {
     539           0 :     ::rtl::OUString lcl_getContainerStorageName_throw( ODatabaseModelImpl::ObjectType _eType )
     540             :     {
     541           0 :         const sal_Char* pAsciiName( NULL );
     542           0 :         switch ( _eType )
     543             :         {
     544           0 :         case ODatabaseModelImpl::E_FORM:   pAsciiName = "forms"; break;
     545           0 :         case ODatabaseModelImpl::E_REPORT: pAsciiName = "reports"; break;
     546           0 :         case ODatabaseModelImpl::E_QUERY:  pAsciiName = "queries"; break;
     547           0 :         case ODatabaseModelImpl::E_TABLE:  pAsciiName = "tables"; break;
     548             :         default:
     549           0 :             throw RuntimeException();
     550             :         }
     551           0 :         return ::rtl::OUString::createFromAscii( pAsciiName );
     552             :     }
     553             : 
     554           0 :     bool lcl_hasObjectWithMacros_throw( const ODefinitionContainer_Impl& _rObjectDefinitions, const Reference< XStorage >& _rxContainerStorage )
     555             :     {
     556           0 :         bool bSomeDocHasMacros = false;
     557             : 
     558           0 :         for (   ODefinitionContainer_Impl::const_iterator object = _rObjectDefinitions.begin();
     559           0 :                 ( object != _rObjectDefinitions.end() ) && !bSomeDocHasMacros;
     560             :                 ++object
     561             :             )
     562             :         {
     563             : #if OSL_DEBUG_LEVEL > 0
     564             :             const ::rtl::OUString& rName( object->first ); (void)rName;
     565             : #endif
     566             : 
     567           0 :             const TContentPtr& rDefinition( object->second );
     568           0 :             const ::rtl::OUString& rPersistentName( rDefinition->m_aProps.sPersistentName );
     569             : 
     570           0 :             if ( rPersistentName.isEmpty() )
     571             :             {   // it's a logical sub folder used to organize the real objects
     572           0 :                 const ODefinitionContainer_Impl& rSubFoldersObjectDefinitions( dynamic_cast< const ODefinitionContainer_Impl& >( *rDefinition.get() ) );
     573           0 :                 bSomeDocHasMacros = lcl_hasObjectWithMacros_throw( rSubFoldersObjectDefinitions, _rxContainerStorage );
     574           0 :                 continue;
     575             :             }
     576             : 
     577           0 :             bSomeDocHasMacros = ODatabaseModelImpl::objectHasMacros( _rxContainerStorage, rPersistentName );
     578             :         }
     579           0 :         return bSomeDocHasMacros;
     580             :     }
     581             : 
     582           0 :     bool lcl_hasObjectsWithMacros_nothrow( ODatabaseModelImpl& _rModel, const ODatabaseModelImpl::ObjectType _eType )
     583             :     {
     584           0 :         bool bSomeDocHasMacros = false;
     585             : 
     586           0 :         const OContentHelper_Impl& rContainerData( *_rModel.getObjectContainer( _eType ).get() );
     587           0 :         const ODefinitionContainer_Impl& rObjectDefinitions = dynamic_cast< const ODefinitionContainer_Impl& >( rContainerData );
     588             : 
     589             :         try
     590             :         {
     591           0 :             Reference< XStorage > xContainerStorage( _rModel.getStorage( _eType, ElementModes::READWRITE ) );
     592             :             // note the READWRITE here: If the storage already existed before, then the OpenMode will
     593             :             // be ignored, anyway.
     594             :             // If the storage did not yet exist, then it will be created. If the database document
     595             :             // is read-only, the OpenMode will be automatically downgraded to READ. Otherwise,
     596             :             // the storage will in fact be created as READWRITE. While this is not strictly necessary
     597             :             // for this particular use case here, it is required since the storage is *cached*, and
     598             :             // later use cases will need the READWRITE mode.
     599             : 
     600           0 :             if ( xContainerStorage.is() )
     601           0 :                 bSomeDocHasMacros = lcl_hasObjectWithMacros_throw( rObjectDefinitions, xContainerStorage );
     602             :         }
     603           0 :         catch( const Exception& )
     604             :         {
     605             :             DBG_UNHANDLED_EXCEPTION();
     606             :             // be on the safe side: If we can't reliably determine whether there are macros,
     607             :             // assume there actually are. Better this way, than the other way round.
     608           0 :             bSomeDocHasMacros = true;
     609             :         }
     610             : 
     611           0 :         return bSomeDocHasMacros;
     612             :     }
     613             : }
     614             : 
     615           0 : bool ODatabaseModelImpl::objectHasMacros( const Reference< XStorage >& _rxContainerStorage, const ::rtl::OUString& _rPersistentName )
     616             : {
     617             :     OSL_PRECOND( _rxContainerStorage.is(), "ODatabaseModelImpl::objectHasMacros: this will crash!" );
     618             : 
     619           0 :     bool bHasMacros = true;
     620             :     try
     621             :     {
     622           0 :         if ( !_rxContainerStorage->hasByName( _rPersistentName ) )
     623           0 :             return false;
     624             : 
     625           0 :         Reference< XStorage > xObjectStor( _rxContainerStorage->openStorageElement(
     626           0 :             _rPersistentName, ElementModes::READ ) );
     627             : 
     628           0 :         bHasMacros = ::sfx2::DocumentMacroMode::storageHasMacros( xObjectStor );
     629             :     }
     630           0 :     catch( const Exception& )
     631             :     {
     632             :         DBG_UNHANDLED_EXCEPTION();
     633             :     }
     634           0 :     return bHasMacros;
     635             : }
     636             : 
     637           0 : void ODatabaseModelImpl::reset()
     638             : {
     639           0 :     m_bReadOnly = sal_False;
     640           0 :     ::std::vector< TContentPtr > aEmptyContainers( 4 );
     641           0 :     m_aContainer.swap( aEmptyContainers );
     642             : 
     643           0 :     if ( m_pStorageAccess )
     644             :     {
     645           0 :         m_pStorageAccess->dispose();
     646           0 :         m_pStorageAccess->release();
     647           0 :         m_pStorageAccess = NULL;
     648           0 :     }
     649           0 : }
     650             : 
     651           0 : void SAL_CALL ODatabaseModelImpl::disposing( const ::com::sun::star::lang::EventObject& Source ) throw(RuntimeException)
     652             : {
     653           0 :     Reference<XConnection> xCon(Source.Source,UNO_QUERY);
     654           0 :     if ( xCon.is() )
     655             :     {
     656           0 :         bool bStore = false;
     657           0 :         OWeakConnectionArray::iterator aEnd = m_aConnections.end();
     658           0 :         for (OWeakConnectionArray::iterator i = m_aConnections.begin(); aEnd != i; ++i)
     659             :         {
     660           0 :             if ( xCon == i->get() )
     661             :             {
     662           0 :                 *i = OWeakConnection();
     663           0 :                 bStore = true;
     664           0 :                 break;
     665             :             }
     666             :         }
     667             : 
     668           0 :         if ( bStore )
     669           0 :             commitRootStorage();
     670             :     }
     671             :     else
     672             :     {
     673             :         OSL_FAIL( "ODatabaseModelImpl::disposing: where does this come from?" );
     674           0 :     }
     675           0 : }
     676             : 
     677           0 : void ODatabaseModelImpl::clearConnections()
     678             : {
     679           0 :     OWeakConnectionArray aConnections;
     680           0 :     aConnections.swap( m_aConnections );
     681             : 
     682           0 :     Reference< XConnection > xConn;
     683           0 :     OWeakConnectionArray::iterator aEnd = aConnections.end();
     684           0 :     for ( OWeakConnectionArray::iterator i = aConnections.begin(); aEnd != i; ++i )
     685             :     {
     686           0 :         xConn = *i;
     687           0 :         if ( xConn.is() )
     688             :         {
     689             :             try
     690             :             {
     691           0 :                 xConn->close();
     692             :             }
     693           0 :             catch(const Exception&)
     694             :             {
     695             :                 DBG_UNHANDLED_EXCEPTION();
     696             :             }
     697             :         }
     698             :     }
     699             : 
     700           0 :     m_pSharedConnectionManager = NULL;
     701           0 :     m_xSharedConnectionManager = NULL;
     702           0 : }
     703             : 
     704           0 : void ODatabaseModelImpl::dispose()
     705             : {
     706             :     // dispose the data source and the model
     707             :     try
     708             :     {
     709           0 :         Reference< XDataSource > xDS( m_xDataSource );
     710           0 :         ::comphelper::disposeComponent( xDS );
     711             : 
     712           0 :         Reference< XModel > xModel( m_xModel );
     713           0 :         ::comphelper::disposeComponent( xModel );
     714             :     }
     715           0 :     catch( const Exception& )
     716             :     {
     717             :         DBG_UNHANDLED_EXCEPTION();
     718             :     }
     719           0 :     m_xDataSource = WeakReference<XDataSource>();
     720           0 :     m_xModel = WeakReference< XModel >();
     721             : 
     722           0 :     ::std::vector<TContentPtr>::iterator aIter = m_aContainer.begin();
     723           0 :     ::std::vector<TContentPtr>::iterator aEnd = m_aContainer.end();
     724           0 :     for (;aIter != aEnd ; ++aIter)
     725             :     {
     726           0 :         if ( aIter->get() )
     727           0 :             (*aIter)->m_pDataSource = NULL;
     728             :     }
     729           0 :     m_aContainer.clear();
     730             : 
     731           0 :     clearConnections();
     732             : 
     733           0 :     m_xNumberFormatsSupplier = NULL;
     734             : 
     735             :     try
     736             :     {
     737           0 :         sal_Bool bCouldStore = commitEmbeddedStorage( true );
     738             :             // "true" means that committing the embedded storage should not trigger committing the root
     739             :             // storage. This is because we are going to commit the root storage ourself, anyway
     740           0 :         disposeStorages();
     741           0 :         if ( bCouldStore )
     742           0 :             commitRootStorage();
     743             : 
     744           0 :         impl_switchToStorage_throw( NULL );
     745             :     }
     746           0 :     catch( const Exception& )
     747             :     {
     748             :         DBG_UNHANDLED_EXCEPTION();
     749             :     }
     750             : 
     751           0 :     if ( m_pStorageAccess )
     752             :     {
     753           0 :         m_pStorageAccess->dispose();
     754           0 :         m_pStorageAccess->release();
     755           0 :         m_pStorageAccess = NULL;
     756             :     }
     757           0 : }
     758             : 
     759           0 : const Reference< XNumberFormatsSupplier > & ODatabaseModelImpl::getNumberFormatsSupplier()
     760             : {
     761           0 :     if (!m_xNumberFormatsSupplier.is())
     762             :     {
     763             :         // the arguments : the locale of the current user
     764           0 :         UserInformation aUserInfo;
     765           0 :         Locale aLocale = aUserInfo.getUserLanguage();
     766             : 
     767           0 :         m_xNumberFormatsSupplier.set( NumberFormatsSupplier::createWithLocale( m_aContext.getUNOContext(), aLocale ) );
     768             :     }
     769           0 :     return m_xNumberFormatsSupplier;
     770             : }
     771             : 
     772           0 : void ODatabaseModelImpl::setDocFileLocation( const ::rtl::OUString& i_rLoadedFrom )
     773             : {
     774           0 :     ENSURE_OR_THROW( !i_rLoadedFrom.isEmpty(), "invalid URL" );
     775           0 :     m_sDocFileLocation = i_rLoadedFrom;
     776           0 : }
     777             : 
     778           0 : void ODatabaseModelImpl::setResource( const ::rtl::OUString& i_rDocumentURL, const Sequence< PropertyValue >& _rArgs )
     779             : {
     780           0 :     ENSURE_OR_THROW( !i_rDocumentURL.isEmpty(), "invalid URL" );
     781             : 
     782           0 :     ::comphelper::NamedValueCollection aMediaDescriptor( _rArgs );
     783             : #if OSL_DEBUG_LEVEL > 0
     784             :     if ( aMediaDescriptor.has( "SalvagedFile" ) )
     785             :     {
     786             :         ::rtl::OUString sSalvagedFile( aMediaDescriptor.getOrDefault( "SalvagedFile", ::rtl::OUString() ) );
     787             :         // If SalvagedFile is an empty string, this indicates "the document is being recovered, but i_rDocumentURL already
     788             :         // is the real document URL, not the temporary document location"
     789             :         if ( sSalvagedFile.isEmpty() )
     790             :             sSalvagedFile = i_rDocumentURL;
     791             : 
     792             :         OSL_ENSURE( sSalvagedFile == i_rDocumentURL, "ODatabaseModelImpl::setResource: inconsistency!" );
     793             :             // nowadays, setResource should only be called with the logical URL of the document
     794             :     }
     795             : #endif
     796             : 
     797           0 :     m_aMediaDescriptor = stripLoadArguments( aMediaDescriptor );
     798             : 
     799           0 :     impl_switchToLogicalURL( i_rDocumentURL );
     800           0 : }
     801             : 
     802           0 : ::comphelper::NamedValueCollection ODatabaseModelImpl::stripLoadArguments( const ::comphelper::NamedValueCollection& _rArguments )
     803             : {
     804             :     OSL_ENSURE( !_rArguments.has( "Model" ), "ODatabaseModelImpl::stripLoadArguments: this is suspicious (1)!" );
     805             :     OSL_ENSURE( !_rArguments.has( "ViewName" ), "ODatabaseModelImpl::stripLoadArguments: this is suspicious (2)!" );
     806             : 
     807           0 :     ::comphelper::NamedValueCollection aMutableArgs( _rArguments );
     808           0 :     aMutableArgs.remove( "Model" );
     809           0 :     aMutableArgs.remove( "ViewName" );
     810           0 :     return aMutableArgs;
     811             : }
     812             : 
     813           0 : void ODatabaseModelImpl::disposeStorages() SAL_THROW(())
     814             : {
     815           0 :     getDocumentStorageAccess()->disposeStorages();
     816           0 : }
     817             : 
     818           0 : Reference< XSingleServiceFactory > ODatabaseModelImpl::createStorageFactory() const
     819             : {
     820           0 :     return StorageFactory::create( m_aContext.getUNOContext() );
     821             : }
     822             : 
     823           0 : void ODatabaseModelImpl::commitRootStorage()
     824             : {
     825           0 :     Reference< XStorage > xStorage( getOrCreateRootStorage() );
     826             : #if OSL_DEBUG_LEVEL > 0
     827             :     bool bSuccess =
     828             : #endif
     829           0 :     commitStorageIfWriteable_ignoreErrors( xStorage );
     830             :     OSL_ENSURE( bSuccess || !xStorage.is(),
     831           0 :         "ODatabaseModelImpl::commitRootStorage: could commit the storage!" );
     832           0 : }
     833             : 
     834           0 : Reference< XStorage > ODatabaseModelImpl::getOrCreateRootStorage()
     835             : {
     836           0 :     if ( !m_xDocumentStorage.is() )
     837             :     {
     838           0 :         Reference< XSingleServiceFactory> xStorageFactory = StorageFactory::create( m_aContext.getUNOContext() );
     839           0 :         Any aSource;
     840           0 :         aSource = m_aMediaDescriptor.get( "Stream" );
     841           0 :         if ( !aSource.hasValue() )
     842           0 :             aSource = m_aMediaDescriptor.get( "InputStream" );
     843           0 :         if ( !aSource.hasValue() && !m_sDocFileLocation.isEmpty() )
     844           0 :             aSource <<= m_sDocFileLocation;
     845             :         // TODO: shouldn't we also check URL?
     846             : 
     847             :         OSL_ENSURE( aSource.hasValue(), "ODatabaseModelImpl::getOrCreateRootStorage: no source to create the storage from!" );
     848             : 
     849           0 :         if ( aSource.hasValue() )
     850             :         {
     851           0 :             Sequence< Any > aStorageCreationArgs(2);
     852           0 :             aStorageCreationArgs[0] = aSource;
     853           0 :             aStorageCreationArgs[1] <<= ElementModes::READWRITE;
     854             : 
     855           0 :             Reference< XStorage > xDocumentStorage;
     856             :             try
     857             :             {
     858           0 :                 xDocumentStorage.set( xStorageFactory->createInstanceWithArguments( aStorageCreationArgs ), UNO_QUERY_THROW );
     859             :             }
     860           0 :             catch( const Exception& )
     861             :             {
     862           0 :                 m_bDocumentReadOnly = sal_True;
     863           0 :                 aStorageCreationArgs[1] <<= ElementModes::READ;
     864             :                 try
     865             :                 {
     866           0 :                     xDocumentStorage.set( xStorageFactory->createInstanceWithArguments( aStorageCreationArgs ), UNO_QUERY_THROW );
     867             :                 }
     868           0 :                 catch( const Exception& )
     869             :                 {
     870             :                     DBG_UNHANDLED_EXCEPTION();
     871             :                 }
     872             :             }
     873             : 
     874           0 :             impl_switchToStorage_throw( xDocumentStorage );
     875           0 :         }
     876             :     }
     877           0 :     return m_xDocumentStorage.getTyped();
     878             : }
     879             : 
     880           0 : DocumentStorageAccess* ODatabaseModelImpl::getDocumentStorageAccess()
     881             : {
     882           0 :     if ( !m_pStorageAccess )
     883             :     {
     884           0 :         m_pStorageAccess = new DocumentStorageAccess( *this );
     885           0 :         m_pStorageAccess->acquire();
     886             :     }
     887           0 :     return m_pStorageAccess;
     888             : }
     889             : 
     890           0 : void ODatabaseModelImpl::modelIsDisposing( const bool _wasInitialized, ResetModelAccess )
     891             : {
     892           0 :     m_xModel = Reference< XModel >();
     893             : 
     894             :     // Basic libraries and Dialog libraries are a model facet, though held at this impl class.
     895             :     // They automatically dispose themself when the model they belong to is being disposed.
     896             :     // So, to not be tempted to do anything with them, again, we reset them.
     897           0 :     m_xBasicLibraries.clear();
     898           0 :     m_xDialogLibraries.clear();
     899             : 
     900           0 :     m_bDocumentInitialized = _wasInitialized;
     901           0 : }
     902             : 
     903           0 : Reference< XDocumentSubStorageSupplier > ODatabaseModelImpl::getDocumentSubStorageSupplier()
     904             : {
     905           0 :     return getDocumentStorageAccess();
     906             : }
     907             : 
     908           0 : bool ODatabaseModelImpl::commitEmbeddedStorage( bool _bPreventRootCommits )
     909             : {
     910           0 :     return getDocumentStorageAccess()->commitEmbeddedStorage( _bPreventRootCommits );
     911             : }
     912             : 
     913           0 : bool ODatabaseModelImpl::commitStorageIfWriteable_ignoreErrors( const Reference< XStorage >& _rxStorage ) SAL_THROW(())
     914             : {
     915           0 :     bool bSuccess = false;
     916             :     try
     917             :     {
     918           0 :         bSuccess = tools::stor::commitStorageIfWriteable( _rxStorage );
     919             :     }
     920           0 :     catch( const Exception& )
     921             :     {
     922             :         DBG_UNHANDLED_EXCEPTION();
     923             :     }
     924           0 :     return bSuccess;
     925             : }
     926             : 
     927           0 : void ODatabaseModelImpl::setModified( sal_Bool _bModified )
     928             : {
     929           0 :     if ( isModifyLocked() )
     930           0 :         return;
     931             : 
     932             :     try
     933             :     {
     934           0 :         Reference< XModifiable > xModi( m_xModel.get(), UNO_QUERY );
     935           0 :         if ( xModi.is() )
     936           0 :             xModi->setModified( _bModified );
     937             :         else
     938           0 :             m_bModified = _bModified;
     939             :     }
     940           0 :     catch( const Exception& )
     941             :     {
     942             :         DBG_UNHANDLED_EXCEPTION();
     943             :     }
     944             : }
     945             : 
     946           0 : Reference<XDataSource> ODatabaseModelImpl::getOrCreateDataSource()
     947             : {
     948           0 :     Reference<XDataSource> xDs = m_xDataSource;
     949           0 :     if ( !xDs.is() )
     950             :     {
     951           0 :         xDs = new ODatabaseSource(this);
     952           0 :         m_xDataSource = xDs;
     953             :     }
     954           0 :     return xDs;
     955             : }
     956             : 
     957           0 : Reference< XModel> ODatabaseModelImpl::getModel_noCreate() const
     958             : {
     959           0 :     return m_xModel;
     960             : }
     961             : 
     962           0 : Reference< XModel > ODatabaseModelImpl::createNewModel_deliverOwnership( bool _bInitialize )
     963             : {
     964           0 :     Reference< XModel > xModel( m_xModel );
     965             :     OSL_PRECOND( !xModel.is(), "ODatabaseModelImpl::createNewModel_deliverOwnership: not to be called if there already is a model!" );
     966           0 :     if ( !xModel.is() )
     967             :     {
     968           0 :         bool bHadModelBefore = m_bDocumentInitialized;
     969             : 
     970           0 :         xModel = ODatabaseDocument::createDatabaseDocument( this, ODatabaseDocument::FactoryAccess() );
     971           0 :         m_xModel = xModel;
     972             : 
     973             :         try
     974             :         {
     975           0 :             Reference< XGlobalEventBroadcaster > xModelCollection = GlobalEventBroadcaster::create( m_aContext.getUNOContext() );
     976           0 :             xModelCollection->insert( makeAny( xModel ) );
     977             :         }
     978           0 :         catch( const Exception& )
     979             :         {
     980             :             DBG_UNHANDLED_EXCEPTION();
     981             :         }
     982             : 
     983           0 :         if ( bHadModelBefore )
     984             :         {
     985             :             // do an attachResources
     986             :             // In case the document is loaded regularly, this is not necessary, as our loader will do it.
     987             :             // However, in case that the document is implicitly created by asking the data source for the document,
     988             :             // then nobody would call the doc's attachResource. So, we do it here, to ensure it's in a proper
     989             :             // state, fires all events, and so on.
     990             :             // #i105505#
     991           0 :             xModel->attachResource( xModel->getURL(), m_aMediaDescriptor.getPropertyValues() );
     992             :         }
     993             : 
     994           0 :         if ( _bInitialize )
     995             :         {
     996             :             try
     997             :             {
     998           0 :                 Reference< XLoadable > xLoad( xModel, UNO_QUERY_THROW );
     999           0 :                 xLoad->initNew();
    1000             :             }
    1001           0 :             catch( RuntimeException& ) { throw; }
    1002           0 :             catch( const Exception& )
    1003             :             {
    1004             :                 DBG_UNHANDLED_EXCEPTION();
    1005             :             }
    1006             :         }
    1007             :     }
    1008           0 :     return xModel;
    1009             : }
    1010             : 
    1011           0 : oslInterlockedCount SAL_CALL ODatabaseModelImpl::acquire()
    1012             : {
    1013           0 :     return osl_atomic_increment(&m_refCount);
    1014             : }
    1015             : 
    1016           0 : oslInterlockedCount SAL_CALL ODatabaseModelImpl::release()
    1017             : {
    1018           0 :     if ( osl_atomic_decrement(&m_refCount) == 0 )
    1019             :     {
    1020           0 :         acquire();  // prevent multiple releases
    1021           0 :         m_pDBContext->removeFromTerminateListener(*this);
    1022           0 :         dispose();
    1023           0 :         m_pDBContext->storeTransientProperties(*this);
    1024           0 :         revokeDataSource();
    1025           0 :         delete this;
    1026           0 :         return 0;
    1027             :     }
    1028           0 :     return m_refCount;
    1029             : }
    1030             : 
    1031           0 : void ODatabaseModelImpl::commitStorages() SAL_THROW(( IOException, RuntimeException ))
    1032             : {
    1033           0 :     getDocumentStorageAccess()->commitStorages();
    1034           0 : }
    1035             : 
    1036           0 : Reference< XStorage > ODatabaseModelImpl::getStorage( const ObjectType _eType, const sal_Int32 _nDesiredMode )
    1037             : {
    1038           0 :     return getDocumentStorageAccess()->getDocumentSubStorage( getObjectContainerStorageName( _eType ), _nDesiredMode );
    1039             : }
    1040             : 
    1041           0 : const AsciiPropertyValue* ODatabaseModelImpl::getDefaultDataSourceSettings()
    1042             : {
    1043             :     static const AsciiPropertyValue aKnownSettings[] =
    1044             :     {
    1045             :         // known JDBC settings
    1046             :         AsciiPropertyValue( "JavaDriverClass",            makeAny( ::rtl::OUString() ) ),
    1047             :         AsciiPropertyValue( "JavaDriverClassPath",       makeAny( ::rtl::OUString() ) ),
    1048             :         AsciiPropertyValue( "IgnoreCurrency",             makeAny( (sal_Bool)sal_False ) ),
    1049             :         // known settings for file-based drivers
    1050             :         AsciiPropertyValue( "Extension",                  makeAny( ::rtl::OUString() ) ),
    1051             :         AsciiPropertyValue( "CharSet",                    makeAny( ::rtl::OUString() ) ),
    1052             :         AsciiPropertyValue( "HeaderLine",                 makeAny( (sal_Bool)sal_True ) ),
    1053             :         AsciiPropertyValue( "FieldDelimiter",             makeAny( ::rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "," ) ) ) ),
    1054             :         AsciiPropertyValue( "StringDelimiter",            makeAny( ::rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "\"" ) ) ) ),
    1055             :         AsciiPropertyValue( "DecimalDelimiter",           makeAny( ::rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "." ) ) ) ),
    1056             :         AsciiPropertyValue( "ThousandDelimiter",          makeAny( ::rtl::OUString() ) ),
    1057             :         AsciiPropertyValue( "ShowDeleted",                makeAny( (sal_Bool)sal_False ) ),
    1058             :         // known ODBC settings
    1059             :         AsciiPropertyValue( "SystemDriverSettings",       makeAny( ::rtl::OUString() ) ),
    1060             :         AsciiPropertyValue( "UseCatalog",                 makeAny( (sal_Bool)sal_False ) ),
    1061             :         AsciiPropertyValue( "TypeInfoSettings",           makeAny( Sequence< Any >()) ),
    1062             :         // settings related to auto increment handling
    1063             :         AsciiPropertyValue( "AutoIncrementCreation",      makeAny( ::rtl::OUString() ) ),
    1064             :         AsciiPropertyValue( "AutoRetrievingStatement",    makeAny( ::rtl::OUString() ) ),
    1065             :         AsciiPropertyValue( "IsAutoRetrievingEnabled",    makeAny( (sal_Bool)sal_False ) ),
    1066             :         // known LDAP driver settings
    1067             :         AsciiPropertyValue( "HostName",                   makeAny( ::rtl::OUString() ) ),
    1068             :         AsciiPropertyValue( "PortNumber",                 makeAny( (sal_Int32)389 ) ),
    1069             :         AsciiPropertyValue( "BaseDN",                     makeAny( ::rtl::OUString() ) ),
    1070             :         AsciiPropertyValue( "MaxRowCount",                makeAny( (sal_Int32)100 ) ),
    1071             :         // known MySQLNative driver settings
    1072             :         AsciiPropertyValue( "LocalSocket",                makeAny( ::rtl::OUString() ) ),
    1073             :         AsciiPropertyValue( "NamedPipe",                  makeAny( ::rtl::OUString() ) ),
    1074             :         // misc known driver settings
    1075             :         AsciiPropertyValue( "ParameterNameSubstitution",  makeAny( (sal_Bool)sal_False ) ),
    1076             :         AsciiPropertyValue( "AddIndexAppendix",           makeAny( (sal_Bool)sal_True ) ),
    1077             :         AsciiPropertyValue( "IgnoreDriverPrivileges",     makeAny( (sal_Bool)sal_True ) ),
    1078           0 :         AsciiPropertyValue( "ImplicitCatalogRestriction", ::cppu::UnoType< ::rtl::OUString >::get() ),
    1079           0 :         AsciiPropertyValue( "ImplicitSchemaRestriction",  ::cppu::UnoType< ::rtl::OUString >::get() ),
    1080           0 :         AsciiPropertyValue( "PrimaryKeySupport",          ::cppu::UnoType< sal_Bool >::get() ),
    1081             :         AsciiPropertyValue( "ShowColumnDescription",      makeAny( (sal_Bool)sal_False ) ),
    1082             :         // known SDB level settings
    1083             :         AsciiPropertyValue( "NoNameLengthLimit",          makeAny( (sal_Bool)sal_False ) ),
    1084             :         AsciiPropertyValue( "AppendTableAliasName",       makeAny( (sal_Bool)sal_False ) ),
    1085             :         AsciiPropertyValue( "GenerateASBeforeCorrelationName",  makeAny( (sal_Bool)sal_True ) ),
    1086             :         AsciiPropertyValue( "ColumnAliasInOrderBy",       makeAny( (sal_Bool)sal_True ) ),
    1087             :         AsciiPropertyValue( "EnableSQL92Check",           makeAny( (sal_Bool)sal_False ) ),
    1088             :         AsciiPropertyValue( "BooleanComparisonMode",      makeAny( BooleanComparisonMode::EQUAL_INTEGER ) ),
    1089             :         AsciiPropertyValue( "TableTypeFilterMode",        makeAny( (sal_Int32)3 ) ),
    1090             :         AsciiPropertyValue( "RespectDriverResultSetType", makeAny( (sal_Bool)sal_False ) ),
    1091             :         AsciiPropertyValue( "UseSchemaInSelect",          makeAny( (sal_Bool)sal_True ) ),
    1092             :         AsciiPropertyValue( "UseCatalogInSelect",         makeAny( (sal_Bool)sal_True ) ),
    1093             :         AsciiPropertyValue( "EnableOuterJoinEscape",      makeAny( (sal_Bool)sal_True ) ),
    1094             :         AsciiPropertyValue( "PreferDosLikeLineEnds",      makeAny( (sal_Bool)sal_False ) ),
    1095             :         AsciiPropertyValue( "FormsCheckRequiredFields",   makeAny( (sal_Bool)sal_True ) ),
    1096             :         AsciiPropertyValue( "EscapeDateTime",             makeAny( (sal_Bool)sal_True ) ),
    1097             : 
    1098             :         // known services to handle database tasks
    1099             :         AsciiPropertyValue( "TableAlterationServiceName", makeAny( ::rtl::OUString() ) ),
    1100             :         AsciiPropertyValue( "TableRenameServiceName",     makeAny( ::rtl::OUString() ) ),
    1101             :         AsciiPropertyValue( "ViewAlterationServiceName",  makeAny( ::rtl::OUString() ) ),
    1102             :         AsciiPropertyValue( "ViewAccessServiceName",      makeAny( ::rtl::OUString() ) ),
    1103             :         AsciiPropertyValue( "CommandDefinitions",         makeAny( ::rtl::OUString() ) ),
    1104             :         AsciiPropertyValue( "Forms",                      makeAny( ::rtl::OUString() ) ),
    1105             :         AsciiPropertyValue( "Reports",                    makeAny( ::rtl::OUString() ) ),
    1106             :         AsciiPropertyValue( "KeyAlterationServiceName",   makeAny( ::rtl::OUString() ) ),
    1107             :         AsciiPropertyValue( "IndexAlterationServiceName", makeAny( ::rtl::OUString() ) ),
    1108             : 
    1109             :         AsciiPropertyValue()
    1110           0 :     };
    1111           0 :     return aKnownSettings;
    1112             : }
    1113             : 
    1114           0 : TContentPtr& ODatabaseModelImpl::getObjectContainer( ObjectType _eType )
    1115             : {
    1116             :     OSL_PRECOND( _eType >= E_FORM && _eType <= E_TABLE, "ODatabaseModelImpl::getObjectContainer: illegal index!" );
    1117           0 :     TContentPtr& rContentPtr = m_aContainer[ _eType ];
    1118             : 
    1119           0 :     if ( !rContentPtr.get() )
    1120             :     {
    1121           0 :         rContentPtr = TContentPtr( new ODefinitionContainer_Impl );
    1122           0 :         rContentPtr->m_pDataSource = this;
    1123           0 :         rContentPtr->m_aProps.aTitle = lcl_getContainerStorageName_throw( _eType );
    1124             :     }
    1125           0 :     return rContentPtr;
    1126             : }
    1127             : 
    1128           0 : void ODatabaseModelImpl::revokeDataSource() const
    1129             : {
    1130           0 :     if ( m_pDBContext && !m_sDocumentURL.isEmpty() )
    1131           0 :         m_pDBContext->revokeDatabaseDocument( *this );
    1132           0 : }
    1133             : 
    1134           0 : bool ODatabaseModelImpl::adjustMacroMode_AutoReject()
    1135             : {
    1136           0 :     return m_aMacroMode.adjustMacroMode( NULL );
    1137             : }
    1138             : 
    1139           0 : bool ODatabaseModelImpl::checkMacrosOnLoading()
    1140             : {
    1141           0 :     Reference< XInteractionHandler > xInteraction;
    1142           0 :     xInteraction = m_aMediaDescriptor.getOrDefault( "InteractionHandler", xInteraction );
    1143           0 :     return m_aMacroMode.checkMacrosOnLoading( xInteraction );
    1144             : }
    1145             : 
    1146           0 : void ODatabaseModelImpl::resetMacroExecutionMode()
    1147             : {
    1148           0 :     m_aMacroMode = ::sfx2::DocumentMacroMode( *this );
    1149           0 : }
    1150             : 
    1151           0 : Reference< XStorageBasedLibraryContainer > ODatabaseModelImpl::getLibraryContainer( bool _bScript )
    1152             : {
    1153           0 :     Reference< XStorageBasedLibraryContainer >& rxContainer( _bScript ? m_xBasicLibraries : m_xDialogLibraries );
    1154           0 :     if ( rxContainer.is() )
    1155           0 :         return rxContainer;
    1156             : 
    1157           0 :     Reference< XStorageBasedDocument > xDocument( getModel_noCreate(), UNO_QUERY_THROW );
    1158             :         // this is only to be called if there already exists a document model - in fact, it is
    1159             :         // to be called by the document model only
    1160             : 
    1161             :     try
    1162             :     {
    1163             :         Reference< XStorageBasedLibraryContainer > (*Factory)( const Reference< XComponentContext >&, const Reference< XStorageBasedDocument >&)
    1164           0 :             = _bScript ? &DocumentScriptLibraryContainer::create : &DocumentDialogLibraryContainer::create;
    1165             : 
    1166             :         rxContainer.set(
    1167             :             (*Factory)( m_aContext.getUNOContext(), xDocument ),
    1168             :             UNO_QUERY_THROW
    1169           0 :         );
    1170             :     }
    1171           0 :     catch( const RuntimeException& )
    1172             :     {
    1173           0 :         throw;
    1174             :     }
    1175           0 :     catch( const Exception& )
    1176             :     {
    1177             :         throw WrappedTargetRuntimeException(
    1178             :             ::rtl::OUString(),
    1179             :             xDocument,
    1180             :             ::cppu::getCaughtException()
    1181           0 :         );
    1182             :     }
    1183           0 :     return rxContainer;
    1184             : }
    1185             : 
    1186           0 : void ODatabaseModelImpl::storeLibraryContainersTo( const Reference< XStorage >& _rxToRootStorage )
    1187             : {
    1188           0 :     if ( m_xBasicLibraries.is() )
    1189           0 :         m_xBasicLibraries->storeLibrariesToStorage( _rxToRootStorage );
    1190             : 
    1191           0 :     if ( m_xDialogLibraries.is() )
    1192           0 :         m_xDialogLibraries->storeLibrariesToStorage( _rxToRootStorage );
    1193           0 : }
    1194             : 
    1195           0 : Reference< XStorage > ODatabaseModelImpl::switchToStorage( const Reference< XStorage >& _rxNewRootStorage )
    1196             : {
    1197           0 :     if ( !_rxNewRootStorage.is() )
    1198           0 :         throw IllegalArgumentException();
    1199             : 
    1200           0 :     return impl_switchToStorage_throw( _rxNewRootStorage );
    1201             : }
    1202             : 
    1203             : namespace
    1204             : {
    1205           0 :     void lcl_modifyListening( ::sfx2::IModifiableDocument& _rDocument,
    1206             :         const Reference< XStorage >& _rxStorage, ::rtl::Reference< ::sfx2::DocumentStorageModifyListener >& _inout_rListener,
    1207             :         ::osl::SolarMutex& _rMutex, bool _bListen )
    1208             :     {
    1209           0 :         Reference< XModifiable > xModify( _rxStorage, UNO_QUERY );
    1210             :         OSL_ENSURE( xModify.is() || !_rxStorage.is(), "lcl_modifyListening: storage can't notify us!" );
    1211             : 
    1212           0 :         if ( xModify.is() && !_bListen && _inout_rListener.is() )
    1213             :         {
    1214           0 :             xModify->removeModifyListener( _inout_rListener.get() );
    1215             :         }
    1216             : 
    1217           0 :         if ( _inout_rListener.is() )
    1218             :         {
    1219           0 :             _inout_rListener->dispose();
    1220           0 :             _inout_rListener = NULL;
    1221             :         }
    1222             : 
    1223           0 :         if ( xModify.is() && _bListen )
    1224             :         {
    1225           0 :             _inout_rListener = new ::sfx2::DocumentStorageModifyListener( _rDocument, _rMutex );
    1226           0 :             xModify->addModifyListener( _inout_rListener.get() );
    1227           0 :         }
    1228           0 :     }
    1229             : }
    1230             : 
    1231             : namespace
    1232             : {
    1233           0 :     static void lcl_rebaseScriptStorage_throw( const Reference< XStorageBasedLibraryContainer >& _rxContainer,
    1234             :         const Reference< XStorage >& _rxNewRootStorage )
    1235             :     {
    1236           0 :         if ( _rxContainer.is() )
    1237             :         {
    1238           0 :             if ( _rxNewRootStorage.is() )
    1239           0 :                 _rxContainer->setRootStorage( _rxNewRootStorage );
    1240             : //            else
    1241             :                    // TODO: what to do here? dispose the container?
    1242             :         }
    1243           0 :     }
    1244             : }
    1245             : 
    1246           0 : Reference< XStorage > ODatabaseModelImpl::impl_switchToStorage_throw( const Reference< XStorage >& _rxNewRootStorage )
    1247             : {
    1248             :     // stop listening for modifications at the old storage
    1249           0 :     lcl_modifyListening( *this, m_xDocumentStorage.getTyped(), m_pStorageModifyListener, m_aMutexFacade, false );
    1250             : 
    1251             :     // set new storage
    1252           0 :     m_xDocumentStorage.reset( _rxNewRootStorage, SharedStorage::TakeOwnership );
    1253             : 
    1254             :     // start listening for modifications
    1255           0 :     lcl_modifyListening( *this, m_xDocumentStorage.getTyped(), m_pStorageModifyListener, m_aMutexFacade, true );
    1256             : 
    1257             :     // forward new storage to Basic and Dialog library containers
    1258           0 :     lcl_rebaseScriptStorage_throw( m_xBasicLibraries, m_xDocumentStorage.getTyped() );
    1259           0 :     lcl_rebaseScriptStorage_throw( m_xDialogLibraries, m_xDocumentStorage.getTyped() );
    1260             : 
    1261           0 :     m_bReadOnly = !tools::stor::storageIsWritable_nothrow( m_xDocumentStorage.getTyped() );
    1262             :     // TODO: our data source, if it exists, must broadcast the change of its ReadOnly property
    1263             : 
    1264           0 :     return m_xDocumentStorage.getTyped();
    1265             : }
    1266             : 
    1267           0 : void ODatabaseModelImpl::impl_switchToLogicalURL( const ::rtl::OUString& i_rDocumentURL )
    1268             : {
    1269           0 :     if ( i_rDocumentURL == m_sDocumentURL )
    1270           0 :         return;
    1271             : 
    1272           0 :     const ::rtl::OUString sOldURL( m_sDocumentURL );
    1273             :     // update our name, if necessary
    1274           0 :     if  (   ( m_sName == m_sDocumentURL )   // our name is our old URL
    1275           0 :         ||  ( m_sName.isEmpty() )        // we do not have a name, yet (i.e. are not registered at the database context)
    1276             :         )
    1277             :     {
    1278           0 :         INetURLObject aURL( i_rDocumentURL );
    1279           0 :         if ( aURL.GetProtocol() != INET_PROT_NOT_VALID )
    1280             :         {
    1281           0 :             m_sName = i_rDocumentURL;
    1282             :             // TODO: our data source must broadcast the change of the Name property
    1283           0 :         }
    1284             :     }
    1285             : 
    1286             :     // remember URL
    1287           0 :     m_sDocumentURL = i_rDocumentURL;
    1288             : 
    1289             :     // update our location, if necessary
    1290           0 :     if  ( m_sDocFileLocation.isEmpty() )
    1291           0 :         m_sDocFileLocation = m_sDocumentURL;
    1292             : 
    1293             :     // register at the database context, or change registration
    1294           0 :     if ( m_pDBContext )
    1295             :     {
    1296           0 :         if ( !sOldURL.isEmpty() )
    1297           0 :             m_pDBContext->databaseDocumentURLChange( sOldURL, m_sDocumentURL );
    1298             :         else
    1299           0 :             m_pDBContext->registerDatabaseDocument( *this );
    1300           0 :     }
    1301             : }
    1302             : 
    1303           0 : ::rtl::OUString ODatabaseModelImpl::getObjectContainerStorageName( const ObjectType _eType )
    1304             : {
    1305           0 :     return lcl_getContainerStorageName_throw( _eType );
    1306             : }
    1307             : 
    1308           0 : sal_Int16 ODatabaseModelImpl::getCurrentMacroExecMode() const
    1309             : {
    1310           0 :     sal_Int16 nCurrentMode = MacroExecMode::NEVER_EXECUTE;
    1311             :     try
    1312             :     {
    1313           0 :         nCurrentMode = m_aMediaDescriptor.getOrDefault( "MacroExecutionMode", nCurrentMode );
    1314             :     }
    1315           0 :     catch( const Exception& )
    1316             :     {
    1317             :         DBG_UNHANDLED_EXCEPTION();
    1318             :     }
    1319           0 :     return nCurrentMode;
    1320             : }
    1321             : 
    1322           0 : sal_Bool ODatabaseModelImpl::setCurrentMacroExecMode( sal_uInt16 nMacroMode )
    1323             : {
    1324           0 :     m_aMediaDescriptor.put( "MacroExecutionMode", nMacroMode );
    1325           0 :     return sal_True;
    1326             : }
    1327             : 
    1328           0 : ::rtl::OUString ODatabaseModelImpl::getDocumentLocation() const
    1329             : {
    1330           0 :     return getURL();
    1331             :     // formerly, we returned getDocFileLocation here, which is the location of the file from which we
    1332             :     // recovered the "real" document.
    1333             :     // However, during CWS autorecovery evolving, we clarified (with MAV/MT) the role of XModel::getURL and
    1334             :     // XStorable::getLocation. In this course, we agreed that for a macro security check, the *document URL*
    1335             :     // (not the recovery file URL) is to be used: The recovery file lies in the backup folder, and by definition,
    1336             :     // this folder is considered to be secure. So, the document URL needs to be used to decide about the security.
    1337             : }
    1338             : 
    1339           0 : Reference< XStorage > ODatabaseModelImpl::getZipStorageToSign()
    1340             : {
    1341             :     // we do not support signing the scripting storages, so we're allowed to
    1342             :     // return <NULL/> here.
    1343           0 :     return Reference< XStorage >();
    1344             : }
    1345             : 
    1346           0 : ODatabaseModelImpl::EmbeddedMacros ODatabaseModelImpl::determineEmbeddedMacros()
    1347             : {
    1348           0 :     if ( !m_aEmbeddedMacros )
    1349             :     {
    1350           0 :         if ( ::sfx2::DocumentMacroMode::storageHasMacros( const_cast< ODatabaseModelImpl* >( this )->getOrCreateRootStorage() ) )
    1351             :         {
    1352           0 :             m_aEmbeddedMacros.reset( eDocumentWideMacros );
    1353             :         }
    1354           0 :         else if (   lcl_hasObjectsWithMacros_nothrow( const_cast< ODatabaseModelImpl& >( *this ), E_FORM )
    1355           0 :                 ||  lcl_hasObjectsWithMacros_nothrow( const_cast< ODatabaseModelImpl& >( *this ), E_REPORT )
    1356             :                 )
    1357             :         {
    1358           0 :             m_aEmbeddedMacros.reset( eSubDocumentMacros );
    1359             :         }
    1360             :         else
    1361             :         {
    1362           0 :             m_aEmbeddedMacros.reset( eNoMacros );
    1363             :         }
    1364             :     }
    1365           0 :     return *m_aEmbeddedMacros;
    1366             : }
    1367             : 
    1368           0 : sal_Bool ODatabaseModelImpl::documentStorageHasMacros() const
    1369             : {
    1370           0 :     const_cast< ODatabaseModelImpl* >( this )->determineEmbeddedMacros();
    1371           0 :     return ( *m_aEmbeddedMacros != eNoMacros );
    1372             : }
    1373             : 
    1374           0 : Reference< XEmbeddedScripts > ODatabaseModelImpl::getEmbeddedDocumentScripts() const
    1375             : {
    1376           0 :     return Reference< XEmbeddedScripts >( getModel_noCreate(), UNO_QUERY );
    1377             : }
    1378             : 
    1379           0 : sal_Int16 ODatabaseModelImpl::getScriptingSignatureState()
    1380             : {
    1381             :     // no support for signatures at the moment
    1382           0 :     return SIGNATURESTATE_NOSIGNATURES;
    1383             : }
    1384             : 
    1385           0 : sal_Bool ODatabaseModelImpl::hasTrustedScriptingSignature( sal_Bool /*bAllowUIToAddAuthor*/ )
    1386             : {
    1387             :     // no support for signatures at the moment
    1388           0 :     return sal_False;
    1389             : }
    1390             : 
    1391           0 : void ODatabaseModelImpl::showBrokenSignatureWarning( const Reference< XInteractionHandler >& /*_rxInteraction*/ ) const
    1392             : {
    1393             :     OSL_FAIL( "ODatabaseModelImpl::showBrokenSignatureWarning: signatures can't be broken - we do not support them!" );
    1394           0 : }
    1395             : 
    1396           0 : void ODatabaseModelImpl::storageIsModified()
    1397             : {
    1398           0 :     setModified( sal_True );
    1399           0 : }
    1400             : 
    1401           0 : ModelDependentComponent::ModelDependentComponent( const ::rtl::Reference< ODatabaseModelImpl >& _model )
    1402             :     :m_pImpl( _model )
    1403           0 :     ,m_aMutex( _model->getSharedMutex() )
    1404             : {
    1405           0 : }
    1406             : 
    1407           0 : ModelDependentComponent::~ModelDependentComponent()
    1408             : {
    1409           0 : }
    1410             : 
    1411             : }   // namespace dbaccess
    1412             : /* vim:set shiftwidth=4 softtabstop=4 expandtab: */

Generated by: LCOV version 1.10