LCOV - code coverage report
Current view: top level - basic/source/classes - sbxmod.cxx (source / functions) Hit Total Coverage
Test: commit 10e77ab3ff6f4314137acd6e2702a6e5c1ce1fae Lines: 669 1367 48.9 %
Date: 2014-11-03 Functions: 96 216 44.4 %
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 <list>
      22             : 
      23             : #include <boost/noncopyable.hpp>
      24             : #include <boost/scoped_ptr.hpp>
      25             : #include <vcl/svapp.hxx>
      26             : #include <tools/stream.hxx>
      27             : #include <svl/SfxBroadcaster.hxx>
      28             : #include <basic/sbx.hxx>
      29             : #include <basic/sbuno.hxx>
      30             : #include "sb.hxx"
      31             : #include <sbjsmeth.hxx>
      32             : #include "sbjsmod.hxx"
      33             : #include "sbintern.hxx"
      34             : #include "image.hxx"
      35             : #include "opcodes.hxx"
      36             : #include "runtime.hxx"
      37             : #include "token.hxx"
      38             : #include "sbunoobj.hxx"
      39             : 
      40             : #include <sal/log.hxx>
      41             : 
      42             : #include <basic/basrdll.hxx>
      43             : #include <osl/mutex.hxx>
      44             : #include "sbobjmod.hxx"
      45             : #include <basic/vbahelper.hxx>
      46             : #include <cppuhelper/implbase3.hxx>
      47             : #include <unotools/eventcfg.hxx>
      48             : #include <com/sun/star/frame/Desktop.hpp>
      49             : #include <com/sun/star/lang/XServiceInfo.hpp>
      50             : #include <com/sun/star/script/ModuleType.hpp>
      51             : #include <com/sun/star/script/vba/XVBACompatibility.hpp>
      52             : #include <com/sun/star/script/vba/VBAScriptEventId.hpp>
      53             : #include <com/sun/star/beans/XPropertySet.hpp>
      54             : #include <com/sun/star/document/XEventBroadcaster.hpp>
      55             : #include <com/sun/star/document/XEventListener.hpp>
      56             : 
      57             : #ifdef UNX
      58             : #include <sys/resource.h>
      59             : #endif
      60             : 
      61             : #include <stdio.h>
      62             : #include <com/sun/star/frame/XDesktop.hpp>
      63             : #include <com/sun/star/lang/XMultiServiceFactory.hpp>
      64             : #include <comphelper/processfactory.hxx>
      65             : #include <map>
      66             : #include <com/sun/star/reflection/ProxyFactory.hpp>
      67             : #include <cppuhelper/implbase1.hxx>
      68             : #include <com/sun/star/uno/XAggregation.hpp>
      69             : #include <com/sun/star/script/XInvocation.hpp>
      70             : 
      71             : #include <com/sun/star/script/XLibraryContainer.hpp>
      72             : #include <com/sun/star/awt/DialogProvider.hpp>
      73             : #include <com/sun/star/awt/XTopWindow.hpp>
      74             : #include <com/sun/star/awt/XWindow.hpp>
      75             : #include <com/sun/star/awt/XControl.hpp>
      76             : #include <comphelper/anytostring.hxx>
      77             : #include <ooo/vba/VbQueryClose.hpp>
      78             : #include "sbcomp.hxx"
      79             : #include "sbxmod.hxx"
      80             : 
      81             : using namespace com::sun::star;
      82             : using namespace com::sun::star::lang;
      83             : using namespace com::sun::star::reflection;
      84             : using namespace com::sun::star::beans;
      85             : using namespace com::sun::star::script;
      86             : using namespace com::sun::star::uno;
      87             : 
      88             : typedef ::cppu::WeakImplHelper1< XInvocation > DocObjectWrapper_BASE;
      89             : typedef ::std::map< sal_Int16, Any, ::std::less< sal_Int16 > > OutParamMap;
      90             : 
      91             : class DocObjectWrapper : public DocObjectWrapper_BASE
      92             : {
      93             :     Reference< XAggregation >  m_xAggProxy;
      94             :     Reference< XInvocation >  m_xAggInv;
      95             :     Reference< XTypeProvider > m_xAggregateTypeProv;
      96             :     Sequence< Type >           m_Types;
      97             :     SbModule*                m_pMod;
      98             :     SbMethodRef getMethod( const OUString& aName ) throw (RuntimeException);
      99             :     SbPropertyRef getProperty( const OUString& aName ) throw (RuntimeException);
     100             :     OUString mName; // for debugging
     101             : 
     102             : public:
     103             :     DocObjectWrapper( SbModule* pMod );
     104             :     virtual ~DocObjectWrapper();
     105             : 
     106             :     virtual void SAL_CALL acquire() throw() SAL_OVERRIDE;
     107             :     virtual void SAL_CALL release() throw() SAL_OVERRIDE;
     108             : 
     109           0 :     virtual Sequence< sal_Int8 > SAL_CALL getImplementationId() throw (RuntimeException, std::exception) SAL_OVERRIDE
     110             :     {
     111           0 :         return css::uno::Sequence<sal_Int8>();
     112             :     }
     113             : 
     114             :     virtual Reference< XIntrospectionAccess > SAL_CALL getIntrospection(  ) throw (RuntimeException, std::exception) SAL_OVERRIDE;
     115             : 
     116             :     virtual Any SAL_CALL invoke( const OUString& aFunctionName, const Sequence< Any >& aParams, Sequence< ::sal_Int16 >& aOutParamIndex, Sequence< Any >& aOutParam ) throw (IllegalArgumentException, CannotConvertException, InvocationTargetException, RuntimeException, std::exception) SAL_OVERRIDE;
     117             :     virtual void SAL_CALL setValue( const OUString& aPropertyName, const Any& aValue ) throw (UnknownPropertyException, CannotConvertException, InvocationTargetException, RuntimeException, std::exception) SAL_OVERRIDE;
     118             :     virtual Any SAL_CALL getValue( const OUString& aPropertyName ) throw (UnknownPropertyException, RuntimeException, std::exception) SAL_OVERRIDE;
     119             :     virtual sal_Bool SAL_CALL hasMethod( const OUString& aName ) throw (RuntimeException, std::exception) SAL_OVERRIDE;
     120             :     virtual sal_Bool SAL_CALL hasProperty( const OUString& aName ) throw (RuntimeException, std::exception) SAL_OVERRIDE;
     121             :     virtual  Any SAL_CALL queryInterface( const Type& aType ) throw ( RuntimeException, std::exception ) SAL_OVERRIDE;
     122             : 
     123             :     virtual Sequence< Type > SAL_CALL getTypes() throw ( RuntimeException, std::exception ) SAL_OVERRIDE;
     124             : };
     125             : 
     126          88 : DocObjectWrapper::DocObjectWrapper( SbModule* pVar ) : m_pMod( pVar ), mName( pVar->GetName() )
     127             : {
     128          88 :     SbObjModule* pMod = PTR_CAST(SbObjModule,pVar);
     129          88 :     if ( pMod )
     130             :     {
     131          88 :         if ( pMod->GetModuleType() == ModuleType::DOCUMENT )
     132             :         {
     133             :             // Use proxy factory service to create aggregatable proxy.
     134          88 :             SbUnoObject* pUnoObj = PTR_CAST(SbUnoObject,pMod->GetObject() );
     135          88 :             Reference< XInterface > xIf;
     136          88 :             if ( pUnoObj )
     137             :             {
     138          88 :                    Any aObj = pUnoObj->getUnoAny();
     139          88 :                    aObj >>= xIf;
     140          88 :                    if ( xIf.is() )
     141             :                    {
     142          88 :                        m_xAggregateTypeProv.set( xIf, UNO_QUERY );
     143          88 :                        m_xAggInv.set( xIf, UNO_QUERY );
     144          88 :                    }
     145             :             }
     146          88 :             if ( xIf.is() )
     147             :             {
     148             :                 try
     149             :                 {
     150          88 :                     Reference< XProxyFactory > xProxyFac = ProxyFactory::create( comphelper::getProcessComponentContext() );
     151          88 :                     m_xAggProxy = xProxyFac->createProxy( xIf );
     152             :                 }
     153           0 :                 catch(const Exception& )
     154             :                 {
     155             :                     SAL_WARN( "basic", "DocObjectWrapper::DocObjectWrapper: Caught exception!" );
     156             :                 }
     157             :             }
     158             : 
     159          88 :             if ( m_xAggProxy.is() )
     160             :             {
     161          88 :                 osl_atomic_increment( &m_refCount );
     162             : 
     163             :                 /* i35609 - Fix crash on Solaris. The setDelegator call needs
     164             :                     to be in its own block to ensure that all temporary Reference
     165             :                     instances that are acquired during the call are released
     166             :                     before m_refCount is decremented again */
     167             :                 {
     168          88 :                     m_xAggProxy->setDelegator( static_cast< cppu::OWeakObject * >( this ) );
     169             :                 }
     170             : 
     171          88 :                  osl_atomic_decrement( &m_refCount );
     172          88 :             }
     173             :         }
     174             :     }
     175          88 : }
     176             : 
     177             : void SAL_CALL
     178      159706 : DocObjectWrapper::acquire() throw ()
     179             : {
     180      159706 :     osl_atomic_increment( &m_refCount );
     181             :     SAL_INFO("basic","DocObjectWrapper::acquire("<< OUStringToOString( mName, RTL_TEXTENCODING_UTF8 ).getStr() << ") 0x" << this << " refcount is now " << m_refCount );
     182      159706 : }
     183             : void SAL_CALL
     184      159706 : DocObjectWrapper::release() throw ()
     185             : {
     186      159706 :     if ( osl_atomic_decrement( &m_refCount ) == 0 )
     187             :     {
     188             :         SAL_INFO("basic","DocObjectWrapper::release("<< OUStringToOString( mName, RTL_TEXTENCODING_UTF8 ).getStr() << ") 0x" << this << " refcount is now " << m_refCount );
     189          88 :         delete this;
     190             :     }
     191             :     else
     192             :     {
     193             :         SAL_INFO("basic","DocObjectWrapper::release("<< OUStringToOString( mName, RTL_TEXTENCODING_UTF8 ).getStr() << ") 0x" << this << " refcount is now " << m_refCount );
     194             :     }
     195      159706 : }
     196             : 
     197         176 : DocObjectWrapper::~DocObjectWrapper()
     198             : {
     199         176 : }
     200             : 
     201         948 : Sequence< Type > SAL_CALL DocObjectWrapper::getTypes()
     202             :     throw ( RuntimeException, std::exception )
     203             : {
     204         948 :     if ( m_Types.getLength() == 0 )
     205             :     {
     206          48 :         Sequence< Type > sTypes;
     207          48 :         if ( m_xAggregateTypeProv.is() )
     208             :         {
     209          48 :             sTypes = m_xAggregateTypeProv->getTypes();
     210             :         }
     211          48 :         m_Types.realloc( sTypes.getLength() + 1 );
     212          48 :         Type* pPtr = m_Types.getArray();
     213         260 :         for ( int i=0; i<m_Types.getLength(); ++i, ++pPtr )
     214             :         {
     215         212 :             if ( i == 0 )
     216             :             {
     217          48 :                 *pPtr = cppu::UnoType<XInvocation>::get();
     218             :             }
     219             :             else
     220             :             {
     221         164 :                 *pPtr = sTypes[ i - 1 ];
     222             :             }
     223          48 :         }
     224             :     }
     225         948 :     return m_Types;
     226             : }
     227             : 
     228             : Reference< XIntrospectionAccess > SAL_CALL
     229           0 : DocObjectWrapper::getIntrospection(  ) throw (RuntimeException, std::exception)
     230             : {
     231           0 :     return NULL;
     232             : }
     233             : 
     234             : Any SAL_CALL
     235           0 : DocObjectWrapper::invoke( const OUString& aFunctionName, const Sequence< Any >& aParams, Sequence< ::sal_Int16 >& aOutParamIndex, Sequence< Any >& aOutParam ) throw (IllegalArgumentException, CannotConvertException, InvocationTargetException, RuntimeException, std::exception)
     236             : {
     237           0 :     if ( m_xAggInv.is() &&  m_xAggInv->hasMethod( aFunctionName ) )
     238           0 :             return m_xAggInv->invoke( aFunctionName, aParams, aOutParamIndex, aOutParam );
     239           0 :     SbMethodRef pMethod = getMethod( aFunctionName );
     240           0 :     if ( !pMethod )
     241           0 :         throw RuntimeException();
     242             :     // check number of parameters
     243           0 :     sal_Int32 nParamsCount = aParams.getLength();
     244           0 :     SbxInfo* pInfo = pMethod->GetInfo();
     245           0 :     if ( pInfo )
     246             :     {
     247           0 :         sal_Int32 nSbxOptional = 0;
     248           0 :         sal_uInt16 n = 1;
     249           0 :         for ( const SbxParamInfo* pParamInfo = pInfo->GetParam( n ); pParamInfo; pParamInfo = pInfo->GetParam( ++n ) )
     250             :         {
     251           0 :             if ( ( pParamInfo->nFlags & SBX_OPTIONAL ) != SBX_NONE )
     252           0 :                 ++nSbxOptional;
     253             :             else
     254           0 :                 nSbxOptional = 0;
     255             :         }
     256           0 :         sal_Int32 nSbxCount = n - 1;
     257           0 :         if ( nParamsCount < nSbxCount - nSbxOptional )
     258             :         {
     259           0 :             throw RuntimeException( "wrong number of parameters!" );
     260             :         }
     261             :     }
     262             :     // set parameters
     263           0 :     SbxArrayRef xSbxParams;
     264           0 :     if ( nParamsCount > 0 )
     265             :     {
     266           0 :         xSbxParams = new SbxArray;
     267           0 :         const Any* pParams = aParams.getConstArray();
     268           0 :         for ( sal_Int32 i = 0; i < nParamsCount; ++i )
     269             :         {
     270           0 :             SbxVariableRef xSbxVar = new SbxVariable( SbxVARIANT );
     271           0 :             unoToSbxValue( static_cast< SbxVariable* >( xSbxVar ), pParams[i] );
     272           0 :             xSbxParams->Put( xSbxVar, static_cast< sal_uInt16 >( i ) + 1 );
     273             : 
     274             :             // Enable passing by ref
     275           0 :             if ( xSbxVar->GetType() != SbxVARIANT )
     276           0 :                 xSbxVar->SetFlag( SBX_FIXED );
     277           0 :         }
     278             :     }
     279           0 :     if ( xSbxParams.Is() )
     280           0 :         pMethod->SetParameters( xSbxParams );
     281             : 
     282             :     // call method
     283           0 :     SbxVariableRef xReturn = new SbxVariable;
     284             : 
     285           0 :     pMethod->Call( xReturn );
     286           0 :     Any aReturn;
     287             :     // get output parameters
     288           0 :     if ( xSbxParams.Is() )
     289             :     {
     290           0 :         SbxInfo* pInfo_ = pMethod->GetInfo();
     291           0 :         if ( pInfo_ )
     292             :         {
     293           0 :             OutParamMap aOutParamMap;
     294           0 :             for ( sal_uInt16 n = 1, nCount = xSbxParams->Count(); n < nCount; ++n )
     295             :             {
     296           0 :                 const SbxParamInfo* pParamInfo = pInfo_->GetParam( n );
     297           0 :                 if ( pParamInfo && ( pParamInfo->eType & SbxBYREF ) != 0 )
     298             :                 {
     299           0 :                     SbxVariable* pVar = xSbxParams->Get( n );
     300           0 :                     if ( pVar )
     301             :                     {
     302           0 :                         SbxVariableRef xVar = pVar;
     303           0 :                         aOutParamMap.insert( OutParamMap::value_type( n - 1, sbxToUnoValue( xVar ) ) );
     304             :                     }
     305             :                 }
     306             :             }
     307           0 :             sal_Int32 nOutParamCount = aOutParamMap.size();
     308           0 :             aOutParamIndex.realloc( nOutParamCount );
     309           0 :             aOutParam.realloc( nOutParamCount );
     310           0 :             sal_Int16* pOutParamIndex = aOutParamIndex.getArray();
     311           0 :             Any* pOutParam = aOutParam.getArray();
     312           0 :             for ( OutParamMap::iterator aIt = aOutParamMap.begin(); aIt != aOutParamMap.end(); ++aIt, ++pOutParamIndex, ++pOutParam )
     313             :             {
     314           0 :                 *pOutParamIndex = aIt->first;
     315           0 :                 *pOutParam = aIt->second;
     316           0 :             }
     317             :         }
     318             :     }
     319             : 
     320             :     // get return value
     321           0 :     aReturn = sbxToUnoValue( xReturn );
     322             : 
     323           0 :     pMethod->SetParameters( NULL );
     324             : 
     325           0 :     return aReturn;
     326             : }
     327             : 
     328             : void SAL_CALL
     329           0 : DocObjectWrapper::setValue( const OUString& aPropertyName, const Any& aValue ) throw (UnknownPropertyException, CannotConvertException, InvocationTargetException, RuntimeException, std::exception)
     330             : {
     331           0 :     if ( m_xAggInv.is() &&  m_xAggInv->hasProperty( aPropertyName ) )
     332           0 :             return m_xAggInv->setValue( aPropertyName, aValue );
     333             : 
     334           0 :     SbPropertyRef pProperty = getProperty( aPropertyName );
     335           0 :     if ( !pProperty.Is() )
     336           0 :        throw UnknownPropertyException();
     337           0 :     unoToSbxValue( (SbxVariable*) pProperty, aValue );
     338             : }
     339             : 
     340             : Any SAL_CALL
     341           0 : DocObjectWrapper::getValue( const OUString& aPropertyName ) throw (UnknownPropertyException, RuntimeException, std::exception)
     342             : {
     343           0 :     if ( m_xAggInv.is() &&  m_xAggInv->hasProperty( aPropertyName ) )
     344           0 :             return m_xAggInv->getValue( aPropertyName );
     345             : 
     346           0 :     SbPropertyRef pProperty = getProperty( aPropertyName );
     347           0 :     if ( !pProperty.Is() )
     348           0 :        throw UnknownPropertyException();
     349             : 
     350           0 :     SbxVariable* pProp = ( SbxVariable* ) pProperty;
     351           0 :     if ( pProp->GetType() == SbxEMPTY )
     352           0 :         pProperty->Broadcast( SBX_HINT_DATAWANTED );
     353             : 
     354           0 :     Any aRet = sbxToUnoValue( pProp );
     355           0 :     return aRet;
     356             : }
     357             : 
     358             : sal_Bool SAL_CALL
     359           0 : DocObjectWrapper::hasMethod( const OUString& aName ) throw (RuntimeException, std::exception)
     360             : {
     361           0 :     if ( m_xAggInv.is() && m_xAggInv->hasMethod( aName ) )
     362           0 :         return sal_True;
     363           0 :     return getMethod( aName ).Is();
     364             : }
     365             : 
     366             : sal_Bool SAL_CALL
     367           0 : DocObjectWrapper::hasProperty( const OUString& aName ) throw (RuntimeException, std::exception)
     368             : {
     369           0 :     bool bRes = false;
     370           0 :     if ( m_xAggInv.is() && m_xAggInv->hasProperty( aName ) )
     371           0 :         bRes = true;
     372           0 :     else bRes = getProperty( aName ).Is();
     373           0 :     return bRes;
     374             : }
     375             : 
     376       45890 : Any SAL_CALL DocObjectWrapper::queryInterface( const Type& aType )
     377             :     throw ( RuntimeException, std::exception )
     378             : {
     379       45890 :     Any aRet = DocObjectWrapper_BASE::queryInterface( aType );
     380       45890 :     if ( aRet.hasValue() )
     381       25000 :         return aRet;
     382       20890 :     else if ( m_xAggProxy.is() )
     383       20890 :         aRet = m_xAggProxy->queryAggregation( aType );
     384       20890 :     return aRet;
     385             : }
     386             : 
     387           0 : SbMethodRef DocObjectWrapper::getMethod( const OUString& aName ) throw (RuntimeException)
     388             : {
     389           0 :     SbMethodRef pMethod = NULL;
     390           0 :     if ( m_pMod )
     391             :     {
     392           0 :         SbxFlagBits nSaveFlgs = m_pMod->GetFlags();
     393             :         // Limit search to this module
     394           0 :         m_pMod->ResetFlag( SBX_GBLSEARCH );
     395           0 :         pMethod = dynamic_cast<SbMethod*>(m_pMod->SbModule::Find(aName,  SbxCLASS_METHOD));
     396           0 :         m_pMod->SetFlags( nSaveFlgs );
     397             :     }
     398             : 
     399           0 :     return pMethod;
     400             : }
     401             : 
     402           0 : SbPropertyRef DocObjectWrapper::getProperty( const OUString& aName ) throw (RuntimeException)
     403             : {
     404           0 :     SbPropertyRef pProperty = NULL;
     405           0 :     if ( m_pMod )
     406             :     {
     407           0 :         SbxFlagBits nSaveFlgs = m_pMod->GetFlags();
     408             :         // Limit search to this module.
     409           0 :         m_pMod->ResetFlag( SBX_GBLSEARCH );
     410           0 :         pProperty = dynamic_cast<SbProperty*>(m_pMod->SbModule::Find(aName,  SbxCLASS_PROPERTY));
     411           0 :         m_pMod->SetFlag( nSaveFlgs );
     412             :     }
     413             : 
     414           0 :     return pProperty;
     415             : }
     416             : 
     417       44162 : TYPEINIT1(SbModule,SbxObject)
     418       59974 : TYPEINIT1(SbMethod,SbxMethod)
     419       68620 : TYPEINIT1(SbProperty,SbxProperty)
     420       20056 : TYPEINIT1(SbProcedureProperty,SbxProperty)
     421           0 : TYPEINIT1(SbJScriptModule,SbModule)
     422           0 : TYPEINIT1(SbJScriptMethod,SbMethod)
     423        6376 : TYPEINIT1(SbObjModule,SbModule)
     424        1764 : TYPEINIT1(SbUserFormModule,SbObjModule)
     425             : 
     426         830 : uno::Reference< frame::XModel > getDocumentModel( StarBASIC* pb )
     427             : {
     428         830 :     uno::Reference< frame::XModel > xModel;
     429         830 :     if( pb && pb->IsDocBasic() )
     430             :     {
     431          50 :         uno::Any aDoc;
     432          50 :         if( pb->GetUNOConstant( "ThisComponent", aDoc ) )
     433          50 :             xModel.set( aDoc, uno::UNO_QUERY );
     434             :     }
     435         830 :     return xModel;
     436             : }
     437             : 
     438         504 : uno::Reference< vba::XVBACompatibility > getVBACompatibility( const uno::Reference< frame::XModel >& rxModel )
     439             : {
     440         504 :     uno::Reference< vba::XVBACompatibility > xVBACompat;
     441             :     try
     442             :     {
     443         504 :         uno::Reference< beans::XPropertySet > xModelProps( rxModel, uno::UNO_QUERY_THROW );
     444          54 :         xVBACompat.set( xModelProps->getPropertyValue( "BasicLibraries" ), uno::UNO_QUERY );
     445             :     }
     446         450 :     catch(const uno::Exception& )
     447             :     {
     448             :     }
     449         504 :     return xVBACompat;
     450             : }
     451             : 
     452         450 : bool getDefaultVBAMode( StarBASIC* pb )
     453             : {
     454         450 :     uno::Reference< vba::XVBACompatibility > xVBACompat = getVBACompatibility( getDocumentModel( pb ) );
     455         450 :     return xVBACompat.is() && xVBACompat->getVBACompatibilityMode();
     456             : }
     457             : 
     458             : class AsyncQuitHandler: private boost::noncopyable
     459             : {
     460           0 :     AsyncQuitHandler() {}
     461             : 
     462             : public:
     463           0 :     static AsyncQuitHandler& instance()
     464             :     {
     465           0 :         static AsyncQuitHandler dInst;
     466           0 :         return dInst;
     467             :     }
     468             : 
     469           0 :     void QuitApplication()
     470             :     {
     471           0 :         uno::Reference< frame::XDesktop2 > xDeskTop = frame::Desktop::create( comphelper::getProcessComponentContext() );
     472           0 :         xDeskTop->terminate();
     473           0 :     }
     474             :     DECL_LINK( OnAsyncQuit, void* );
     475             : };
     476             : 
     477           0 : IMPL_LINK( AsyncQuitHandler, OnAsyncQuit, void*, /*pNull*/ )
     478             : {
     479           0 :     QuitApplication();
     480           0 :     return 0L;
     481             : }
     482             : 
     483             : // A Basic module has set EXTSEARCH, so that the elements, that the modul contains,
     484             : // could be found from other module.
     485             : 
     486         450 : SbModule::SbModule( const OUString& rName, bool bVBACompat )
     487             :          : SbxObject( "StarBASICModule" ),
     488         450 :            pImage( NULL ), pBreaks( NULL ), pClassData( NULL ), mbVBACompat( bVBACompat ),  pDocObject( NULL ), bIsProxyModule( false )
     489             : {
     490         450 :     SetName( rName );
     491         450 :     SetFlag( SBX_EXTSEARCH | SBX_GBLSEARCH );
     492         450 :     SetModuleType( script::ModuleType::NORMAL );
     493             : 
     494             :     // #i92642: Set name property to intitial name
     495         450 :     SbxVariable* pNameProp = pProps->Find( "Name", SbxCLASS_PROPERTY );
     496         450 :     if( pNameProp != NULL )
     497             :     {
     498         450 :         pNameProp->PutString( GetName() );
     499             :     }
     500         450 : }
     501             : 
     502        1092 : SbModule::~SbModule()
     503             : {
     504             :     SAL_INFO("basic","Module named " << OUStringToOString( GetName(), RTL_TEXTENCODING_UTF8 ).getStr() << " is destructing");
     505         448 :     delete pImage;
     506         448 :     delete pBreaks;
     507         448 :     delete pClassData;
     508         448 :     mxWrapper = NULL;
     509         644 : }
     510             : 
     511             : uno::Reference< script::XInvocation >
     512        3898 : SbModule::GetUnoModule()
     513             : {
     514        3898 :     if ( !mxWrapper.is() )
     515          88 :         mxWrapper = new DocObjectWrapper( this );
     516             : 
     517             :     SAL_INFO("basic","Module named " << OUStringToOString( GetName(), RTL_TEXTENCODING_UTF8 ).getStr() << " returning wrapper mxWrapper (0x" << mxWrapper.get() <<")" );
     518        3898 :     return mxWrapper;
     519             : }
     520             : 
     521        4124 : bool SbModule::IsCompiled() const
     522             : {
     523        4124 :     return pImage != 0;
     524             : }
     525             : 
     526         310 : const SbxObject* SbModule::FindType( const OUString& aTypeName ) const
     527             : {
     528         310 :     return pImage ? pImage->FindType( aTypeName ) : NULL;
     529             : }
     530             : 
     531             : 
     532             : // From the code generator: deletion of images and the oposite of validation for entries
     533             : 
     534         798 : void SbModule::StartDefinitions()
     535             : {
     536         798 :     delete pImage; pImage = NULL;
     537         798 :     if( pClassData )
     538           0 :         pClassData->clear();
     539             : 
     540             :     // methods and properties persist, but they are invalid;
     541             :     // at least are the information under certain conditions clogged
     542             :     sal_uInt16 i;
     543        1592 :     for( i = 0; i < pMethods->Count(); i++ )
     544             :     {
     545         794 :         SbMethod* p = PTR_CAST(SbMethod,pMethods->Get( i ) );
     546         794 :         if( p )
     547         794 :             p->bInvalid = true;
     548             :     }
     549        3192 :     for( i = 0; i < pProps->Count(); )
     550             :     {
     551        1596 :         SbProperty* p = PTR_CAST(SbProperty,pProps->Get( i ) );
     552        1596 :         if( p )
     553           0 :             pProps->Remove( i );
     554             :         else
     555        1596 :             i++;
     556             :     }
     557         798 : }
     558             : 
     559             : // request/create method
     560             : 
     561        1690 : SbMethod* SbModule::GetMethod( const OUString& rName, SbxDataType t )
     562             : {
     563        1690 :     SbxVariable* p = pMethods->Find( rName, SbxCLASS_METHOD );
     564        1690 :     SbMethod* pMeth = p ? PTR_CAST(SbMethod,p) : NULL;
     565        1690 :     if( p && !pMeth )
     566             :     {
     567           0 :         pMethods->Remove( p );
     568             :     }
     569        1690 :     if( !pMeth )
     570             :     {
     571         896 :         pMeth = new SbMethod( rName, t, this );
     572         896 :         pMeth->SetParent( this );
     573         896 :         pMeth->SetFlags( SBX_READ );
     574         896 :         pMethods->Put( pMeth, pMethods->Count() );
     575         896 :         StartListening( pMeth->GetBroadcaster(), true );
     576             :     }
     577             :     // The method is per default valid, because it could be
     578             :     // created from the compiler (code generator) as well.
     579        1690 :     pMeth->bInvalid = false;
     580        1690 :     pMeth->ResetFlag( SBX_FIXED );
     581        1690 :     pMeth->SetFlag( SBX_WRITE );
     582        1690 :     pMeth->SetType( t );
     583        1690 :     pMeth->ResetFlag( SBX_WRITE );
     584        1690 :     if( t != SbxVARIANT )
     585             :     {
     586        1372 :         pMeth->SetFlag( SBX_FIXED );
     587             :     }
     588        1690 :     return pMeth;
     589             : }
     590             : 
     591             : // request/create property
     592             : 
     593         260 : SbProperty* SbModule::GetProperty( const OUString& rName, SbxDataType t )
     594             : {
     595         260 :     SbxVariable* p = pProps->Find( rName, SbxCLASS_PROPERTY );
     596         260 :     SbProperty* pProp = p ? PTR_CAST(SbProperty,p) : NULL;
     597         260 :     if( p && !pProp )
     598             :     {
     599           0 :         pProps->Remove( p );
     600             :     }
     601         260 :     if( !pProp )
     602             :     {
     603         260 :         pProp = new SbProperty( rName, t, this );
     604         260 :         pProp->SetFlag( SBX_READWRITE );
     605         260 :         pProp->SetParent( this );
     606         260 :         pProps->Put( pProp, pProps->Count() );
     607         260 :         StartListening( pProp->GetBroadcaster(), true );
     608             :     }
     609         260 :     return pProp;
     610             : }
     611             : 
     612           0 : SbProcedureProperty* SbModule::GetProcedureProperty( const OUString& rName, SbxDataType t )
     613             : {
     614           0 :     SbxVariable* p = pProps->Find( rName, SbxCLASS_PROPERTY );
     615           0 :     SbProcedureProperty* pProp = p ? PTR_CAST(SbProcedureProperty,p) : NULL;
     616           0 :     if( p && !pProp )
     617             :     {
     618           0 :         pProps->Remove( p );
     619             :     }
     620           0 :     if( !pProp )
     621             :     {
     622           0 :         pProp = new SbProcedureProperty( rName, t );
     623           0 :         pProp->SetFlag( SBX_READWRITE );
     624           0 :         pProp->SetParent( this );
     625           0 :         pProps->Put( pProp, pProps->Count() );
     626           0 :         StartListening( pProp->GetBroadcaster(), true );
     627             :     }
     628           0 :     return pProp;
     629             : }
     630             : 
     631           0 : SbIfaceMapperMethod* SbModule::GetIfaceMapperMethod( const OUString& rName, SbMethod* pImplMeth )
     632             : {
     633           0 :     SbxVariable* p = pMethods->Find( rName, SbxCLASS_METHOD );
     634           0 :     SbIfaceMapperMethod* pMapperMethod = p ? PTR_CAST(SbIfaceMapperMethod,p) : NULL;
     635           0 :     if( p && !pMapperMethod )
     636             :     {
     637           0 :         pMethods->Remove( p );
     638             :     }
     639           0 :     if( !pMapperMethod )
     640             :     {
     641           0 :         pMapperMethod = new SbIfaceMapperMethod( rName, pImplMeth );
     642           0 :         pMapperMethod->SetParent( this );
     643           0 :         pMapperMethod->SetFlags( SBX_READ );
     644           0 :         pMethods->Put( pMapperMethod, pMethods->Count() );
     645             :     }
     646           0 :     pMapperMethod->bInvalid = false;
     647           0 :     return pMapperMethod;
     648             : }
     649             : 
     650           0 : SbIfaceMapperMethod::~SbIfaceMapperMethod()
     651             : {
     652           0 : }
     653             : 
     654           0 : TYPEINIT1(SbIfaceMapperMethod,SbMethod)
     655             : 
     656             : 
     657             : // From the code generator: remove invalid entries
     658             : 
     659         798 : void SbModule::EndDefinitions( bool bNewState )
     660             : {
     661        3286 :     for( sal_uInt16 i = 0; i < pMethods->Count(); )
     662             :     {
     663        1690 :         SbMethod* p = PTR_CAST(SbMethod,pMethods->Get( i ) );
     664        1690 :         if( p )
     665             :         {
     666        1690 :             if( p->bInvalid )
     667             :             {
     668           0 :                 pMethods->Remove( p );
     669             :             }
     670             :             else
     671             :             {
     672        1690 :                 p->bInvalid = bNewState;
     673        1690 :                 i++;
     674             :             }
     675             :         }
     676             :         else
     677           0 :             i++;
     678             :     }
     679         798 :     SetModified( true );
     680         798 : }
     681             : 
     682           0 : void SbModule::Clear()
     683             : {
     684           0 :     delete pImage; pImage = NULL;
     685           0 :     if( pClassData )
     686           0 :         pClassData->clear();
     687           0 :     SbxObject::Clear();
     688           0 : }
     689             : 
     690             : 
     691       41978 : SbxVariable* SbModule::Find( const OUString& rName, SbxClassType t )
     692             : {
     693             :     // make sure a search in an uninstatiated class module will fail
     694       41978 :     SbxVariable* pRes = SbxObject::Find( rName, t );
     695       41978 :     if ( bIsProxyModule && !GetSbData()->bRunInit )
     696             :     {
     697           0 :         return NULL;
     698             :     }
     699       41978 :     if( !pRes && pImage )
     700             :     {
     701       25028 :         SbiInstance* pInst = GetSbData()->pInst;
     702       25028 :         if( pInst && pInst->IsCompatibility() )
     703             :         {
     704             :             // Put enum types as objects into module,
     705             :             // allows MyEnum.First notation
     706        1816 :             SbxArrayRef xArray = pImage->GetEnums();
     707        1816 :             if( xArray.Is() )
     708             :             {
     709           0 :                 SbxVariable* pEnumVar = xArray->Find( rName, SbxCLASS_DONTCARE );
     710           0 :                 SbxObject* pEnumObject = PTR_CAST( SbxObject, pEnumVar );
     711           0 :                 if( pEnumObject )
     712             :                 {
     713           0 :                     bool bPrivate = pEnumObject->IsSet( SBX_PRIVATE );
     714           0 :                     OUString aEnumName = pEnumObject->GetName();
     715             : 
     716           0 :                     pRes = new SbxVariable( SbxOBJECT );
     717           0 :                     pRes->SetName( aEnumName );
     718           0 :                     pRes->SetParent( this );
     719           0 :                     pRes->SetFlag( SBX_READ );
     720           0 :                     if( bPrivate )
     721             :                     {
     722           0 :                         pRes->SetFlag( SBX_PRIVATE );
     723             :                     }
     724           0 :                     pRes->PutObject( pEnumObject );
     725             :                 }
     726        1816 :             }
     727             :         }
     728             :     }
     729       41978 :     return pRes;
     730             : }
     731             : 
     732             : 
     733           0 : const OUString& SbModule::GetSource() const
     734             : {
     735           0 :     static OUString aRetStr;
     736           0 :     aRetStr = aOUSource;
     737           0 :     return aRetStr;
     738             : }
     739             : 
     740             : // Parent and BASIC are one!
     741             : 
     742         450 : void SbModule::SetParent( SbxObject* p )
     743             : {
     744         450 :     pParent = p;
     745         450 : }
     746             : 
     747        7306 : void SbModule::SFX_NOTIFY( SfxBroadcaster& rBC, const TypeId& rBCType,
     748             :                            const SfxHint& rHint, const TypeId& rHintType )
     749             : {
     750        7306 :     const SbxHint* pHint = dynamic_cast<const SbxHint*>(&rHint);
     751        7306 :     if( pHint )
     752             :     {
     753        7306 :         SbxVariable* pVar = pHint->GetVar();
     754        7306 :         SbProperty* pProp = PTR_CAST(SbProperty,pVar);
     755        7306 :         SbMethod* pMeth = PTR_CAST(SbMethod,pVar);
     756        7306 :         SbProcedureProperty* pProcProperty = PTR_CAST( SbProcedureProperty, pVar );
     757        7306 :         if( pProcProperty )
     758             :         {
     759             : 
     760           0 :             if( pHint->GetId() == SBX_HINT_DATAWANTED )
     761             :             {
     762           0 :                 OUString aProcName("Property Get ");
     763           0 :                 aProcName += pProcProperty->GetName();
     764             : 
     765           0 :                 SbxVariable* pMethVar = Find( aProcName, SbxCLASS_METHOD );
     766           0 :                 if( pMethVar )
     767             :                 {
     768           0 :                     SbxValues aVals;
     769           0 :                     aVals.eType = SbxVARIANT;
     770             : 
     771           0 :                     SbxArray* pArg = pVar->GetParameters();
     772           0 :                     sal_uInt16 nVarParCount = (pArg != NULL) ? pArg->Count() : 0;
     773           0 :                     if( nVarParCount > 1 )
     774             :                     {
     775           0 :                         SbxArrayRef xMethParameters = new SbxArray;
     776           0 :                         xMethParameters->Put( pMethVar, 0 );    // Method as parameter 0
     777           0 :                         for( sal_uInt16 i = 1 ; i < nVarParCount ; ++i )
     778             :                         {
     779           0 :                             SbxVariable* pPar = pArg->Get( i );
     780           0 :                             xMethParameters->Put( pPar, i );
     781             :                         }
     782             : 
     783           0 :                         pMethVar->SetParameters( xMethParameters );
     784           0 :                         pMethVar->Get( aVals );
     785           0 :                         pMethVar->SetParameters( NULL );
     786             :                     }
     787             :                     else
     788             :                     {
     789           0 :                         pMethVar->Get( aVals );
     790             :                     }
     791             : 
     792           0 :                     pVar->Put( aVals );
     793           0 :                 }
     794             :             }
     795           0 :             else if( pHint->GetId() == SBX_HINT_DATACHANGED )
     796             :             {
     797           0 :                 SbxVariable* pMethVar = NULL;
     798             : 
     799           0 :                 bool bSet = pProcProperty->isSet();
     800           0 :                 if( bSet )
     801             :                 {
     802           0 :                     pProcProperty->setSet( false );
     803             : 
     804           0 :                     OUString aProcName("Property Set ");
     805           0 :                     aProcName += pProcProperty->GetName();
     806           0 :                     pMethVar = Find( aProcName, SbxCLASS_METHOD );
     807             :                 }
     808           0 :                 if( !pMethVar ) // Let
     809             :                 {
     810           0 :                     OUString aProcName("Property Let " );
     811           0 :                     aProcName += pProcProperty->GetName();
     812           0 :                     pMethVar = Find( aProcName, SbxCLASS_METHOD );
     813             :                 }
     814             : 
     815           0 :                 if( pMethVar )
     816             :                 {
     817             :                     // Setup parameters
     818           0 :                     SbxArrayRef xArray = new SbxArray;
     819           0 :                     xArray->Put( pMethVar, 0 ); // Method as parameter 0
     820           0 :                     xArray->Put( pVar, 1 );
     821           0 :                     pMethVar->SetParameters( xArray );
     822             : 
     823           0 :                     SbxValues aVals;
     824           0 :                     pMethVar->Get( aVals );
     825           0 :                     pMethVar->SetParameters( NULL );
     826             :                 }
     827             :             }
     828             :         }
     829        7306 :         if( pProp )
     830             :         {
     831        3430 :             if( pProp->GetModule() != this )
     832           0 :                 SetError( SbxERR_BAD_ACTION );
     833             :         }
     834        3876 :         else if( pMeth )
     835             :         {
     836        2734 :             if( pHint->GetId() == SBX_HINT_DATAWANTED )
     837             :             {
     838        2734 :                 if( pMeth->bInvalid && !Compile() )
     839             :                 {
     840             :                     // auto compile has not worked!
     841           0 :                     StarBASIC::Error( SbERR_BAD_PROP_VALUE );
     842             :                 }
     843             :                 else
     844             :                 {
     845             :                     // Call of a subprogram
     846        2734 :                     SbModule* pOld = GetSbData()->pMod;
     847        2734 :                     GetSbData()->pMod = this;
     848        2734 :                     Run( static_cast<SbMethod*>(pVar) );
     849        2734 :                     GetSbData()->pMod = pOld;
     850             :                 }
     851             :             }
     852             :         }
     853             :         else
     854             :         {
     855             :             // #i92642: Special handling for name property to avoid
     856             :             // side effects when using name as variable implicitly
     857        1142 :             bool bForwardToSbxObject = true;
     858             : 
     859        1142 :             sal_uIntPtr nId = pHint->GetId();
     860        2284 :             if( (nId == SBX_HINT_DATAWANTED || nId == SBX_HINT_DATACHANGED) &&
     861        1142 :                 pVar->GetName().equalsIgnoreAsciiCase( "name" ) )
     862             :             {
     863         450 :                     bForwardToSbxObject = false;
     864             :             }
     865        1142 :             if( bForwardToSbxObject )
     866             :             {
     867         692 :                 SbxObject::SFX_NOTIFY( rBC, rBCType, rHint, rHintType );
     868             :             }
     869             :         }
     870             :     }
     871        7306 : }
     872             : 
     873             : // The setting of the source makes the image invalid
     874             : // and scans the method definitions newly in
     875             : 
     876           0 : void SbModule::SetSource( const OUString& r )
     877             : {
     878           0 :     SetSource32( r );
     879           0 : }
     880             : 
     881         450 : void SbModule::SetSource32( const OUString& r )
     882             : {
     883             :     // Default basic mode to library container mode, but.. allow Option VBASupport 0/1 override
     884         450 :     SetVBACompat( getDefaultVBAMode( static_cast< StarBASIC*>( GetParent() ) ) );
     885         450 :     aOUSource = r;
     886         450 :     StartDefinitions();
     887         450 :     SbiTokenizer aTok( r );
     888         450 :     aTok.SetCompatible( IsVBACompat() );
     889             : 
     890        2218 :     while( !aTok.IsEof() )
     891             :     {
     892        1318 :         SbiToken eEndTok = NIL;
     893             : 
     894             :         // Searching for SUB or FUNCTION
     895        1318 :         SbiToken eLastTok = NIL;
     896        9700 :         while( !aTok.IsEof() )
     897             :         {
     898             :             // #32385: not by declare
     899        7936 :             SbiToken eCurTok = aTok.Next();
     900        7936 :             if( eLastTok != DECLARE )
     901             :             {
     902        7928 :                 if( eCurTok == SUB )
     903             :                 {
     904         590 :                     eEndTok = ENDSUB; break;
     905             :                 }
     906        7338 :                 if( eCurTok == FUNCTION )
     907             :                 {
     908         282 :                     eEndTok = ENDFUNC; break;
     909             :                 }
     910        7056 :                 if( eCurTok == PROPERTY )
     911             :                 {
     912           0 :                     eEndTok = ENDPROPERTY; break;
     913             :                 }
     914        7056 :                 if( eCurTok == OPTION )
     915             :                 {
     916         378 :                     eCurTok = aTok.Next();
     917         378 :                     if( eCurTok == COMPATIBLE )
     918             :                     {
     919           0 :                         aTok.SetCompatible( true );
     920             :                     }
     921         378 :                     else if ( ( eCurTok == VBASUPPORT ) && ( aTok.Next() == NUMBER ) )
     922             :                     {
     923         330 :                         bool bIsVBA = ( aTok.GetDbl()== 1 );
     924         330 :                         SetVBACompat( bIsVBA );
     925         330 :                         aTok.SetCompatible( bIsVBA );
     926             :                     }
     927             :                 }
     928             :             }
     929        7064 :             eLastTok = eCurTok;
     930             :         }
     931             :         // Definition of the method
     932        1318 :         SbMethod* pMeth = NULL;
     933        1318 :         if( eEndTok != NIL )
     934             :         {
     935         872 :             sal_uInt16 nLine1 = aTok.GetLine();
     936         872 :             if( aTok.Next() == SYMBOL )
     937             :             {
     938         872 :                 OUString aName_( aTok.GetSym() );
     939         872 :                 SbxDataType t = aTok.GetType();
     940         872 :                 if( t == SbxVARIANT && eEndTok == ENDSUB )
     941             :                 {
     942         590 :                     t = SbxVOID;
     943             :                 }
     944         872 :                 pMeth = GetMethod( aName_, t );
     945         872 :                 pMeth->nLine1 = pMeth->nLine2 = nLine1;
     946             :                 // The method is for a start VALID
     947         872 :                 pMeth->bInvalid = false;
     948             :             }
     949             :             else
     950             :             {
     951           0 :                 eEndTok = NIL;
     952             :             }
     953             :         }
     954             :         // Skip up to END SUB/END FUNCTION
     955        1318 :         if( eEndTok != NIL )
     956             :         {
     957      100872 :             while( !aTok.IsEof() )
     958             :             {
     959       99996 :                 if( aTok.Next() == eEndTok )
     960             :                 {
     961         868 :                     pMeth->nLine2 = aTok.GetLine();
     962         868 :                     break;
     963             :                 }
     964             :             }
     965         872 :             if( aTok.IsEof() )
     966             :             {
     967           4 :                 pMeth->nLine2 = aTok.GetLine();
     968             :             }
     969             :         }
     970             :     }
     971         450 :     EndDefinitions( true );
     972         450 : }
     973             : 
     974             : // Broadcast of a hint to all Basics
     975             : 
     976        2044 : static void _SendHint( SbxObject* pObj, sal_uIntPtr nId, SbMethod* p )
     977             : {
     978             :     // Self a BASIC?
     979        2044 :     if( pObj->IsA( TYPE(StarBASIC) ) && pObj->IsBroadcaster() )
     980        1136 :         pObj->GetBroadcaster().Broadcast( SbxHint( nId, p ) );
     981             :     // Then ask for the subobjects
     982        2044 :     SbxArray* pObjs = pObj->GetObjects();
     983        3824 :     for( sal_uInt16 i = 0; i < pObjs->Count(); i++ )
     984             :     {
     985        1780 :         SbxVariable* pVar = pObjs->Get( i );
     986        1780 :         if( pVar->IsA( TYPE(SbxObject) ) )
     987        1780 :             _SendHint( PTR_CAST(SbxObject,pVar), nId, p );
     988             :     }
     989        2044 : }
     990             : 
     991         264 : static void SendHint( SbxObject* pObj, sal_uIntPtr nId, SbMethod* p )
     992             : {
     993         768 :     while( pObj->GetParent() )
     994         240 :         pObj = pObj->GetParent();
     995         264 :     _SendHint( pObj, nId, p );
     996         264 : }
     997             : 
     998             : // #57841 Clear Uno-Objects, which were helt in RTL functions,
     999             : // at the end of the program, so that nothing were helt.
    1000         752 : void ClearUnoObjectsInRTL_Impl_Rek( StarBASIC* pBasic )
    1001             : {
    1002             :     // delete the return value of CreateUnoService
    1003         752 :     static OUString aName("CreateUnoService");
    1004         752 :     SbxVariable* pVar = pBasic->GetRtl()->Find( aName, SbxCLASS_METHOD );
    1005         752 :     if( pVar )
    1006             :     {
    1007         752 :         pVar->SbxValue::Clear();
    1008             :     }
    1009             :     // delete the return value of CreateUnoDialog
    1010         752 :     static OUString aName2("CreateUnoDialog");
    1011         752 :     pVar = pBasic->GetRtl()->Find( aName2, SbxCLASS_METHOD );
    1012         752 :     if( pVar )
    1013             :     {
    1014         752 :         pVar->SbxValue::Clear();
    1015             :     }
    1016             :     // delete the return value of CDec
    1017         752 :     static OUString aName3("CDec");
    1018         752 :     pVar = pBasic->GetRtl()->Find( aName3, SbxCLASS_METHOD );
    1019         752 :     if( pVar )
    1020             :     {
    1021         752 :         pVar->SbxValue::Clear();
    1022             :     }
    1023             :     // delete return value of CreateObject
    1024         752 :     static OUString aName4("CreateObject");
    1025         752 :     pVar = pBasic->GetRtl()->Find( aName4, SbxCLASS_METHOD );
    1026         752 :     if( pVar )
    1027             :     {
    1028         752 :         pVar->SbxValue::Clear();
    1029             :     }
    1030             :     // Go over all Sub-Basics
    1031         752 :     SbxArray* pObjs = pBasic->GetObjects();
    1032         752 :     sal_uInt16 nCount = pObjs->Count();
    1033        1646 :     for( sal_uInt16 i = 0 ; i < nCount ; i++ )
    1034             :     {
    1035         894 :         SbxVariable* pObjVar = pObjs->Get( i );
    1036         894 :         StarBASIC* pSubBasic = PTR_CAST( StarBASIC, pObjVar );
    1037         894 :         if( pSubBasic )
    1038             :         {
    1039         558 :             ClearUnoObjectsInRTL_Impl_Rek( pSubBasic );
    1040             :         }
    1041             :     }
    1042         752 : }
    1043             : 
    1044         132 : void ClearUnoObjectsInRTL_Impl( StarBASIC* pBasic )
    1045             : {
    1046             :     // #67781 Delete return values of the Uno-methods
    1047         132 :     clearUnoMethods();
    1048         132 :     clearUnoServiceCtors();
    1049             : 
    1050         132 :     ClearUnoObjectsInRTL_Impl_Rek( pBasic );
    1051             : 
    1052             :     // Search for the topmost Basic
    1053         132 :     SbxObject* p = pBasic;
    1054         382 :     while( p->GetParent() )
    1055         118 :         p = p->GetParent();
    1056         132 :     if( static_cast<StarBASIC*>(p) != pBasic )
    1057          62 :         ClearUnoObjectsInRTL_Impl_Rek( static_cast<StarBASIC*>(p) );
    1058         132 : }
    1059             : 
    1060             : 
    1061         780 : void SbModule::SetVBACompat( bool bCompat )
    1062             : {
    1063         780 :     if( mbVBACompat != bCompat )
    1064             :     {
    1065         638 :         mbVBACompat = bCompat;
    1066             :         // initialize VBA document API
    1067         638 :         if( mbVBACompat ) try
    1068             :         {
    1069         330 :             StarBASIC* pBasic = static_cast< StarBASIC* >( GetParent() );
    1070         660 :             uno::Reference< lang::XMultiServiceFactory > xFactory( getDocumentModel( pBasic ), uno::UNO_QUERY_THROW );
    1071           0 :             xFactory->createInstance( "ooo.vba.VBAGlobals" );
    1072             :         }
    1073         330 :         catch( Exception& )
    1074             :         {
    1075             :         }
    1076             :     }
    1077         780 : }
    1078             : 
    1079             : // Run a Basic-subprogram
    1080        2734 : sal_uInt16 SbModule::Run( SbMethod* pMeth )
    1081             : {
    1082             :     SAL_INFO("basic","About to run " << OUStringToOString( pMeth->GetName(), RTL_TEXTENCODING_UTF8 ).getStr() << ", vba compatmode is " << mbVBACompat );
    1083             :     static sal_uInt16 nMaxCallLevel = 0;
    1084             : 
    1085        2734 :     sal_uInt16 nRes = 0;
    1086        2734 :     bool bDelInst = ( GetSbData()->pInst == NULL );
    1087        2734 :     bool bQuit = false;
    1088        2734 :     StarBASICRef xBasic;
    1089        5468 :     uno::Reference< frame::XModel > xModel;
    1090        5468 :     uno::Reference< script::vba::XVBACompatibility > xVBACompat;
    1091        2734 :     if( bDelInst )
    1092             :     {
    1093             :         // #32779: Hold Basic during the execution
    1094         132 :         xBasic = static_cast<StarBASIC*>( GetParent() );
    1095             : 
    1096         132 :         GetSbData()->pInst = new SbiInstance( static_cast<StarBASIC*>(GetParent()) );
    1097             : 
    1098             :         /*  If a VBA script in a document is started, get the VBA compatibility
    1099             :             interface from the document Basic library container, and notify all
    1100             :             VBA script listeners about the started script. */
    1101         132 :         if( mbVBACompat )
    1102             :         {
    1103          72 :             StarBASIC* pBasic = static_cast< StarBASIC* >( GetParent() );
    1104          72 :             if( pBasic && pBasic->IsDocBasic() ) try
    1105             :             {
    1106          50 :                 xModel.set( getDocumentModel( pBasic ), uno::UNO_SET_THROW );
    1107          50 :                 xVBACompat.set( getVBACompatibility( xModel ), uno::UNO_SET_THROW );
    1108          50 :                 xVBACompat->broadcastVBAScriptEvent( script::vba::VBAScriptEventId::SCRIPT_STARTED, GetName() );
    1109             :             }
    1110           0 :             catch(const uno::Exception& )
    1111             :             {
    1112             :             }
    1113             :         }
    1114             : 
    1115             :         // Launcher problem
    1116             :         // i80726 The Find below will genarate an error in Testtool so we reset it unless there was one before already
    1117         132 :         bool bWasError = SbxBase::GetError() != 0;
    1118         132 :         SbxVariable* pMSOMacroRuntimeLibVar = Find( "Launcher", SbxCLASS_OBJECT );
    1119         132 :         if ( !bWasError && (SbxBase::GetError() == SbxERR_PROC_UNDEFINED) )
    1120           0 :             SbxBase::ResetError();
    1121         132 :         if( pMSOMacroRuntimeLibVar )
    1122             :         {
    1123           0 :             StarBASIC* pMSOMacroRuntimeLib = PTR_CAST(StarBASIC,pMSOMacroRuntimeLibVar);
    1124           0 :             if( pMSOMacroRuntimeLib )
    1125             :             {
    1126           0 :                 SbxFlagBits nGblFlag = pMSOMacroRuntimeLib->GetFlags() & SBX_GBLSEARCH;
    1127           0 :                 pMSOMacroRuntimeLib->ResetFlag( SBX_GBLSEARCH );
    1128           0 :                 SbxVariable* pAppSymbol = pMSOMacroRuntimeLib->Find( "Application", SbxCLASS_METHOD );
    1129           0 :                 pMSOMacroRuntimeLib->SetFlag( nGblFlag );
    1130           0 :                 if( pAppSymbol )
    1131             :                 {
    1132           0 :                     pMSOMacroRuntimeLib->SetFlag( SBX_EXTSEARCH );      // Could have been disabled before
    1133           0 :                     GetSbData()->pMSOMacroRuntimLib = pMSOMacroRuntimeLib;
    1134             :                 }
    1135             :             }
    1136             :         }
    1137             : 
    1138         132 :         if( nMaxCallLevel == 0 )
    1139             :         {
    1140             : #ifdef UNX
    1141             :           struct rlimit rl;
    1142          16 :           getrlimit ( RLIMIT_STACK, &rl );
    1143             : #endif
    1144             : #if defined LINUX
    1145             :           // Empiric value, 900 = needed bytes/Basic call level
    1146             :           // for Linux including 10% safety margin
    1147          16 :           nMaxCallLevel = rl.rlim_cur / 900;
    1148             : #elif defined SOLARIS
    1149             :           // Empiric value, 1650 = needed bytes/Basic call level
    1150             :           // for Solaris including 10% safety margin
    1151             :           nMaxCallLevel = rl.rlim_cur / 1650;
    1152             : #elif defined WIN32
    1153             :           nMaxCallLevel = 5800;
    1154             : #else
    1155             :           nMaxCallLevel = MAXRECURSION;
    1156             : #endif
    1157             :         }
    1158             :     }
    1159             : 
    1160             :     // Recursion to deep?
    1161        2734 :     if( ++GetSbData()->pInst->nCallLvl <= nMaxCallLevel )
    1162             :     {
    1163             :         // Define a globale variable in all Mods
    1164        2734 :         GlobalRunInit( /* bBasicStart = */ bDelInst );
    1165             : 
    1166             :         // Appeared a compiler error? Then we don't launch
    1167        2734 :         if( !GetSbData()->bGlobalInitErr )
    1168             :         {
    1169        2734 :             if( bDelInst )
    1170             :             {
    1171         132 :                 SendHint( GetParent(), SBX_HINT_BASICSTART, pMeth );
    1172             : 
    1173             :                 // 1996-10-16: #31460 New concept for StepInto/Over/Out
    1174             :                 // For an explanation see runtime.cxx at SbiInstance::CalcBreakCallLevel()
    1175             :                 // Identify the BreakCallLevel
    1176         132 :                 GetSbData()->pInst->CalcBreakCallLevel( pMeth->GetDebugFlags() );
    1177             :             }
    1178             : 
    1179        2734 :             SbModule* pOldMod = GetSbData()->pMod;
    1180        2734 :             GetSbData()->pMod = this;
    1181        2734 :             SbiRuntime* pRt = new SbiRuntime( this, pMeth, pMeth->nStart );
    1182             : 
    1183        2734 :             pRt->pNext = GetSbData()->pInst->pRun;
    1184        2734 :             if( pRt->pNext )
    1185        2602 :                 pRt->pNext->block();
    1186        2734 :             GetSbData()->pInst->pRun = pRt;
    1187        2734 :             if ( mbVBACompat )
    1188             :             {
    1189        2032 :                 GetSbData()->pInst->EnableCompatibility( true );
    1190             :             }
    1191        2734 :             while( pRt->Step() ) {}
    1192        2734 :             if( pRt->pNext )
    1193        2602 :                 pRt->pNext->unblock();
    1194             : 
    1195             :             // #63710 It can happen by an another thread handling at events,
    1196             :             // that the show call returns to an dialog (by closing the
    1197             :             // dialog per UI), before a by an event triggered further call returned,
    1198             :             // which stands in Basic more top in the stack and that had been run on
    1199             :             // a  Basic-Breakpoint. Then would the instance below destroyed. And if the Basic,
    1200             :             // that stand still in the call, further runs, there is a GPF.
    1201             :             // Thus here had to be wait until the other call comes back.
    1202        2734 :             if( bDelInst )
    1203             :             {
    1204             :                 // Compare here with 1 instead of 0, because before nCallLvl--
    1205         264 :                 while( GetSbData()->pInst->nCallLvl != 1 )
    1206           0 :                     Application::Yield();
    1207             :             }
    1208             : 
    1209        2734 :             nRes = sal_True;
    1210        2734 :             GetSbData()->pInst->pRun = pRt->pNext;
    1211        2734 :             GetSbData()->pInst->nCallLvl--;          // Call-Level down again
    1212             : 
    1213             :             // Exist an higher-ranking runtime instance?
    1214             :             // Then take over SbDEBUG_BREAK, if set
    1215        2734 :             SbiRuntime* pRtNext = pRt->pNext;
    1216        2734 :             if( pRtNext && (pRt->GetDebugFlags() & SbDEBUG_BREAK) )
    1217           0 :                 pRtNext->SetDebugFlags( SbDEBUG_BREAK );
    1218             : 
    1219        2734 :             delete pRt;
    1220        2734 :             GetSbData()->pMod = pOldMod;
    1221        2734 :             if( bDelInst )
    1222             :             {
    1223             :                 // #57841 Clear Uno-Objects, which were helt in RTL functions,
    1224             :                 // at the end of the program, so that nothing were helt.
    1225         132 :                 ClearUnoObjectsInRTL_Impl( xBasic );
    1226             : 
    1227         132 :                 clearNativeObjectWrapperVector();
    1228             : 
    1229             :                 SAL_WARN_IF(GetSbData()->pInst->nCallLvl != 0,"basic","BASIC-Call-Level > 0");
    1230         132 :                 delete GetSbData()->pInst, GetSbData()->pInst = NULL, bDelInst = false;
    1231             : 
    1232             :                 // #i30690
    1233         132 :                 SolarMutexGuard aSolarGuard;
    1234         132 :                 SendHint( GetParent(), SBX_HINT_BASICSTOP, pMeth );
    1235             : 
    1236         132 :                 GlobalRunDeInit();
    1237             : 
    1238         132 :                 if( xVBACompat.is() )
    1239             :                 {
    1240             :                     // notify all VBA script listeners about the stopped script
    1241             :                     try
    1242             :                     {
    1243          50 :                         xVBACompat->broadcastVBAScriptEvent( script::vba::VBAScriptEventId::SCRIPT_STOPPED, GetName() );
    1244             :                     }
    1245           0 :                     catch(const uno::Exception& )
    1246             :                     {
    1247             :                     }
    1248             :                     // VBA always ensures screenupdating is enabled after completing
    1249          50 :                     ::basic::vba::lockControllersOfAllDocuments( xModel, false );
    1250          50 :                     ::basic::vba::enableContainerWindowsOfAllDocuments( xModel, true );
    1251         132 :                 }
    1252             : 
    1253             : #ifdef DBG_TRACE_BASIC
    1254             :                 dbg_DeInitTrace();
    1255             : #endif
    1256             :             }
    1257             :         }
    1258             :         else
    1259           0 :                GetSbData()->pInst->nCallLvl--;           // Call-Level down again
    1260             :     }
    1261             :     else
    1262             :     {
    1263           0 :         GetSbData()->pInst->nCallLvl--;          // Call-Level down again
    1264           0 :         StarBASIC::FatalError( SbERR_STACK_OVERFLOW );
    1265             :     }
    1266             : 
    1267        2734 :     StarBASIC* pBasic = PTR_CAST(StarBASIC,GetParent());
    1268        2734 :     if( bDelInst )
    1269             :     {
    1270             :        // #57841 Clear Uno-Objects, which were helt in RTL functions,
    1271             :        // the end of the program, so that nothing were helt.
    1272           0 :         ClearUnoObjectsInRTL_Impl( xBasic );
    1273             : 
    1274           0 :         delete GetSbData()->pInst;
    1275           0 :         GetSbData()->pInst = NULL;
    1276             :     }
    1277        2734 :     if ( pBasic && pBasic->IsDocBasic() && pBasic->IsQuitApplication() && !GetSbData()->pInst )
    1278           0 :             bQuit = true;
    1279        2734 :         if ( bQuit )
    1280             :     {
    1281           0 :         Application::PostUserEvent( LINK( &AsyncQuitHandler::instance(), AsyncQuitHandler, OnAsyncQuit ), NULL );
    1282             :     }
    1283             : 
    1284        5468 :     return nRes;
    1285             : }
    1286             : 
    1287             : // Execute of the init method of a module after the loading
    1288             : // or the compilation
    1289             : 
    1290         888 : void SbModule::RunInit()
    1291             : {
    1292         888 :     if( pImage
    1293         888 :      && !pImage->bInit
    1294        1674 :      && pImage->GetFlag( SBIMG_INITCODE ) )
    1295             :     {
    1296             :         // Set flag, so that RunInit get activ (Testtool)
    1297          74 :         GetSbData()->bRunInit = true;
    1298             : 
    1299          74 :         SbModule* pOldMod = GetSbData()->pMod;
    1300          74 :         GetSbData()->pMod = this;
    1301             :         // The init code starts always here
    1302          74 :         SbiRuntime* pRt = new SbiRuntime( this, NULL, 0 );
    1303             : 
    1304          74 :         pRt->pNext = GetSbData()->pInst->pRun;
    1305          74 :         GetSbData()->pInst->pRun = pRt;
    1306          74 :         while( pRt->Step() ) {}
    1307             : 
    1308          74 :         GetSbData()->pInst->pRun = pRt->pNext;
    1309          74 :         delete pRt;
    1310          74 :         GetSbData()->pMod = pOldMod;
    1311          74 :         pImage->bInit = true;
    1312          74 :         pImage->bFirstInit = false;
    1313             : 
    1314             :         // RunInit is not activ anymore
    1315          74 :         GetSbData()->bRunInit = false;
    1316             :     }
    1317         888 : }
    1318             : 
    1319             : // Delete with private/dim declared variables
    1320             : 
    1321          44 : void SbModule::AddVarName( const OUString& aName )
    1322             : {
    1323             :     // see if the name is added already
    1324          44 :     std::vector< OUString >::iterator it_end = mModuleVariableNames.end();
    1325         114 :     for ( std::vector< OUString >::iterator it = mModuleVariableNames.begin(); it != it_end; ++it )
    1326             :     {
    1327          70 :         if ( aName == *it )
    1328          44 :             return;
    1329             :     }
    1330          44 :     mModuleVariableNames.push_back( aName );
    1331             : }
    1332             : 
    1333         348 : void SbModule::RemoveVars()
    1334             : {
    1335         348 :     std::vector< OUString >::iterator it_end = mModuleVariableNames.end();
    1336         348 :     for ( std::vector< OUString >::iterator it = mModuleVariableNames.begin(); it != it_end; ++it )
    1337             :     {
    1338             :     // We don't want a Find being called in a derived class ( e.g.
    1339             :     // SbUserform because it could trigger say an initialise event
    1340             :     // which would cause basic to be re-run in the middle of the init ( and remember RemoveVars is called from compile and we don't want code to run as part of the compile )
    1341           0 :     SbxVariableRef p = SbModule::Find( *it, SbxCLASS_PROPERTY );
    1342           0 :     if( p.Is() )
    1343           0 :         Remove (p);
    1344           0 :     }
    1345         348 : }
    1346             : 
    1347           0 : void SbModule::ClearPrivateVars()
    1348             : {
    1349           0 :     for( sal_uInt16 i = 0 ; i < pProps->Count() ; i++ )
    1350             :     {
    1351           0 :         SbProperty* p = PTR_CAST(SbProperty,pProps->Get( i ) );
    1352           0 :         if( p )
    1353             :         {
    1354             :             // Delete not the arrays, only their content
    1355           0 :             if( p->GetType() & SbxARRAY )
    1356             :             {
    1357           0 :                 SbxArray* pArray = PTR_CAST(SbxArray,p->GetObject());
    1358           0 :                 if( pArray )
    1359             :                 {
    1360           0 :                     for( sal_uInt16 j = 0 ; j < pArray->Count() ; j++ )
    1361             :                     {
    1362           0 :                         SbxVariable* pj = PTR_CAST(SbxVariable,pArray->Get( j ));
    1363           0 :                         pj->SbxValue::Clear();
    1364             :                     }
    1365             :                 }
    1366             :             }
    1367             :             else
    1368             :             {
    1369           0 :                 p->SbxValue::Clear();
    1370             :             }
    1371             :         }
    1372             :     }
    1373           0 : }
    1374             : 
    1375         200 : void SbModule::implClearIfVarDependsOnDeletedBasic( SbxVariable* pVar, StarBASIC* pDeletedBasic )
    1376             : {
    1377         200 :     if( pVar->SbxValue::GetType() != SbxOBJECT || pVar->ISA( SbProcedureProperty ) )
    1378         376 :         return;
    1379             : 
    1380          24 :     SbxObject* pObj = PTR_CAST(SbxObject,pVar->GetObject());
    1381          24 :     if( pObj != NULL )
    1382             :     {
    1383           8 :         SbxObject* p = pObj;
    1384             : 
    1385           8 :         SbModule* pMod = PTR_CAST( SbModule, p );
    1386           8 :         if( pMod != NULL )
    1387           0 :             pMod->ClearVarsDependingOnDeletedBasic( pDeletedBasic );
    1388             : 
    1389          16 :         while( (p = p->GetParent()) != NULL )
    1390             :         {
    1391           0 :             StarBASIC* pBasic = PTR_CAST( StarBASIC, p );
    1392           0 :             if( pBasic != NULL && pBasic == pDeletedBasic )
    1393             :             {
    1394           0 :                 pVar->SbxValue::Clear();
    1395           0 :                 break;
    1396             :             }
    1397             :         }
    1398             :     }
    1399             : }
    1400             : 
    1401         364 : void SbModule::ClearVarsDependingOnDeletedBasic( StarBASIC* pDeletedBasic )
    1402             : {
    1403             :     (void)pDeletedBasic;
    1404             : 
    1405        1336 :     for( sal_uInt16 i = 0 ; i < pProps->Count() ; i++ )
    1406             :     {
    1407         972 :         SbProperty* p = PTR_CAST(SbProperty,pProps->Get( i ) );
    1408         972 :         if( p )
    1409             :         {
    1410         200 :             if( p->GetType() & SbxARRAY )
    1411             :             {
    1412           0 :                 SbxArray* pArray = PTR_CAST(SbxArray,p->GetObject());
    1413           0 :                 if( pArray )
    1414             :                 {
    1415           0 :                     for( sal_uInt16 j = 0 ; j < pArray->Count() ; j++ )
    1416             :                     {
    1417           0 :                         SbxVariable* pVar = PTR_CAST(SbxVariable,pArray->Get( j ));
    1418           0 :                         implClearIfVarDependsOnDeletedBasic( pVar, pDeletedBasic );
    1419             :                     }
    1420             :                 }
    1421             :             }
    1422             :             else
    1423             :             {
    1424         200 :                 implClearIfVarDependsOnDeletedBasic( p, pDeletedBasic );
    1425             :             }
    1426             :         }
    1427             :     }
    1428         364 : }
    1429             : 
    1430         268 : void StarBASIC::ClearAllModuleVars( void )
    1431             : {
    1432             :     // Initialise the own module
    1433         728 :     for ( sal_uInt16 nMod = 0; nMod < pModules->Count(); nMod++ )
    1434             :     {
    1435         460 :         SbModule* pModule = static_cast<SbModule*>(pModules->Get( nMod ));
    1436             :         // Initialise only, if the startcode was already executed
    1437         460 :         if( pModule->pImage && pModule->pImage->bInit && !pModule->isProxyModule() && !pModule->ISA(SbObjModule) )
    1438           0 :             pModule->ClearPrivateVars();
    1439             :     }
    1440             : 
    1441         268 : }
    1442             : 
    1443             : // Execution of the init-code of all module
    1444        2734 : void SbModule::GlobalRunInit( bool bBasicStart )
    1445             : {
    1446             :     // If no Basic-Start, only initialise, if the module is not initialised
    1447        2734 :     if( !bBasicStart )
    1448        2602 :         if( !(pImage && !pImage->bInit) )
    1449        5242 :             return;
    1450             : 
    1451             :     // Initialise GlobalInitErr-Flag for Compiler-Error
    1452             :     // With the help of this flags could be located in SbModule::Run() after the call of
    1453             :     // GlobalRunInit, if at the intialising of the module
    1454             :     // an error occurred. Then it will not be launched.
    1455         226 :     GetSbData()->bGlobalInitErr = false;
    1456             : 
    1457             :     // Parent of the module is a Basic
    1458         226 :     StarBASIC *pBasic = PTR_CAST(StarBASIC,GetParent());
    1459         226 :     if( pBasic )
    1460             :     {
    1461         226 :         pBasic->InitAllModules();
    1462             : 
    1463         226 :         SbxObject* pParent_ = pBasic->GetParent();
    1464         226 :         if( pParent_ )
    1465             :         {
    1466         158 :             StarBASIC * pParentBasic = PTR_CAST(StarBASIC,pParent_);
    1467         158 :             if( pParentBasic )
    1468             :             {
    1469         158 :                 pParentBasic->InitAllModules( pBasic );
    1470             : 
    1471             :                 // #109018 Parent can also have a parent (library in doc)
    1472         158 :                 SbxObject* pParentParent = pParentBasic->GetParent();
    1473         158 :                 if( pParentParent )
    1474             :                 {
    1475         148 :                     StarBASIC * pParentParentBasic = PTR_CAST(StarBASIC,pParentParent);
    1476         148 :                     if( pParentParentBasic )
    1477         148 :                         pParentParentBasic->InitAllModules( pParentBasic );
    1478             :                 }
    1479             :             }
    1480             :         }
    1481             :     }
    1482             : }
    1483             : 
    1484         132 : void SbModule::GlobalRunDeInit( void )
    1485             : {
    1486         132 :     StarBASIC *pBasic = PTR_CAST(StarBASIC,GetParent());
    1487         132 :     if( pBasic )
    1488             :     {
    1489         132 :         pBasic->DeInitAllModules();
    1490             : 
    1491         132 :         SbxObject* pParent_ = pBasic->GetParent();
    1492         132 :         if( pParent_ )
    1493          62 :             pBasic = PTR_CAST(StarBASIC,pParent_);
    1494         132 :         if( pBasic )
    1495         132 :             pBasic->DeInitAllModules();
    1496             :     }
    1497         132 : }
    1498             : 
    1499             : // Search for the next STMNT-Command in the code. This was used from the STMNT-
    1500             : // Opcode to set the endcolumn.
    1501             : 
    1502       23610 : const sal_uInt8* SbModule::FindNextStmnt( const sal_uInt8* p, sal_uInt16& nLine, sal_uInt16& nCol ) const
    1503             : {
    1504       23610 :     return FindNextStmnt( p, nLine, nCol, false );
    1505             : }
    1506             : 
    1507       23650 : const sal_uInt8* SbModule::FindNextStmnt( const sal_uInt8* p, sal_uInt16& nLine, sal_uInt16& nCol,
    1508             :     bool bFollowJumps, const SbiImage* pImg ) const
    1509             : {
    1510       23650 :     sal_uInt32 nPC = (sal_uInt32) ( p - (const sal_uInt8*) pImage->GetCode() );
    1511      153690 :     while( nPC < pImage->GetCodeSize() )
    1512             :     {
    1513      128774 :         SbiOpcode eOp = (SbiOpcode ) ( *p++ );
    1514      128774 :         nPC++;
    1515      128774 :         if( bFollowJumps && eOp == _JUMP && pImg )
    1516             :         {
    1517             :             SAL_WARN_IF( !pImg, "basic", "FindNextStmnt: pImg==NULL with FollowJumps option" );
    1518           0 :             sal_uInt32 nOp1 = *p++; nOp1 |= *p++ << 8;
    1519           0 :             nOp1 |= *p++ << 16; nOp1 |= *p++ << 24;
    1520           0 :             p = (const sal_uInt8*) pImg->GetCode() + nOp1;
    1521             :         }
    1522      128774 :         else if( eOp >= SbOP1_START && eOp <= SbOP1_END )
    1523       20640 :             p += 4, nPC += 4;
    1524      108134 :         else if( eOp == _STMNT )
    1525             :         {
    1526             :             sal_uInt32 nl, nc;
    1527       22384 :             nl = *p++; nl |= *p++ << 8;
    1528       22384 :             nl |= *p++ << 16 ; nl |= *p++ << 24;
    1529       22384 :             nc = *p++; nc |= *p++ << 8;
    1530       22384 :             nc |= *p++ << 16 ; nc |= *p++ << 24;
    1531       22384 :             nLine = (sal_uInt16)nl; nCol = (sal_uInt16)nc;
    1532       22384 :             return p;
    1533             :         }
    1534       85750 :         else if( eOp >= SbOP2_START && eOp <= SbOP2_END )
    1535       41994 :             p += 8, nPC += 8;
    1536       43756 :         else if( !( eOp >= SbOP0_START && eOp <= SbOP0_END ) )
    1537             :         {
    1538           0 :             StarBASIC::FatalError( SbERR_INTERNAL_ERROR );
    1539           0 :             break;
    1540             :         }
    1541             :     }
    1542        1266 :     return NULL;
    1543             : }
    1544             : 
    1545             : // Test, if a line contains STMNT-Opcodes
    1546             : 
    1547           0 : bool SbModule::IsBreakable( sal_uInt16 nLine ) const
    1548             : {
    1549           0 :     if( !pImage )
    1550           0 :         return false;
    1551           0 :     const sal_uInt8* p = (const sal_uInt8* ) pImage->GetCode();
    1552             :     sal_uInt16 nl, nc;
    1553           0 :     while( ( p = FindNextStmnt( p, nl, nc ) ) != NULL )
    1554           0 :         if( nl == nLine )
    1555           0 :             return true;
    1556           0 :     return false;
    1557             : }
    1558             : 
    1559           0 : bool SbModule::IsBP( sal_uInt16 nLine ) const
    1560             : {
    1561           0 :     if( pBreaks )
    1562             :     {
    1563           0 :         for( size_t i = 0; i < pBreaks->size(); i++ )
    1564             :         {
    1565           0 :             sal_uInt16 b = pBreaks->operator[]( i );
    1566           0 :             if( b == nLine )
    1567           0 :                 return true;
    1568           0 :             if( b < nLine )
    1569           0 :                 break;
    1570             :         }
    1571             :     }
    1572           0 :     return false;
    1573             : }
    1574             : 
    1575           0 : bool SbModule::SetBP( sal_uInt16 nLine )
    1576             : {
    1577           0 :     if( !IsBreakable( nLine ) )
    1578           0 :         return false;
    1579           0 :     if( !pBreaks )
    1580           0 :         pBreaks = new SbiBreakpoints;
    1581             :     size_t i;
    1582           0 :     for( i = 0; i < pBreaks->size(); i++ )
    1583             :     {
    1584           0 :         sal_uInt16 b = pBreaks->operator[]( i );
    1585           0 :         if( b == nLine )
    1586           0 :             return true;
    1587           0 :         if( b < nLine )
    1588           0 :             break;
    1589             :     }
    1590           0 :     pBreaks->insert( pBreaks->begin() + i, nLine );
    1591             : 
    1592             :     // #38568: Set during runtime as well here SbDEBUG_BREAK
    1593           0 :     if( GetSbData()->pInst && GetSbData()->pInst->pRun )
    1594           0 :         GetSbData()->pInst->pRun->SetDebugFlags( SbDEBUG_BREAK );
    1595             : 
    1596           0 :     return IsBreakable( nLine );
    1597             : }
    1598             : 
    1599           0 : bool SbModule::ClearBP( sal_uInt16 nLine )
    1600             : {
    1601           0 :     bool bRes = false;
    1602           0 :     if( pBreaks )
    1603             :     {
    1604           0 :         for( size_t i = 0; i < pBreaks->size(); i++ )
    1605             :         {
    1606           0 :             sal_uInt16 b = pBreaks->operator[]( i );
    1607           0 :             if( b == nLine )
    1608             :             {
    1609           0 :                 pBreaks->erase( pBreaks->begin() + i );
    1610           0 :                 bRes = true;
    1611           0 :                 break;
    1612             :             }
    1613           0 :             if( b < nLine )
    1614           0 :                 break;
    1615             :         }
    1616           0 :         if( pBreaks->empty() )
    1617           0 :             delete pBreaks, pBreaks = NULL;
    1618             :     }
    1619           0 :     return bRes;
    1620             : }
    1621             : 
    1622           0 : void SbModule::ClearAllBP()
    1623             : {
    1624           0 :     delete pBreaks;
    1625           0 :     pBreaks = NULL;
    1626           0 : }
    1627             : 
    1628             : void
    1629           0 : SbModule::fixUpMethodStart( bool bCvtToLegacy, SbiImage* pImg ) const
    1630             : {
    1631           0 :         if ( !pImg )
    1632           0 :             pImg = pImage;
    1633           0 :         for( sal_uInt32 i = 0; i < pMethods->Count(); i++ )
    1634             :         {
    1635           0 :             SbMethod* pMeth = PTR_CAST(SbMethod,pMethods->Get( (sal_uInt16)i ) );
    1636           0 :             if( pMeth )
    1637             :             {
    1638             :                 //fixup method start positions
    1639           0 :                 if ( bCvtToLegacy )
    1640           0 :                     pMeth->nStart = pImg->CalcLegacyOffset( pMeth->nStart );
    1641             :                 else
    1642           0 :                     pMeth->nStart = pImg->CalcNewOffset( (sal_uInt16)pMeth->nStart );
    1643             :             }
    1644             :         }
    1645             : 
    1646           0 : }
    1647             : 
    1648           0 : bool SbModule::LoadData( SvStream& rStrm, sal_uInt16 nVer )
    1649             : {
    1650           0 :     Clear();
    1651           0 :     if( !SbxObject::LoadData( rStrm, 1 ) )
    1652           0 :         return false;
    1653             :     // As a precaution...
    1654           0 :     SetFlag( SBX_EXTSEARCH | SBX_GBLSEARCH );
    1655             :     sal_uInt8 bImage;
    1656           0 :     rStrm.ReadUChar( bImage );
    1657           0 :     if( bImage )
    1658             :     {
    1659           0 :         SbiImage* p = new SbiImage;
    1660           0 :         sal_uInt32 nImgVer = 0;
    1661             : 
    1662           0 :         if( !p->Load( rStrm, nImgVer ) )
    1663             :         {
    1664           0 :             delete p;
    1665           0 :             return false;
    1666             :         }
    1667             :         // If the image is in old format, we fix up the method start offsets
    1668           0 :         if ( nImgVer < B_EXT_IMG_VERSION )
    1669             :         {
    1670           0 :             fixUpMethodStart( false, p );
    1671           0 :             p->ReleaseLegacyBuffer();
    1672             :         }
    1673           0 :         aComment = p->aComment;
    1674           0 :         SetName( p->aName );
    1675           0 :         if( p->GetCodeSize() )
    1676             :         {
    1677           0 :             aOUSource = p->aOUSource;
    1678             :             // Old version: image away
    1679           0 :             if( nVer == 1 )
    1680             :             {
    1681           0 :                 SetSource32( p->aOUSource );
    1682           0 :                 delete p;
    1683             :             }
    1684             :             else
    1685           0 :                 pImage = p;
    1686             :         }
    1687             :         else
    1688             :         {
    1689           0 :             SetSource32( p->aOUSource );
    1690           0 :             delete p;
    1691             :         }
    1692             :     }
    1693           0 :     return true;
    1694             : }
    1695             : 
    1696           0 : bool SbModule::StoreData( SvStream& rStrm ) const
    1697             : {
    1698           0 :     bool bFixup = ( pImage && !pImage->ExceedsLegacyLimits() );
    1699           0 :     if ( bFixup )
    1700           0 :         fixUpMethodStart( true );
    1701           0 :     bool bRet = SbxObject::StoreData( rStrm );
    1702           0 :     if ( !bRet )
    1703           0 :         return false;
    1704             : 
    1705           0 :     if( pImage )
    1706             :     {
    1707           0 :         pImage->aOUSource = aOUSource;
    1708           0 :         pImage->aComment = aComment;
    1709           0 :         pImage->aName = GetName();
    1710           0 :         rStrm.WriteUChar( 1 );
    1711             :         // # PCode is saved only for legacy formats only
    1712             :         // It should be noted that it probably isn't necessary
    1713             :         // It would be better not to store the image ( more flexible with
    1714             :         // formats )
    1715           0 :         bool bRes = pImage->Save( rStrm, B_LEGACYVERSION );
    1716           0 :         if ( bFixup )
    1717           0 :             fixUpMethodStart( false ); // restore method starts
    1718           0 :         return bRes;
    1719             : 
    1720             :     }
    1721             :     else
    1722             :     {
    1723           0 :         SbiImage aImg;
    1724           0 :         aImg.aOUSource = aOUSource;
    1725           0 :         aImg.aComment = aComment;
    1726           0 :         aImg.aName = GetName();
    1727           0 :         rStrm.WriteUChar( 1 );
    1728           0 :         return aImg.Save( rStrm );
    1729             :     }
    1730             : }
    1731             : 
    1732           0 : bool SbModule::ExceedsLegacyModuleSize()
    1733             : {
    1734           0 :     if ( !IsCompiled() )
    1735           0 :         Compile();
    1736           0 :     if ( pImage && pImage->ExceedsLegacyLimits() )
    1737           0 :         return true;
    1738           0 :     return false;
    1739             : }
    1740             : 
    1741             : class ErrorHdlResetter
    1742             : {
    1743             :     Link    mErrHandler;
    1744             :     bool    mbError;
    1745             : public:
    1746           0 :     ErrorHdlResetter() : mbError( false )
    1747             :     {
    1748             :         // save error handler
    1749           0 :         mErrHandler = StarBASIC::GetGlobalErrorHdl();
    1750             :         // set new error handler
    1751           0 :         StarBASIC::SetGlobalErrorHdl( LINK( this, ErrorHdlResetter, BasicErrorHdl ) );
    1752           0 :     }
    1753           0 :     ~ErrorHdlResetter()
    1754             :     {
    1755             :         // restore error handler
    1756           0 :         StarBASIC::SetGlobalErrorHdl(mErrHandler);
    1757           0 :     }
    1758             :     DECL_LINK( BasicErrorHdl, StarBASIC * );
    1759           0 :     bool HasError() { return mbError; }
    1760             : };
    1761             : 
    1762           0 : IMPL_LINK( ErrorHdlResetter, BasicErrorHdl, StarBASIC *, /*pBasic*/)
    1763             : {
    1764           0 :     mbError = true;
    1765           0 :     return 0;
    1766             : }
    1767             : 
    1768           0 : void SbModule::GetCodeCompleteDataFromParse(CodeCompleteDataCache& aCache)
    1769             : {
    1770           0 :     ErrorHdlResetter aErrHdl;
    1771           0 :     SbxBase::ResetError();
    1772             : 
    1773           0 :     boost::scoped_ptr<SbiParser> pParser(new SbiParser( static_cast<StarBASIC*>(GetParent()), this ));
    1774           0 :     pParser->SetCodeCompleting(true);
    1775             : 
    1776           0 :     while( pParser->Parse() ) {}
    1777           0 :     SbiSymPool* pPool = pParser->pPool;
    1778           0 :     aCache.Clear();
    1779           0 :     for( sal_uInt16 i = 0; i < pPool->GetSize(); ++i )
    1780             :     {
    1781           0 :         SbiSymDef* pSymDef = pPool->Get(i);
    1782             :         //std::cerr << "i: " << i << ", type: " << pSymDef->GetType() << "; name:" << pSymDef->GetName() << std::endl;
    1783           0 :         if( (pSymDef->GetType() != SbxEMPTY) || (pSymDef->GetType() != SbxNULL) )
    1784           0 :             aCache.InsertGlobalVar( pSymDef->GetName(), pParser->aGblStrings.Find(pSymDef->GetTypeId()) );
    1785             : 
    1786           0 :         SbiSymPool& pChildPool = pSymDef->GetPool();
    1787           0 :         for(sal_uInt16 j = 0; j < pChildPool.GetSize(); ++j )
    1788             :         {
    1789           0 :             SbiSymDef* pChildSymDef = pChildPool.Get(j);
    1790             :             //std::cerr << "j: " << j << ", type: " << pChildSymDef->GetType() << "; name:" << pChildSymDef->GetName() << std::endl;
    1791           0 :             if( (pChildSymDef->GetType() != SbxEMPTY) || (pChildSymDef->GetType() != SbxNULL) )
    1792           0 :                 aCache.InsertLocalVar( pSymDef->GetName(), pChildSymDef->GetName(), pParser->aGblStrings.Find(pChildSymDef->GetTypeId()) );
    1793             :         }
    1794           0 :     }
    1795           0 : }
    1796             : 
    1797             : 
    1798           0 : OUString SbModule::GetKeywordCase( const OUString& sKeyword ) const
    1799             : {
    1800           0 :     return SbiParser::GetKeywordCase( sKeyword );
    1801             : }
    1802             : 
    1803           0 : bool SbModule::HasExeCode()
    1804             : {
    1805             :     // And empty Image always has the Global Chain set up
    1806             :     static const unsigned char pEmptyImage[] = { 0x45, 0x0 , 0x0, 0x0, 0x0 };
    1807             :     // lets be stricter for the moment than VBA
    1808             : 
    1809           0 :     if (!IsCompiled())
    1810             :     {
    1811           0 :         ErrorHdlResetter aGblErrHdl;
    1812           0 :         Compile();
    1813           0 :         if (aGblErrHdl.HasError()) //assume unsafe on compile error
    1814           0 :             return true;
    1815             :     }
    1816             : 
    1817           0 :     bool bRes = false;
    1818           0 :     if (pImage && !(pImage->GetCodeSize() == 5 && (memcmp(pImage->GetCode(), pEmptyImage, pImage->GetCodeSize()) == 0 )))
    1819           0 :         bRes = true;
    1820             : 
    1821           0 :     return bRes;
    1822             : }
    1823             : 
    1824             : // Store only image, no source
    1825           0 : bool SbModule::StoreBinaryData( SvStream& rStrm )
    1826             : {
    1827           0 :     return StoreBinaryData( rStrm, 0 );
    1828             : }
    1829             : 
    1830           0 : bool SbModule::StoreBinaryData( SvStream& rStrm, sal_uInt16 nVer )
    1831             : {
    1832           0 :     bool bRet = Compile();
    1833           0 :     if( bRet )
    1834             :     {
    1835           0 :         bool bFixup = ( !nVer && !pImage->ExceedsLegacyLimits() );// save in old image format, fix up method starts
    1836             : 
    1837           0 :         if ( bFixup ) // save in old image format, fix up method starts
    1838           0 :             fixUpMethodStart( true );
    1839           0 :          bRet = SbxObject::StoreData( rStrm );
    1840           0 :         if( bRet )
    1841             :         {
    1842           0 :             pImage->aOUSource = OUString();
    1843           0 :             pImage->aComment = aComment;
    1844           0 :             pImage->aName = GetName();
    1845             : 
    1846           0 :             rStrm.WriteUChar( 1 );
    1847           0 :                     if ( nVer )
    1848           0 :                         bRet = pImage->Save( rStrm, B_EXT_IMG_VERSION );
    1849             :                     else
    1850           0 :                         bRet = pImage->Save( rStrm, B_LEGACYVERSION );
    1851           0 :                     if ( bFixup )
    1852           0 :                         fixUpMethodStart( false ); // restore method starts
    1853             : 
    1854           0 :             pImage->aOUSource = aOUSource;
    1855             :         }
    1856             :     }
    1857           0 :     return bRet;
    1858             : }
    1859             : 
    1860             : // Called for >= OO 1.0 passwd protected libraries only
    1861             : 
    1862           0 : bool SbModule::LoadBinaryData( SvStream& rStrm )
    1863             : {
    1864           0 :     OUString aKeepSource = aOUSource;
    1865           0 :     bool bRet = LoadData( rStrm, 2 );
    1866           0 :     LoadCompleted();
    1867           0 :     aOUSource = aKeepSource;
    1868           0 :     return bRet;
    1869             : }
    1870             : 
    1871           0 : bool SbModule::LoadCompleted()
    1872             : {
    1873           0 :     SbxArray* p = GetMethods();
    1874             :     sal_uInt16 i;
    1875           0 :     for( i = 0; i < p->Count(); i++ )
    1876             :     {
    1877           0 :         SbMethod* q = PTR_CAST(SbMethod,p->Get( i ) );
    1878           0 :         if( q )
    1879           0 :             q->pMod = this;
    1880             :     }
    1881           0 :     p = GetProperties();
    1882           0 :     for( i = 0; i < p->Count(); i++ )
    1883             :     {
    1884           0 :         SbProperty* q = PTR_CAST(SbProperty,p->Get( i ) );
    1885           0 :         if( q )
    1886           0 :             q->pMod = this;
    1887             :     }
    1888           0 :     return true;
    1889             : }
    1890             : 
    1891          90 : void SbModule::handleProcedureProperties( SfxBroadcaster& rBC, const SfxHint& rHint )
    1892             : {
    1893          90 :     bool bDone = false;
    1894             : 
    1895          90 :     const SbxHint* pHint = dynamic_cast<const SbxHint*>(&rHint);
    1896          90 :     if( pHint )
    1897             :     {
    1898          90 :         SbxVariable* pVar = pHint->GetVar();
    1899          90 :         SbProcedureProperty* pProcProperty = PTR_CAST( SbProcedureProperty, pVar );
    1900          90 :         if( pProcProperty )
    1901             :         {
    1902           0 :             bDone = true;
    1903             : 
    1904           0 :             if( pHint->GetId() == SBX_HINT_DATAWANTED )
    1905             :             {
    1906           0 :                 OUString aProcName("Property Get ");
    1907           0 :                 aProcName += pProcProperty->GetName();
    1908             : 
    1909           0 :                 SbxVariable* pMeth = Find( aProcName, SbxCLASS_METHOD );
    1910           0 :                 if( pMeth )
    1911             :                 {
    1912           0 :                     SbxValues aVals;
    1913           0 :                     aVals.eType = SbxVARIANT;
    1914             : 
    1915           0 :                     SbxArray* pArg = pVar->GetParameters();
    1916           0 :                     sal_uInt16 nVarParCount = (pArg != NULL) ? pArg->Count() : 0;
    1917           0 :                     if( nVarParCount > 1 )
    1918             :                     {
    1919           0 :                         SbxArrayRef xMethParameters = new SbxArray;
    1920           0 :                         xMethParameters->Put( pMeth, 0 );   // Method as parameter 0
    1921           0 :                         for( sal_uInt16 i = 1 ; i < nVarParCount ; ++i )
    1922             :                         {
    1923           0 :                             SbxVariable* pPar = pArg->Get( i );
    1924           0 :                             xMethParameters->Put( pPar, i );
    1925             :                         }
    1926             : 
    1927           0 :                         pMeth->SetParameters( xMethParameters );
    1928           0 :                         pMeth->Get( aVals );
    1929           0 :                         pMeth->SetParameters( NULL );
    1930             :                     }
    1931             :                     else
    1932             :                     {
    1933           0 :                         pMeth->Get( aVals );
    1934             :                     }
    1935             : 
    1936           0 :                     pVar->Put( aVals );
    1937           0 :                 }
    1938             :             }
    1939           0 :             else if( pHint->GetId() == SBX_HINT_DATACHANGED )
    1940             :             {
    1941           0 :                 SbxVariable* pMeth = NULL;
    1942             : 
    1943           0 :                 bool bSet = pProcProperty->isSet();
    1944           0 :                 if( bSet )
    1945             :                 {
    1946           0 :                     pProcProperty->setSet( false );
    1947             : 
    1948           0 :                     OUString aProcName("Property Set " );
    1949           0 :                     aProcName += pProcProperty->GetName();
    1950           0 :                     pMeth = Find( aProcName, SbxCLASS_METHOD );
    1951             :                 }
    1952           0 :                 if( !pMeth )    // Let
    1953             :                 {
    1954           0 :                     OUString aProcName("Property Let " );
    1955           0 :                     aProcName += pProcProperty->GetName();
    1956           0 :                     pMeth = Find( aProcName, SbxCLASS_METHOD );
    1957             :                 }
    1958             : 
    1959           0 :                 if( pMeth )
    1960             :                 {
    1961             :                     // Setup parameters
    1962           0 :                     SbxArrayRef xArray = new SbxArray;
    1963           0 :                     xArray->Put( pMeth, 0 );    // Method as parameter 0
    1964           0 :                     xArray->Put( pVar, 1 );
    1965           0 :                     pMeth->SetParameters( xArray );
    1966             : 
    1967           0 :                     SbxValues aVals;
    1968           0 :                     pMeth->Get( aVals );
    1969           0 :                     pMeth->SetParameters( NULL );
    1970             :                 }
    1971             :             }
    1972             :         }
    1973             :     }
    1974             : 
    1975          90 :     if( !bDone )
    1976          90 :         SbModule::Notify( rBC, rHint );
    1977          90 : }
    1978             : 
    1979             : 
    1980             : // Implementation SbJScriptModule (Basic module for JavaScript source code)
    1981           0 : SbJScriptModule::SbJScriptModule( const OUString& rName )
    1982           0 :     :SbModule( rName )
    1983             : {
    1984           0 : }
    1985             : 
    1986           0 : bool SbJScriptModule::LoadData( SvStream& rStrm, sal_uInt16 nVer )
    1987             : {
    1988             :     (void)nVer;
    1989             : 
    1990           0 :     Clear();
    1991           0 :     if( !SbxObject::LoadData( rStrm, 1 ) )
    1992           0 :         return false;
    1993             : 
    1994             :     // Get the source string
    1995           0 :     aOUSource = rStrm.ReadUniOrByteString( osl_getThreadTextEncoding() );
    1996           0 :     return true;
    1997             : }
    1998             : 
    1999           0 : bool SbJScriptModule::StoreData( SvStream& rStrm ) const
    2000             : {
    2001           0 :     if( !SbxObject::StoreData( rStrm ) )
    2002           0 :         return false;
    2003             : 
    2004             :     // Write the source string
    2005           0 :     OUString aTmp = aOUSource;
    2006           0 :     rStrm.WriteUniOrByteString( aTmp, osl_getThreadTextEncoding() );
    2007           0 :     return true;
    2008             : }
    2009             : 
    2010             : 
    2011             : 
    2012             : 
    2013         896 : SbMethod::SbMethod( const OUString& r, SbxDataType t, SbModule* p )
    2014         896 :         : SbxMethod( r, t ), pMod( p )
    2015             : {
    2016         896 :     bInvalid     = true;
    2017             :     nStart       =
    2018             :     nDebugFlags  =
    2019             :     nLine1       =
    2020         896 :     nLine2       = 0;
    2021         896 :     refStatics = new SbxArray;
    2022         896 :     mCaller          = 0;
    2023             :     // HACK due to 'Referenz could not be saved'
    2024         896 :     SetFlag( SBX_NO_MODIFY );
    2025         896 : }
    2026             : 
    2027        2734 : SbMethod::SbMethod( const SbMethod& r )
    2028        2734 :     : SvRefBase( r ), SbxMethod( r )
    2029             : {
    2030        2734 :     pMod         = r.pMod;
    2031        2734 :     bInvalid     = r.bInvalid;
    2032        2734 :     nStart       = r.nStart;
    2033        2734 :     nDebugFlags  = r.nDebugFlags;
    2034        2734 :     nLine1       = r.nLine1;
    2035        2734 :     nLine2       = r.nLine2;
    2036        2734 :         refStatics = r.refStatics;
    2037        2734 :     mCaller          = r.mCaller;
    2038        2734 :     SetFlag( SBX_NO_MODIFY );
    2039        2734 : }
    2040             : 
    2041        7228 : SbMethod::~SbMethod()
    2042             : {
    2043        7228 : }
    2044             : 
    2045         818 : void SbMethod::ClearStatics()
    2046             : {
    2047         818 :     refStatics = new SbxArray;
    2048             : 
    2049         818 : }
    2050           0 : SbxArray* SbMethod::GetStatics()
    2051             : {
    2052           0 :     return refStatics;
    2053             : }
    2054             : 
    2055           0 : bool SbMethod::LoadData( SvStream& rStrm, sal_uInt16 nVer )
    2056             : {
    2057           0 :     if( !SbxMethod::LoadData( rStrm, 1 ) )
    2058           0 :         return false;
    2059             :     sal_Int16 n;
    2060           0 :     rStrm.ReadInt16( n );
    2061           0 :     sal_Int16 nTempStart = (sal_Int16)nStart;
    2062           0 :     if( nVer == 2 )
    2063           0 :         rStrm.ReadUInt16( nLine1 ).ReadUInt16( nLine2 ).ReadInt16( nTempStart ).ReadCharAsBool( bInvalid );
    2064             :     // HACK ue to 'Referenz could not be saved'
    2065           0 :     SetFlag( SBX_NO_MODIFY );
    2066           0 :     nStart = nTempStart;
    2067           0 :     return true;
    2068             : }
    2069             : 
    2070           0 : bool SbMethod::StoreData( SvStream& rStrm ) const
    2071             : {
    2072           0 :     if( !SbxMethod::StoreData( rStrm ) )
    2073           0 :         return false;
    2074           0 :     rStrm.WriteInt16(  nDebugFlags )
    2075           0 :          .WriteInt16(  nLine1 )
    2076           0 :          .WriteInt16(  nLine2 )
    2077           0 :          .WriteInt16(  nStart )
    2078           0 :          .WriteUChar(  bInvalid );
    2079           0 :     return true;
    2080             : }
    2081             : 
    2082           0 : void SbMethod::GetLineRange( sal_uInt16& l1, sal_uInt16& l2 )
    2083             : {
    2084           0 :     l1 = nLine1; l2 = nLine2;
    2085           0 : }
    2086             : 
    2087             : // Could later be deleted
    2088             : 
    2089        3864 : SbxInfo* SbMethod::GetInfo()
    2090             : {
    2091        3864 :     return pInfo;
    2092             : }
    2093             : 
    2094             : // Interface to execute a method of the applications
    2095             : // With special RefCounting, so that the Basic was not fired of by CloseDocument()
    2096             : // The return value will be delivered as string.
    2097         154 : ErrCode SbMethod::Call( SbxValue* pRet, SbxVariable* pCaller )
    2098             : {
    2099         154 :     if ( pCaller )
    2100             :     {
    2101             :         SAL_INFO("basic", "SbMethod::Call Have been passed a caller 0x" << pCaller );
    2102           2 :         mCaller = pCaller;
    2103             :     }
    2104             :     // RefCount vom Modul hochzaehlen
    2105         154 :     SbModule* pMod_ = static_cast<SbModule*>(GetParent());
    2106         154 :     pMod_->AddFirstRef();
    2107             : 
    2108             :     // Increment the RefCount of the Basic
    2109         154 :     StarBASIC* pBasic = static_cast<StarBASIC*>(pMod_->GetParent());
    2110         154 :     pBasic->AddFirstRef();
    2111             : 
    2112             :     // Establish the values to get the return value
    2113         154 :     SbxValues aVals;
    2114         154 :     aVals.eType = SbxVARIANT;
    2115             : 
    2116             :     // #104083: Compile BEFORE get
    2117         154 :     if( bInvalid && !pMod_->Compile() )
    2118           0 :         StarBASIC::Error( SbERR_BAD_PROP_VALUE );
    2119             : 
    2120         154 :     Get( aVals );
    2121         154 :     if ( pRet )
    2122         154 :         pRet->Put( aVals );
    2123             : 
    2124             :     // Was there an error
    2125         154 :     ErrCode nErr = SbxBase::GetError();
    2126         154 :     SbxBase::ResetError();
    2127             : 
    2128             :     // Release objects
    2129         154 :     pMod_->ReleaseRef();
    2130         154 :     pBasic->ReleaseRef();
    2131         154 :     mCaller = 0;
    2132         154 :     return nErr;
    2133             : }
    2134             : 
    2135             : 
    2136             : // #100883 Own Broadcast for SbMethod
    2137        9646 : void SbMethod::Broadcast( sal_uIntPtr nHintId )
    2138             : {
    2139        9646 :     if( pCst && !IsSet( SBX_NO_BROADCAST ) )
    2140             :     {
    2141             :         // Because the method could be called from outside, test here once again
    2142             :         // the authorisation
    2143        2734 :         if( nHintId & SBX_HINT_DATAWANTED )
    2144        2734 :             if( !CanRead() )
    2145           0 :                 return;
    2146        2734 :         if( nHintId & SBX_HINT_DATACHANGED )
    2147           0 :             if( !CanWrite() )
    2148           0 :                 return;
    2149             : 
    2150        2734 :         if( pMod && !pMod->IsCompiled() )
    2151           0 :             pMod->Compile();
    2152             : 
    2153             :         // Block broadcasts while creating new method
    2154        2734 :         SfxBroadcaster* pSave = pCst;
    2155        2734 :         pCst = NULL;
    2156        2734 :         SbMethod* pThisCopy = new SbMethod( *this );
    2157        2734 :         SbMethodRef xHolder = pThisCopy;
    2158        2734 :         if( mpPar.Is() )
    2159             :         {
    2160             :             // Enregister this as element 0, but don't reset the parent!
    2161        2244 :             switch( GetType() ) {
    2162             :             case SbxEMPTY:
    2163             :             case SbxVOID:
    2164        1404 :                 break;
    2165             :             default:
    2166         840 :                 mpPar->PutDirect( pThisCopy, 0 );
    2167         840 :                 break;
    2168             :             }
    2169        2244 :             SetParameters( NULL );
    2170             :         }
    2171             : 
    2172        2734 :         pCst = pSave;
    2173        2734 :         pSave->Broadcast( SbxHint( nHintId, pThisCopy ) );
    2174             : 
    2175        2734 :         SbxFlagBits nSaveFlags = GetFlags();
    2176        2734 :         SetFlag( SBX_READWRITE );
    2177        2734 :         pCst = NULL;
    2178        2734 :         Put( pThisCopy->GetValues_Impl() );
    2179        2734 :         pCst = pSave;
    2180        2734 :         SetFlags( nSaveFlags );
    2181             :     }
    2182             : }
    2183             : 
    2184             : 
    2185             : // Implementation of SbJScriptMethod (method class as a wrapper for JavaScript-functions)
    2186             : 
    2187           0 : SbJScriptMethod::SbJScriptMethod( const OUString& r, SbxDataType t, SbModule* p )
    2188           0 :         : SbMethod( r, t, p )
    2189             : {
    2190           0 : }
    2191             : 
    2192           0 : SbJScriptMethod::~SbJScriptMethod()
    2193           0 : {}
    2194             : 
    2195             : 
    2196         252 : SbObjModule::SbObjModule( const OUString& rName, const com::sun::star::script::ModuleInfo& mInfo, bool bIsVbaCompatible )
    2197         252 :     : SbModule( rName, bIsVbaCompatible )
    2198             : {
    2199         252 :     SetModuleType( mInfo.ModuleType );
    2200         252 :     if ( mInfo.ModuleType == script::ModuleType::FORM )
    2201             :     {
    2202           4 :         SetClassName( "Form" );
    2203             :     }
    2204         248 :     else if ( mInfo.ModuleObject.is() )
    2205             :     {
    2206         208 :         SetUnoObject( uno::makeAny( mInfo.ModuleObject ) );
    2207             :     }
    2208         252 : }
    2209             : 
    2210         500 : SbObjModule::~SbObjModule()
    2211             : {
    2212         500 : }
    2213             : 
    2214             : void
    2215         208 : SbObjModule::SetUnoObject( const uno::Any& aObj ) throw ( uno::RuntimeException )
    2216             : {
    2217         208 :     SbUnoObject* pUnoObj = PTR_CAST(SbUnoObject,(SbxVariable*)pDocObject);
    2218         208 :     if ( pUnoObj && pUnoObj->getUnoAny() == aObj ) // object is equal, nothing to do
    2219         208 :         return;
    2220         208 :     pDocObject = new SbUnoObject( GetName(), uno::makeAny( aObj ) );
    2221             : 
    2222         208 :     com::sun::star::uno::Reference< com::sun::star::lang::XServiceInfo > xServiceInfo( aObj, com::sun::star::uno::UNO_QUERY_THROW );
    2223         208 :     if( xServiceInfo->supportsService( "ooo.vba.excel.Worksheet" ) )
    2224             :     {
    2225         156 :         SetClassName( "Worksheet" );
    2226             :     }
    2227          52 :     else if( xServiceInfo->supportsService( "ooo.vba.excel.Workbook" ) )
    2228             :     {
    2229          50 :         SetClassName( "Workbook" );
    2230         208 :     }
    2231             : }
    2232             : 
    2233             : SbxVariable*
    2234          88 : SbObjModule::GetObject()
    2235             : {
    2236          88 :     return pDocObject;
    2237             : }
    2238             : SbxVariable*
    2239         384 : SbObjModule::Find( const OUString& rName, SbxClassType t )
    2240             : {
    2241         384 :     SbxVariable* pVar = NULL;
    2242         384 :     if ( pDocObject)
    2243         384 :         pVar = pDocObject->Find( rName, t );
    2244         384 :     if ( !pVar )
    2245          14 :         pVar = SbModule::Find( rName, t );
    2246         384 :     return pVar;
    2247             : }
    2248             : 
    2249          90 : void SbObjModule::SFX_NOTIFY( SfxBroadcaster& rBC, const TypeId& rBCType,
    2250             :                          const SfxHint& rHint, const TypeId& rHintType )
    2251             : {
    2252          90 :     SbModule::handleProcedureProperties( rBC, rHint );
    2253          90 : }
    2254             : 
    2255             : 
    2256             : typedef ::cppu::WeakImplHelper3<
    2257             :     awt::XTopWindowListener,
    2258             :     awt::XWindowListener,
    2259             :     document::XEventListener > FormObjEventListener_BASE;
    2260             : 
    2261             : class FormObjEventListenerImpl:
    2262             :     public FormObjEventListener_BASE, private boost::noncopyable
    2263             : {
    2264             :     SbUserFormModule* mpUserForm;
    2265             :     uno::Reference< lang::XComponent > mxComponent;
    2266             :     uno::Reference< frame::XModel > mxModel;
    2267             :     bool mbDisposed;
    2268             :     bool mbOpened;
    2269             :     bool mbActivated;
    2270             :     bool mbShowing;
    2271             : 
    2272             : public:
    2273           4 :     FormObjEventListenerImpl( SbUserFormModule* pUserForm, const uno::Reference< lang::XComponent >& xComponent, const uno::Reference< frame::XModel >& xModel ) :
    2274             :         mpUserForm( pUserForm ), mxComponent( xComponent), mxModel( xModel ),
    2275           4 :         mbDisposed( false ), mbOpened( false ), mbActivated( false ), mbShowing( false )
    2276             :     {
    2277           4 :         if ( mxComponent.is() )
    2278             :         {
    2279             :             SAL_INFO("basic", "*********** Registering the listeners");
    2280             :             try
    2281             :             {
    2282           4 :                 uno::Reference< awt::XTopWindow >( mxComponent, uno::UNO_QUERY_THROW )->addTopWindowListener( this );
    2283             :             }
    2284           0 :             catch(const uno::Exception& ) {}
    2285             :             try
    2286             :             {
    2287           4 :                 uno::Reference< awt::XWindow >( mxComponent, uno::UNO_QUERY_THROW )->addWindowListener( this );
    2288             :             }
    2289           0 :             catch(const uno::Exception& ) {}
    2290             :         }
    2291             : 
    2292           4 :         if ( mxModel.is() )
    2293             :         {
    2294             :             try
    2295             :             {
    2296           4 :                 uno::Reference< document::XEventBroadcaster >( mxModel, uno::UNO_QUERY_THROW )->addEventListener( this );
    2297             :             }
    2298           0 :             catch(const uno::Exception& ) {}
    2299             :         }
    2300           4 :     }
    2301             : 
    2302           8 :     virtual ~FormObjEventListenerImpl()
    2303           8 :     {
    2304           4 :         removeListener();
    2305           8 :     }
    2306             : 
    2307           0 :     bool isShowing() const { return mbShowing; }
    2308             : 
    2309           8 :     void removeListener()
    2310             :     {
    2311           8 :         if ( mxComponent.is() && !mbDisposed )
    2312             :         {
    2313             :             SAL_INFO("basic", "*********** Removing the listeners");
    2314             :             try
    2315             :             {
    2316           4 :                 uno::Reference< awt::XTopWindow >( mxComponent, uno::UNO_QUERY_THROW )->removeTopWindowListener( this );
    2317             :             }
    2318           0 :             catch(const uno::Exception& ) {}
    2319             :             try
    2320             :             {
    2321           4 :                 uno::Reference< awt::XWindow >( mxComponent, uno::UNO_QUERY_THROW )->removeWindowListener( this );
    2322             :             }
    2323           0 :             catch(const uno::Exception& ) {}
    2324             :         }
    2325           8 :         mxComponent.clear();
    2326             : 
    2327           8 :         if ( mxModel.is() && !mbDisposed )
    2328             :         {
    2329             :             try
    2330             :             {
    2331           4 :                 uno::Reference< document::XEventBroadcaster >( mxModel, uno::UNO_QUERY_THROW )->removeEventListener( this );
    2332             :             }
    2333           0 :             catch(const uno::Exception& ) {}
    2334             :         }
    2335           8 :         mxModel.clear();
    2336           8 :     }
    2337             : 
    2338           0 :     virtual void SAL_CALL windowOpened( const lang::EventObject& /*e*/ ) throw (uno::RuntimeException, std::exception) SAL_OVERRIDE
    2339             :     {
    2340           0 :         if ( mpUserForm )
    2341             :         {
    2342           0 :             mbOpened = true;
    2343           0 :             mbShowing = true;
    2344           0 :             if ( mbActivated )
    2345             :             {
    2346           0 :                 mbOpened = mbActivated = false;
    2347           0 :                 mpUserForm->triggerActivateEvent();
    2348             :             }
    2349             :         }
    2350           0 :     }
    2351             : 
    2352             : 
    2353           0 :     virtual void SAL_CALL windowClosing( const lang::EventObject& /*e*/ ) throw (uno::RuntimeException, std::exception) SAL_OVERRIDE
    2354             :     {
    2355             : #ifdef IN_THE_FUTURE
    2356             :         uno::Reference< awt::XDialog > xDialog( e.Source, uno::UNO_QUERY );
    2357             :         if ( xDialog.is() )
    2358             :         {
    2359             :             uno::Reference< awt::XControl > xControl( xDialog, uno::UNO_QUERY );
    2360             :             if ( xControl->getPeer().is() )
    2361             :             {
    2362             :                 uno::Reference< document::XVbaMethodParameter > xVbaMethodParameter( xControl->getPeer(), uno::UNO_QUERY );
    2363             :                 if ( xVbaMethodParameter.is() )
    2364             :                 {
    2365             :                     sal_Int8 nCancel = 0;
    2366             :                     sal_Int8 nCloseMode = ::ooo::vba::VbQueryClose::vbFormControlMenu;
    2367             : 
    2368             :                     Sequence< Any > aParams;
    2369             :                     aParams.realloc(2);
    2370             :                     aParams[0] <<= nCancel;
    2371             :                     aParams[1] <<= nCloseMode;
    2372             : 
    2373             :                     mpUserForm->triggerMethod( "Userform_QueryClose", aParams);
    2374             :                     return;
    2375             : 
    2376             :                 }
    2377             :             }
    2378             :         }
    2379             : 
    2380             :         mpUserForm->triggerMethod( "Userform_QueryClose" );
    2381             : #endif
    2382           0 :     }
    2383             : 
    2384             : 
    2385           0 :     virtual void SAL_CALL windowClosed( const lang::EventObject& /*e*/ ) throw (uno::RuntimeException, std::exception) SAL_OVERRIDE
    2386             :     {
    2387           0 :         mbOpened = false;
    2388           0 :         mbShowing = false;
    2389           0 :     }
    2390             : 
    2391           0 :     virtual void SAL_CALL windowMinimized( const lang::EventObject& /*e*/ ) throw (uno::RuntimeException, std::exception) SAL_OVERRIDE
    2392             :     {
    2393           0 :     }
    2394             : 
    2395           0 :     virtual void SAL_CALL windowNormalized( const lang::EventObject& /*e*/ ) throw (uno::RuntimeException, std::exception) SAL_OVERRIDE
    2396             :     {
    2397           0 :     }
    2398             : 
    2399           0 :     virtual void SAL_CALL windowActivated( const lang::EventObject& /*e*/ ) throw (uno::RuntimeException, std::exception) SAL_OVERRIDE
    2400             :     {
    2401           0 :         if ( mpUserForm )
    2402             :         {
    2403           0 :             mbActivated = true;
    2404           0 :             if ( mbOpened )
    2405             :             {
    2406           0 :                 mbOpened = mbActivated = false;
    2407           0 :                 mpUserForm->triggerActivateEvent();
    2408             :             }
    2409             :         }
    2410           0 :     }
    2411             : 
    2412           0 :     virtual void SAL_CALL windowDeactivated( const lang::EventObject& /*e*/ ) throw (uno::RuntimeException, std::exception) SAL_OVERRIDE
    2413             :     {
    2414           0 :         if ( mpUserForm )
    2415           0 :             mpUserForm->triggerDeactivateEvent();
    2416           0 :     }
    2417             : 
    2418           0 :     virtual void SAL_CALL windowResized( const awt::WindowEvent& /*e*/ ) throw (uno::RuntimeException, std::exception) SAL_OVERRIDE
    2419             :     {
    2420           0 :         if ( mpUserForm )
    2421             :         {
    2422           0 :             mpUserForm->triggerResizeEvent();
    2423           0 :             mpUserForm->triggerLayoutEvent();
    2424             :         }
    2425           0 :     }
    2426             : 
    2427           0 :     virtual void SAL_CALL windowMoved( const awt::WindowEvent& /*e*/ ) throw (uno::RuntimeException, std::exception) SAL_OVERRIDE
    2428             :     {
    2429           0 :         if ( mpUserForm )
    2430           0 :             mpUserForm->triggerLayoutEvent();
    2431           0 :     }
    2432             : 
    2433           0 :     virtual void SAL_CALL windowShown( const lang::EventObject& /*e*/ ) throw (uno::RuntimeException, std::exception) SAL_OVERRIDE
    2434             :     {
    2435           0 :     }
    2436             : 
    2437           0 :     virtual void SAL_CALL windowHidden( const lang::EventObject& /*e*/ ) throw (uno::RuntimeException, std::exception) SAL_OVERRIDE
    2438             :     {
    2439           0 :     }
    2440             : 
    2441          12 :     virtual void SAL_CALL notifyEvent( const document::EventObject& rEvent ) throw (uno::RuntimeException, std::exception) SAL_OVERRIDE
    2442             :     {
    2443             :         // early dosposing on document event "OnUnload", to be sure Basic still exists when calling VBA "UserForm_Terminate"
    2444          12 :         if( rEvent.EventName == GlobalEventConfig::GetEventName( STR_EVENT_CLOSEDOC ) )
    2445             :         {
    2446           4 :             removeListener();
    2447           4 :             mbDisposed = true;
    2448           4 :             if ( mpUserForm )
    2449           4 :                 mpUserForm->ResetApiObj();   // will trigger "UserForm_Terminate"
    2450             :         }
    2451          12 :     }
    2452             : 
    2453           0 :     virtual void SAL_CALL disposing( const lang::EventObject& /*Source*/ ) throw (uno::RuntimeException, std::exception) SAL_OVERRIDE
    2454             :     {
    2455             :         SAL_INFO("basic", "** Userform/Dialog disposing");
    2456           0 :         removeListener();
    2457           0 :         mbDisposed = true;
    2458           0 :         if ( mpUserForm )
    2459           0 :             mpUserForm->ResetApiObj( false );   // pass false (too late to trigger VBA events here)
    2460           0 :     }
    2461             : };
    2462             : 
    2463           4 : SbUserFormModule::SbUserFormModule( const OUString& rName, const com::sun::star::script::ModuleInfo& mInfo, bool bIsCompat )
    2464             :     : SbObjModule( rName, mInfo, bIsCompat )
    2465             :     , m_mInfo( mInfo )
    2466           4 :     , mbInit( false )
    2467             : {
    2468           4 :     m_xModel.set( mInfo.ModuleObject, uno::UNO_QUERY_THROW );
    2469           4 : }
    2470             : 
    2471           8 : SbUserFormModule::~SbUserFormModule()
    2472             : {
    2473           8 : }
    2474             : 
    2475           4 : void SbUserFormModule::ResetApiObj(  bool bTriggerTerminateEvent )
    2476             : {
    2477             :     SAL_INFO("basic", " SbUserFormModule::ResetApiObj( " << (bTriggerTerminateEvent ? "true )" : "false )") );
    2478           4 :     if ( bTriggerTerminateEvent && m_xDialog.is() ) // probably someone close the dialog window
    2479             :     {
    2480           4 :         triggerTerminateEvent();
    2481             :     }
    2482           4 :     pDocObject = NULL;
    2483           4 :     m_xDialog = NULL;
    2484           4 : }
    2485             : 
    2486           8 : void SbUserFormModule::triggerMethod( const OUString& aMethodToRun )
    2487             : {
    2488           8 :     Sequence< Any > aArguments;
    2489           8 :     triggerMethod( aMethodToRun, aArguments );
    2490           8 : }
    2491             : 
    2492           8 : void SbUserFormModule::triggerMethod( const OUString& aMethodToRun, Sequence< Any >& aArguments )
    2493             : {
    2494             :     SAL_INFO("basic", "*** trigger " << OUStringToOString( aMethodToRun, RTL_TEXTENCODING_UTF8 ).getStr() << " ***");
    2495             :     // Search method
    2496           8 :     SbxVariable* pMeth = SbObjModule::Find( aMethodToRun, SbxCLASS_METHOD );
    2497           8 :     if( pMeth )
    2498             :     {
    2499           0 :         if ( aArguments.getLength() > 0 )   // Setup parameters
    2500             :         {
    2501           0 :             SbxArrayRef xArray = new SbxArray;
    2502           0 :             xArray->Put( pMeth, 0 );    // Method as parameter 0
    2503             : 
    2504           0 :             for ( sal_Int32 i = 0; i < aArguments.getLength(); ++i )
    2505             :             {
    2506           0 :                 SbxVariableRef xSbxVar = new SbxVariable( SbxVARIANT );
    2507           0 :                 unoToSbxValue( static_cast< SbxVariable* >( xSbxVar ), aArguments[i] );
    2508           0 :                 xArray->Put( xSbxVar, static_cast< sal_uInt16 >( i ) + 1 );
    2509             : 
    2510             :                 // Enable passing by ref
    2511           0 :                 if ( xSbxVar->GetType() != SbxVARIANT )
    2512           0 :                     xSbxVar->SetFlag( SBX_FIXED );
    2513           0 :             }
    2514           0 :             pMeth->SetParameters( xArray );
    2515             : 
    2516           0 :             SbxValues aVals;
    2517           0 :             pMeth->Get( aVals );
    2518             : 
    2519           0 :             for ( sal_Int32 i = 0; i < aArguments.getLength(); ++i )
    2520             :             {
    2521           0 :                 aArguments[i] = sbxToUnoValue( xArray->Get( static_cast< sal_uInt16 >(i) + 1) );
    2522             :             }
    2523           0 :             pMeth->SetParameters( NULL );
    2524             :         }
    2525             :         else
    2526             :         {
    2527           0 :             SbxValues aVals;
    2528           0 :             pMeth->Get( aVals );
    2529             :         }
    2530             :     }
    2531           8 : }
    2532             : 
    2533           0 : void SbUserFormModule::triggerActivateEvent( void )
    2534             : {
    2535             :     SAL_INFO("basic", "**** entering SbUserFormModule::triggerActivate");
    2536           0 :     triggerMethod( "UserForm_Activate" );
    2537             :     SAL_INFO("basic", "**** leaving SbUserFormModule::triggerActivate");
    2538           0 : }
    2539             : 
    2540           0 : void SbUserFormModule::triggerDeactivateEvent( void )
    2541             : {
    2542             :     SAL_INFO("basic", "**** SbUserFormModule::triggerDeactivate");
    2543           0 :     triggerMethod( "Userform_Deactivate" );
    2544           0 : }
    2545             : 
    2546           4 : void SbUserFormModule::triggerInitializeEvent( void )
    2547             : {
    2548           4 :     if ( mbInit )
    2549           4 :         return;
    2550             :     SAL_INFO("basic", "**** SbUserFormModule::triggerInitializeEvent");
    2551           4 :     static OUString aInitMethodName( "Userform_Initialize");
    2552           4 :     triggerMethod( aInitMethodName );
    2553           4 :     mbInit = true;
    2554             : }
    2555             : 
    2556           4 : void SbUserFormModule::triggerTerminateEvent( void )
    2557             : {
    2558             :     SAL_INFO("basic", "**** SbUserFormModule::triggerTerminateEvent");
    2559           4 :     static OUString aTermMethodName( "Userform_Terminate" );
    2560           4 :     triggerMethod( aTermMethodName );
    2561           4 :     mbInit=false;
    2562           4 : }
    2563             : 
    2564           0 : void SbUserFormModule::triggerLayoutEvent( void )
    2565             : {
    2566           0 :     static OUString aMethodName( "Userform_Layout" );
    2567           0 :     triggerMethod( aMethodName );
    2568           0 : }
    2569             : 
    2570           0 : void SbUserFormModule::triggerResizeEvent( void )
    2571             : {
    2572           0 :     static OUString aMethodName("Userform_Resize");
    2573           0 :     triggerMethod( aMethodName );
    2574           0 : }
    2575             : 
    2576           0 : SbUserFormModuleInstance* SbUserFormModule::CreateInstance()
    2577             : {
    2578           0 :     SbUserFormModuleInstance* pInstance = new SbUserFormModuleInstance( this, GetName(), m_mInfo, IsVBACompat() );
    2579           0 :     return pInstance;
    2580             : }
    2581             : 
    2582           0 : SbUserFormModuleInstance::SbUserFormModuleInstance( SbUserFormModule* pParentModule,
    2583             :     const OUString& rName, const com::sun::star::script::ModuleInfo& mInfo, bool bIsVBACompat )
    2584             :         : SbUserFormModule( rName, mInfo, bIsVBACompat )
    2585           0 :         , m_pParentModule( pParentModule )
    2586             : {
    2587           0 : }
    2588             : 
    2589           0 : bool SbUserFormModuleInstance::IsClass( const OUString& rName ) const
    2590             : {
    2591           0 :     bool bParentNameMatches = m_pParentModule->GetName().equalsIgnoreAsciiCase( rName );
    2592           0 :     bool bRet = bParentNameMatches || SbxObject::IsClass( rName );
    2593           0 :     return bRet;
    2594             : }
    2595             : 
    2596           0 : SbxVariable* SbUserFormModuleInstance::Find( const OUString& rName, SbxClassType t )
    2597             : {
    2598           0 :     SbxVariable* pVar = m_pParentModule->Find( rName, t );
    2599           0 :     return pVar;
    2600             : }
    2601             : 
    2602             : 
    2603           0 : void SbUserFormModule::Load()
    2604             : {
    2605             :     SAL_INFO("basic", "** load() ");
    2606             :     // forces a load
    2607           0 :     if ( !pDocObject )
    2608           0 :         InitObject();
    2609           0 : }
    2610             : 
    2611             : 
    2612           0 : void SbUserFormModule::Unload()
    2613             : {
    2614             :     SAL_INFO("basic", "** Unload() ");
    2615             : 
    2616           0 :     sal_Int8 nCancel = 0;
    2617           0 :     sal_Int8 nCloseMode = ::ooo::vba::VbQueryClose::vbFormCode;
    2618             : 
    2619           0 :     Sequence< Any > aParams;
    2620           0 :     aParams.realloc(2);
    2621           0 :     aParams[0] <<= nCancel;
    2622           0 :     aParams[1] <<= nCloseMode;
    2623             : 
    2624           0 :     triggerMethod( "Userform_QueryClose", aParams);
    2625             : 
    2626           0 :     aParams[0] >>= nCancel;
    2627             :     // basic boolean ( and what the user might use ) can be ambiguous ( e.g. basic true = -1 )
    2628             :     // test against 0 ( false ) and assume anything else is true
    2629             :     // ( Note: ) this used to work ( something changes somewhere )
    2630           0 :     if (nCancel != 0)
    2631             :     {
    2632           0 :         return;
    2633             :     }
    2634             : 
    2635           0 :     if ( m_xDialog.is() )
    2636             :     {
    2637           0 :         triggerTerminateEvent();
    2638             :     }
    2639             :     // Search method
    2640           0 :     SbxVariable* pMeth = SbObjModule::Find( "UnloadObject", SbxCLASS_METHOD );
    2641           0 :     if( pMeth )
    2642             :     {
    2643             :         SAL_INFO("basic", "Attempting too run the UnloadObjectMethod");
    2644           0 :         m_xDialog.clear(); //release ref to the uno object
    2645           0 :         SbxValues aVals;
    2646           0 :         bool bWaitForDispose = true; // assume dialog is showing
    2647           0 :         if ( m_DialogListener.get() )
    2648             :         {
    2649           0 :             bWaitForDispose = m_DialogListener->isShowing();
    2650             :             SAL_INFO("basic", "Showing " << bWaitForDispose );
    2651             :         }
    2652           0 :         pMeth->Get( aVals);
    2653           0 :         if ( !bWaitForDispose )
    2654             :         {
    2655             :             // we've either already got a dispose or we'er never going to get one
    2656           0 :             ResetApiObj();
    2657             :         } // else wait for dispose
    2658             :         SAL_INFO("basic", "UnloadObject completed ( we hope )");
    2659           0 :     }
    2660             : }
    2661             : 
    2662             : 
    2663           4 : void SbUserFormModule::InitObject()
    2664             : {
    2665             :     try
    2666             :     {
    2667           4 :         OUString aHook("VBAGlobals");
    2668           4 :         SbUnoObject* pGlobs = static_cast<SbUnoObject*>(GetParent()->Find( aHook, SbxCLASS_DONTCARE ));
    2669           4 :         if ( m_xModel.is() && pGlobs )
    2670             :         {
    2671             :             // broadcast INITIALIZE_USERFORM script event before the dialog is created
    2672           4 :             Reference< script::vba::XVBACompatibility > xVBACompat( getVBACompatibility( m_xModel ), uno::UNO_SET_THROW );
    2673           4 :             xVBACompat->broadcastVBAScriptEvent( script::vba::VBAScriptEventId::INITIALIZE_USERFORM, GetName() );
    2674           8 :             uno::Reference< lang::XMultiServiceFactory > xVBAFactory( pGlobs->getUnoAny(), uno::UNO_QUERY_THROW );
    2675           8 :             uno::Reference< uno::XComponentContext > xContext = comphelper::getProcessComponentContext();
    2676           8 :             OUString sDialogUrl( "vnd.sun.star.script:"  );
    2677           8 :             OUString sProjectName( "Standard" );
    2678             : 
    2679             :             try
    2680             :             {
    2681           4 :                 Reference< beans::XPropertySet > xProps( m_xModel, UNO_QUERY_THROW );
    2682           8 :                 uno::Reference< script::vba::XVBACompatibility > xVBAMode( xProps->getPropertyValue( "BasicLibraries" ), uno::UNO_QUERY_THROW );
    2683           8 :                 sProjectName = xVBAMode->getProjectName();
    2684             :             }
    2685           0 :             catch(const Exception& ) {}
    2686             : 
    2687           4 :             sDialogUrl = sDialogUrl + sProjectName + "." + GetName() + "?location=document";
    2688             : 
    2689           8 :             uno::Reference< awt::XDialogProvider > xProvider = awt::DialogProvider::createWithModel( xContext, m_xModel  );
    2690           4 :             m_xDialog = xProvider->createDialog( sDialogUrl );
    2691             : 
    2692             :             // create vba api object
    2693           8 :             uno::Sequence< uno::Any > aArgs(4);
    2694           4 :             aArgs[ 0 ] = uno::Any();
    2695           4 :             aArgs[ 1 ] <<= m_xDialog;
    2696           4 :             aArgs[ 2 ] <<= m_xModel;
    2697           4 :             aArgs[ 3 ] <<= OUString( GetParent()->GetName() );
    2698           4 :             pDocObject = new SbUnoObject( GetName(), uno::makeAny( xVBAFactory->createInstanceWithArguments( "ooo.vba.msforms.UserForm", aArgs  ) ) );
    2699             : 
    2700           8 :             uno::Reference< lang::XComponent > xComponent( m_xDialog, uno::UNO_QUERY_THROW );
    2701             : 
    2702             :             // the dialog must be disposed at the end!
    2703           4 :             StarBASIC* pParentBasic = NULL;
    2704           4 :             SbxObject* pCurObject = this;
    2705           4 :             do
    2706             :             {
    2707           4 :                 SbxObject* pObjParent = pCurObject->GetParent();
    2708           4 :                 pParentBasic = PTR_CAST( StarBASIC, pObjParent );
    2709           4 :                 pCurObject = pObjParent;
    2710             :             }
    2711           0 :             while( pParentBasic == NULL && pCurObject != NULL );
    2712             : 
    2713             :             SAL_WARN_IF( pParentBasic == NULL, "basic", "pParentBasic == NULL" );
    2714           4 :             registerComponentToBeDisposedForBasic( xComponent, pParentBasic );
    2715             : 
    2716             :             // if old listener object exists, remove it from dialog and document model
    2717           4 :             if( m_DialogListener.is() )
    2718           0 :                 m_DialogListener->removeListener();
    2719           4 :             m_DialogListener.set( new FormObjEventListenerImpl( this, xComponent, m_xModel ) );
    2720             : 
    2721           8 :             triggerInitializeEvent();
    2722           4 :         }
    2723             :     }
    2724           0 :     catch(const uno::Exception& )
    2725             :     {
    2726             :     }
    2727             : 
    2728           4 : }
    2729             : 
    2730             : SbxVariable*
    2731         108 : SbUserFormModule::Find( const OUString& rName, SbxClassType t )
    2732             : {
    2733         108 :     if ( !pDocObject && !GetSbData()->bRunInit && GetSbData()->pInst )
    2734           4 :         InitObject();
    2735         108 :     return SbObjModule::Find( rName, t );
    2736             : }
    2737             : 
    2738         260 : SbProperty::SbProperty( const OUString& r, SbxDataType t, SbModule* p )
    2739         260 :         : SbxProperty( r, t ), pMod( p )
    2740             : {
    2741         260 :     bInvalid = false;
    2742         260 : }
    2743             : 
    2744         520 : SbProperty::~SbProperty()
    2745         520 : {}
    2746             : 
    2747             : 
    2748           0 : SbProcedureProperty::~SbProcedureProperty()
    2749        1203 : {}
    2750             : 
    2751             : /* vim:set shiftwidth=4 softtabstop=4 expandtab: */

Generated by: LCOV version 1.10