summaryrefslogtreecommitdiff
path: root/bridges/source/remote/static
diff options
context:
space:
mode:
Diffstat (limited to 'bridges/source/remote/static')
-rw-r--r--bridges/source/remote/static/helper.cxx212
-rw-r--r--bridges/source/remote/static/makefile.mk61
-rw-r--r--bridges/source/remote/static/mapping.cxx221
-rw-r--r--bridges/source/remote/static/proxy.cxx341
-rw-r--r--bridges/source/remote/static/remote.cxx164
-rw-r--r--bridges/source/remote/static/remote_types.cxx99
-rw-r--r--bridges/source/remote/static/remote_types.hxx92
-rw-r--r--bridges/source/remote/static/stub.cxx339
8 files changed, 1529 insertions, 0 deletions
diff --git a/bridges/source/remote/static/helper.cxx b/bridges/source/remote/static/helper.cxx
new file mode 100644
index 000000000000..d120d38b80df
--- /dev/null
+++ b/bridges/source/remote/static/helper.cxx
@@ -0,0 +1,212 @@
+/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
+/*************************************************************************
+ *
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * Copyright 2000, 2010 Oracle and/or its affiliates.
+ *
+ * OpenOffice.org - a multi-platform office productivity suite
+ *
+ * This file is part of OpenOffice.org.
+ *
+ * OpenOffice.org is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU Lesser General Public License version 3
+ * only, as published by the Free Software Foundation.
+ *
+ * OpenOffice.org is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU Lesser General Public License version 3 for more details
+ * (a copy is included in the LICENSE file that accompanied this code).
+ *
+ * You should have received a copy of the GNU Lesser General Public License
+ * version 3 along with OpenOffice.org. If not, see
+ * <http://www.openoffice.org/license.html>
+ * for a copy of the LGPLv3 License.
+ *
+ ************************************************************************/
+
+// MARKER(update_precomp.py): autogen include statement, do not remove
+#include "precompiled_bridges.hxx"
+#include <rtl/alloc.h>
+#include <osl/diagnose.h>
+
+#include <bridges/remote/helper.hxx>
+
+#include <bridges/remote/stub.hxx>
+#include <bridges/remote/proxy.hxx>
+#include <bridges/remote/remote.hxx>
+
+#include <com/sun/star/uno/Sequence.hxx>
+
+using namespace ::rtl;
+using namespace ::com::sun::star::uno;
+
+namespace bridges_remote
+{
+
+void SAL_CALL remote_createStub (
+ remote_Interface **ppRemoteI,
+ rtl_uString *pOid ,
+ typelib_TypeDescriptionReference *pTypeRef,
+ uno_Environment *pEnvRemote,
+ ReleaseRemoteCallbackFunc releaseRemoteCallback )
+{
+ typelib_TypeDescription *pType = 0;
+ typelib_typedescriptionreference_getDescription( &pType, pTypeRef );
+
+ (void) pEnvRemote->pExtEnv->getRegisteredInterface(
+ pEnvRemote->pExtEnv,
+ (void **)ppRemoteI,
+ pOid,
+ (typelib_InterfaceTypeDescription* )pType );
+
+ if( *ppRemoteI )
+ {
+ if( (*ppRemoteI)->acquire == acquireRemote2RemoteStub ) {
+
+ if( releaseRemoteCallback )
+ {
+ // use the callback handler, the bridge wants to send the call immeadiatly
+ releaseRemoteCallback( *ppRemoteI , pOid, pTypeRef , pEnvRemote );
+ }
+ else
+ {
+ ((::bridges_remote::Remote2RemoteStub *)*ppRemoteI)->releaseRemote();
+ }
+ }
+ else
+ {
+ // Uno2RemoteStub
+ // no release necessary
+ }
+ }
+ else
+ {
+ remote_BridgeImpl *pImpl = ((remote_Context *)pEnvRemote->pContext)->m_pBridgeImpl;
+ *ppRemoteI =
+ new ::bridges_remote::Remote2RemoteStub(
+ pOid,
+ (typelib_InterfaceTypeDescription * ) pType,
+ pEnvRemote,
+ pImpl->m_sendRequest);
+
+ // ppRemoteI may change during registration
+ pEnvRemote->pExtEnv->registerProxyInterface(
+ pEnvRemote->pExtEnv,
+ (void **) ppRemoteI,
+ freeRemote2RemoteStub,
+ pOid,
+ (typelib_InterfaceTypeDescription * ) pType );
+ }
+
+ typelib_typedescription_release( pType );
+}
+
+void SAL_CALL remote_sendQueryInterface(
+ uno_Environment *pEnvRemote,
+ remote_Interface **ppRemoteI,
+ rtl_uString *pOid ,
+ typelib_TypeDescriptionReference *pTypeRef,
+ uno_Any **ppException
+ )
+{
+ OSL_ASSERT( ppRemoteI );
+
+ typelib_InterfaceTypeDescription *pType = 0;
+ typelib_typedescriptionreference_getDescription( (typelib_TypeDescription ** )&pType, pTypeRef );
+
+ if( *ppRemoteI )
+ {
+ (*ppRemoteI)->release( *ppRemoteI );
+ (*ppRemoteI) = 0;
+ }
+
+ remote_BridgeImpl *pImpl = ((remote_Context *)pEnvRemote->pContext)->m_pBridgeImpl;
+
+ Type type = ::getCppuType( (Reference < XInterface > *)0 );
+
+ // get type for queryInterface
+ OUString sCompleteMethodName = type.getTypeName();
+ sCompleteMethodName += OUString(RTL_CONSTASCII_USTRINGPARAM("::queryInterface"));
+
+ typelib_InterfaceMemberTypeDescription *pMemberType = 0;
+ typelib_typedescription_getByName(
+ (typelib_TypeDescription **) &pMemberType,
+ sCompleteMethodName.pData );
+
+ OSL_ASSERT( pMemberType );
+
+ uno_Any anyInterface;
+ anyInterface.pType = 0;
+ anyInterface.pData = 0;
+
+ void *pReturn = &anyInterface;
+ void *ppArgs[1];
+
+ ppArgs[0] = 0;
+ typelib_TypeDescriptionReference *pRef = 0;
+ typelib_typedescriptionreference_new( &pRef ,
+ pType->aBase.eTypeClass,
+ pType->aBase.pTypeName);
+
+ ppArgs[0] = &pRef;
+
+// uno_Any anyException;
+// uno_Any *pAnyException = &anyException;
+
+ // do the queryInterface
+ pImpl->m_sendRequest(
+ pEnvRemote,
+ (typelib_TypeDescription * ) pMemberType,
+ pOid,
+ pType,
+ pReturn,
+ ppArgs,
+ ppException );
+
+
+ // now release everything
+ typelib_typedescriptionreference_release( pRef );
+ typelib_typedescription_release( (typelib_TypeDescription * ) pMemberType );
+
+ if( *ppException )
+ {
+ *ppRemoteI = 0;
+ }
+ else
+ {
+ // set out parameter
+ if( typelib_TypeClass_INTERFACE == anyInterface.pType->eTypeClass )
+ {
+ *ppRemoteI = ( remote_Interface * ) anyInterface.pReserved;
+ }
+ typelib_typedescriptionreference_release( anyInterface.pType );
+ }
+
+ typelib_typedescription_release( (typelib_TypeDescription * ) pType );
+}
+
+
+void SAL_CALL remote_retrieveOidFromProxy(
+ remote_Interface *pRemoteI,
+ rtl_uString **ppOid )
+{
+ if( pRemoteI->acquire == acquireRemote2RemoteStub )
+ {
+ // Remote2RemoteStub
+ ::bridges_remote::Remote2RemoteStub *pStub = (::bridges_remote::Remote2RemoteStub * ) pRemoteI;
+ rtl_uString_newFromString( ppOid , pStub->m_sOid.pData );
+ }
+ else
+ {
+ // Uno2RemoteStub
+ ::bridges_remote::Uno2RemoteStub *pStub = (::bridges_remote::Uno2RemoteStub * ) pRemoteI;
+ rtl_uString_newFromString( ppOid , pStub->m_sOid.pData );
+ pRemoteI->acquire( pRemoteI );
+ }
+}
+
+}
+
+/* vim:set shiftwidth=4 softtabstop=4 expandtab: */
diff --git a/bridges/source/remote/static/makefile.mk b/bridges/source/remote/static/makefile.mk
new file mode 100644
index 000000000000..9b3c2b795f8d
--- /dev/null
+++ b/bridges/source/remote/static/makefile.mk
@@ -0,0 +1,61 @@
+#*************************************************************************
+#
+# DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+#
+# Copyright 2000, 2010 Oracle and/or its affiliates.
+#
+# OpenOffice.org - a multi-platform office productivity suite
+#
+# This file is part of OpenOffice.org.
+#
+# OpenOffice.org is free software: you can redistribute it and/or modify
+# it under the terms of the GNU Lesser General Public License version 3
+# only, as published by the Free Software Foundation.
+#
+# OpenOffice.org is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU Lesser General Public License version 3 for more details
+# (a copy is included in the LICENSE file that accompanied this code).
+#
+# You should have received a copy of the GNU Lesser General Public License
+# version 3 along with OpenOffice.org. If not, see
+# <http://www.openoffice.org/license.html>
+# for a copy of the LGPLv3 License.
+#
+#*************************************************************************
+
+PRJ=..$/..$/..
+
+PRJNAME=bridges
+TARGET=bridges_remote_static
+ENABLE_EXCEPTIONS=TRUE
+USE_DEFFILE=TRUE
+
+# --- Settings -----------------------------------------------------
+
+.INCLUDE : settings.mk
+
+# ------------------------------------------------------------------
+
+SLOFILES= \
+ $(SLO)$/proxy.obj \
+ $(SLO)$/stub.obj \
+ $(SLO)$/remote.obj \
+ $(SLO)$/mapping.obj \
+ $(SLO)$/helper.obj \
+ $(SLO)$/remote_types.obj
+
+# Forte6 update 1 on Solaris Intel dies with internal compiler error
+# on stub.cxx if optimization is on. Switch it off for now.
+# To be reevaluated on compiler upgrade
+.IF "$(OS)$(CPU)"=="SOLARISI"
+NOOPTFILES=\
+ $(SLO)$/stub.obj
+.ENDIF
+
+# --- Targets ------------------------------------------------------
+
+.INCLUDE : target.mk
+
+
diff --git a/bridges/source/remote/static/mapping.cxx b/bridges/source/remote/static/mapping.cxx
new file mode 100644
index 000000000000..cd0201cbb87c
--- /dev/null
+++ b/bridges/source/remote/static/mapping.cxx
@@ -0,0 +1,221 @@
+/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
+/*************************************************************************
+ *
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * Copyright 2000, 2010 Oracle and/or its affiliates.
+ *
+ * OpenOffice.org - a multi-platform office productivity suite
+ *
+ * This file is part of OpenOffice.org.
+ *
+ * OpenOffice.org is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU Lesser General Public License version 3
+ * only, as published by the Free Software Foundation.
+ *
+ * OpenOffice.org is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU Lesser General Public License version 3 for more details
+ * (a copy is included in the LICENSE file that accompanied this code).
+ *
+ * You should have received a copy of the GNU Lesser General Public License
+ * version 3 along with OpenOffice.org. If not, see
+ * <http://www.openoffice.org/license.html>
+ * for a copy of the LGPLv3 License.
+ *
+ ************************************************************************/
+
+// MARKER(update_precomp.py): autogen include statement, do not remove
+#include "precompiled_bridges.hxx"
+#include <osl/diagnose.h>
+
+#include <bridges/remote/proxy.hxx>
+#include <bridges/remote/stub.hxx>
+#include <bridges/remote/counter.hxx>
+#include <bridges/remote/mapping.hxx>
+
+using namespace bridges_remote;
+
+extern "C" {
+
+static void SAL_CALL thisAcquire( uno_Mapping *pMap )
+{
+ RemoteMapping *p = SAL_REINTERPRET_CAST( RemoteMapping * , pMap );
+ if( 1 == osl_incrementInterlockedCount( &(p->m_nRef) ) )
+ {
+ if( remoteToUno == pMap->mapInterface )
+ {
+ uno_registerMapping( &pMap ,
+ freeRemoteMapping,
+ p->pEnvRemote ,
+ p->pEnvUno ,
+ p->m_sPurpose.pData );
+ }
+ else
+ {
+ uno_registerMapping( &pMap ,
+ freeRemoteMapping,
+ p->pEnvUno ,
+ p->pEnvRemote ,
+ p->m_sPurpose.pData );
+ }
+
+ }
+}
+
+static void SAL_CALL thisRelease( uno_Mapping *pMap )
+{
+ RemoteMapping *p = SAL_REINTERPRET_CAST( RemoteMapping * , pMap );
+ if (! osl_decrementInterlockedCount( &(p->m_nRef) ))
+ {
+ uno_revokeMapping( pMap );
+ }
+}
+
+}
+
+namespace bridges_remote {
+
+void remoteToUno( uno_Mapping *pMapping, void **ppUnoI, void *pRemoteI,
+ typelib_InterfaceTypeDescription *pTypeDescr )
+{
+ remote_Mapping *pRemoteMapping = ( remote_Mapping * ) pMapping;
+
+ OSL_ASSERT( ppUnoI && pTypeDescr );
+ if (*ppUnoI)
+ {
+ ((uno_Interface *)*ppUnoI)->release( (uno_Interface *)*ppUnoI );
+ *ppUnoI = 0;
+ }
+
+ if (pRemoteI && pTypeDescr)
+ {
+ // get object id of interface to be wrapped
+ rtl_uString * pOid = 0;
+ pRemoteMapping->pEnvRemote->pExtEnv->getObjectIdentifier(
+ pRemoteMapping->pEnvRemote->pExtEnv,
+ &pOid,
+ pRemoteI );
+
+ OSL_ASSERT(pOid);
+ if( ! pOid )
+ {
+ return;
+ }
+
+ // try to get any known interface from target environment
+ pRemoteMapping->pEnvUno->pExtEnv->getRegisteredInterface(
+ pRemoteMapping->pEnvUno->pExtEnv,
+ ppUnoI,
+ pOid,
+ pTypeDescr);
+
+ if ( ! *ppUnoI) // already existing interface
+ {
+ // try to publish a new proxy; proxy may be exchanged during registration
+ *ppUnoI = new Remote2UnoProxy(
+ ( remote_Interface * ) pRemoteI,
+ pOid,
+ pTypeDescr ,
+ pRemoteMapping->pEnvUno,
+ pRemoteMapping->pEnvRemote);
+
+ pRemoteMapping->pEnvUno->pExtEnv->registerProxyInterface(
+ pRemoteMapping->pEnvUno->pExtEnv,
+ ppUnoI,
+ freeRemote2UnoProxy,
+ pOid,
+ pTypeDescr );
+
+ OSL_ASSERT( *ppUnoI );
+ }
+ rtl_uString_release( pOid );
+ }
+}
+
+void unoToRemote( uno_Mapping *pMapping, void **ppRemoteI, void *pUnoI,
+ typelib_InterfaceTypeDescription *pTypeDescr )
+{
+ remote_Mapping *pRemoteMapping = ( remote_Mapping * ) pMapping;
+ OSL_ASSERT( ppRemoteI && pTypeDescr );
+ if (*ppRemoteI)
+ {
+ ((remote_Interface *)*ppRemoteI)->release( (remote_Interface *)*ppRemoteI);
+ *ppRemoteI = 0;
+ }
+ if (pUnoI && pTypeDescr)
+ {
+ // get object id of interface to be wrapped
+ rtl_uString * pOid = 0;
+ pRemoteMapping->pEnvUno->pExtEnv->getObjectIdentifier(
+ pRemoteMapping->pEnvUno->pExtEnv,
+ &pOid,
+ pUnoI );
+
+ OSL_ASSERT( pOid );
+ if( ! pOid )
+ {
+ return;
+ }
+
+ pRemoteMapping->pEnvRemote->pExtEnv->getRegisteredInterface(
+ pRemoteMapping->pEnvRemote->pExtEnv,
+ (void**)ppRemoteI,
+ pOid,
+ pTypeDescr );
+
+ if( !*ppRemoteI )
+ {
+ // try to publish a new proxy;
+ *ppRemoteI = new Uno2RemoteStub(
+ ( uno_Interface * ) pUnoI,
+ pOid,
+ pTypeDescr,
+ pRemoteMapping->pEnvUno,
+ pRemoteMapping->pEnvRemote );
+
+ // note : ppRemoteI may change during registration
+ pRemoteMapping->pEnvRemote->pExtEnv->registerProxyInterface(
+ pRemoteMapping->pEnvRemote->pExtEnv,
+ (void**) ppRemoteI,
+ freeUno2RemoteStub,
+ pOid,
+ pTypeDescr );
+ }
+
+ rtl_uString_release( pOid );
+ }
+}
+
+void freeRemoteMapping(uno_Mapping * mapping) {
+ delete reinterpret_cast< RemoteMapping * >(mapping);
+}
+
+RemoteMapping::RemoteMapping( uno_Environment *pEnvUno_ ,
+ uno_Environment *pEnvRemote_,
+ uno_MapInterfaceFunc func,
+ const ::rtl::OUString sPurpose) :
+ m_nRef( 1 ),
+ m_sPurpose( sPurpose )
+{
+ pEnvUno = pEnvUno_;
+ pEnvRemote = pEnvRemote_;
+
+ pEnvUno->acquire( pEnvUno );
+ pEnvRemote->acquire( pEnvRemote );
+
+ aBase.mapInterface = func;
+ aBase.acquire = thisAcquire;
+ aBase.release = thisRelease;
+}
+
+RemoteMapping::~RemoteMapping( )
+{
+ pEnvUno->release( pEnvUno );
+ pEnvRemote->release( pEnvRemote );
+}
+
+}
+
+/* vim:set shiftwidth=4 softtabstop=4 expandtab: */
diff --git a/bridges/source/remote/static/proxy.cxx b/bridges/source/remote/static/proxy.cxx
new file mode 100644
index 000000000000..bf8428264ab6
--- /dev/null
+++ b/bridges/source/remote/static/proxy.cxx
@@ -0,0 +1,341 @@
+/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
+/*************************************************************************
+ *
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * Copyright 2000, 2010 Oracle and/or its affiliates.
+ *
+ * OpenOffice.org - a multi-platform office productivity suite
+ *
+ * This file is part of OpenOffice.org.
+ *
+ * OpenOffice.org is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU Lesser General Public License version 3
+ * only, as published by the Free Software Foundation.
+ *
+ * OpenOffice.org is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU Lesser General Public License version 3 for more details
+ * (a copy is included in the LICENSE file that accompanied this code).
+ *
+ * You should have received a copy of the GNU Lesser General Public License
+ * version 3 along with OpenOffice.org. If not, see
+ * <http://www.openoffice.org/license.html>
+ * for a copy of the LGPLv3 License.
+ *
+ ************************************************************************/
+
+// MARKER(update_precomp.py): autogen include statement, do not remove
+#include "precompiled_bridges.hxx"
+#include <sal/alloca.h>
+#include <bridges/remote/proxy.hxx>
+#include <bridges/remote/context.h>
+
+#include <uno/data.h>
+#include <uno/mapping.hxx>
+#include <uno/environment.h>
+
+#include <com/sun/star/uno/Any.hxx>
+
+#include <bridges/remote/bridgeimpl.hxx>
+
+#include "remote_types.hxx"
+
+#if OSL_DEBUG_LEVEL > 1
+#include <bridges/remote/counter.hxx>
+static MyCounter thisCounter( "DEBUG : Remote2UnoProxy");
+#endif
+
+using namespace ::bridges_remote;
+using namespace ::com::sun::star::uno;
+
+extern "C" {
+
+void SAL_CALL remote_release( void *pRemoteI )
+{
+ ((remote_Interface * )pRemoteI)->release( (remote_Interface * ) pRemoteI );
+}
+
+}
+
+namespace bridges_remote {
+
+void freeRemote2UnoProxy(uno_ExtEnvironment *, void * proxy) {
+ delete static_cast< Remote2UnoProxy * >(proxy);
+}
+
+void acquireRemote2UnoProxy( uno_Interface *pThis )
+{
+ Remote2UnoProxy *p = ( Remote2UnoProxy * ) pThis;
+ if( 1 == osl_incrementInterlockedCount( &(p->m_nRef) ) )
+ {
+ p->m_pEnvUno->pExtEnv->registerProxyInterface(
+ p->m_pEnvUno->pExtEnv,
+ (void**)&pThis,
+ freeRemote2UnoProxy,
+ p->m_sOid.pData,
+ p->m_pType );
+ OSL_ASSERT( (uno_Interface *)p == pThis );
+ }
+}
+
+void releaseRemote2UnoProxy( uno_Interface *pThis )
+{
+ Remote2UnoProxy *p = ( Remote2UnoProxy * ) pThis;
+ if ( 0 == osl_decrementInterlockedCount( &(p->m_nRef) ))
+ {
+ p->m_pEnvUno->pExtEnv->revokeInterface( p->m_pEnvUno->pExtEnv, p );
+ }
+}
+
+void SAL_CALL dispatchRemote2UnoProxy(
+ uno_Interface * pUnoI,
+ typelib_TypeDescription const * pType,
+ void * pReturn,
+ void * ppArgs[],
+ uno_Any ** ppException )
+{
+ Remote2UnoProxy *p = ( Remote2UnoProxy * ) pUnoI;
+ RemoteThreadCounter counter( p->m_pEnvRemote );
+
+ typelib_InterfaceMethodTypeDescription *pMethodType = 0;
+ typelib_InterfaceAttributeTypeDescription *pAttributeType = 0;
+ typelib_TypeDescription *pReturnType = 0;
+ typelib_TypeDescription **ppArgType = 0;
+ sal_Int32 nArgCount = 0;
+ sal_Bool *pbIsIn = 0;
+ sal_Bool *pbIsOut = 0;
+ sal_Bool *pbConversionNeeded = 0;
+ sal_Bool bConversionNeededForReturn = 0;
+
+ //--------------------------------
+ // Collect all needed types !
+ //--------------------------------
+ if( typelib_TypeClass_INTERFACE_ATTRIBUTE == pType->eTypeClass )
+ {
+ pAttributeType = ( typelib_InterfaceAttributeTypeDescription * ) pType;
+ if( pReturn )
+ {
+ TYPELIB_DANGER_GET( &pReturnType , pAttributeType->pAttributeTypeRef );
+ bConversionNeededForReturn = remote_relatesToInterface( pReturnType );
+ }
+ else
+ {
+ nArgCount = 1;
+ ppArgType = (typelib_TypeDescription **) alloca( sizeof( void * ) );
+ pbIsIn = ( sal_Bool * ) alloca( sizeof( sal_Bool ) );
+ pbIsOut = ( sal_Bool * ) alloca( sizeof( sal_Bool ) );
+ pbConversionNeeded = ( sal_Bool *) alloca( sizeof( sal_Bool ) );
+
+ pbIsIn[0] = sal_True;
+ pbIsOut[0] = sal_False;
+ ppArgType[0] = 0;
+ TYPELIB_DANGER_GET( &( ppArgType[0] ) , pAttributeType->pAttributeTypeRef );
+ pbConversionNeeded[0] = remote_relatesToInterface( ppArgType[0] );
+
+ }
+ }
+ if( typelib_TypeClass_INTERFACE_METHOD == pType->eTypeClass )
+ {
+ pMethodType = ( typelib_InterfaceMethodTypeDescription * ) pType;
+ TYPELIB_DANGER_GET( &pReturnType , pMethodType->pReturnTypeRef );
+ bConversionNeededForReturn = remote_relatesToInterface( pReturnType );
+ nArgCount = pMethodType->nParams;
+ ppArgType = (typelib_TypeDescription **) alloca( sizeof( void * ) * nArgCount );
+ pbIsIn = (sal_Bool * ) alloca( sizeof( sal_Bool ) * nArgCount );
+ pbIsOut = (sal_Bool * ) alloca( sizeof( sal_Bool ) * nArgCount );
+ pbConversionNeeded = ( sal_Bool *) alloca( sizeof( sal_Bool ) * nArgCount );
+ sal_Int32 i;
+ for( i = 0 ; i < nArgCount ; i ++ )
+ {
+ ppArgType[i] = 0;
+ TYPELIB_DANGER_GET( & (ppArgType[i]) , pMethodType->pParams[i].pTypeRef );
+ pbIsIn[i] = pMethodType->pParams[i].bIn;
+ pbIsOut[i] = pMethodType->pParams[i].bOut;
+ pbConversionNeeded[i] = remote_relatesToInterface( ppArgType[i] );
+ }
+ }
+
+ void *pRemoteReturn = 0;
+ if( pReturnType )
+ {
+ if( bConversionNeededForReturn )
+ {
+ pRemoteReturn = alloca( pReturnType->nSize );
+ }
+ else
+ {
+ pRemoteReturn = pReturn;
+ }
+ }
+
+ void ** ppRemoteArgs = 0;
+ if( nArgCount )
+ {
+ ppRemoteArgs = (void**) alloca( sizeof( void * ) * nArgCount );
+ }
+
+ sal_Int32 i;
+ for( i = 0 ; i < nArgCount ; i ++ )
+ {
+ if( pbConversionNeeded[i] )
+ {
+ ppRemoteArgs[i] = alloca( ppArgType[i]->nSize );
+
+ if( pbIsIn[i] ) {
+ uno_copyAndConvertData(
+ ppRemoteArgs[i],
+ ppArgs[i],
+ ppArgType[i],
+ p->m_mapUno2Remote.get() );
+ }
+ }
+ else
+ {
+ ppRemoteArgs[i] = ppArgs[i];
+ }
+ }
+
+ uno_Any any;
+ uno_Any *pAny = &any;
+
+ p->m_pRemoteI->pDispatcher( p->m_pRemoteI,
+ pType,
+ pRemoteReturn,
+ ppRemoteArgs,
+ &pAny );
+
+ if( ! pAny )
+ {
+ if( pReturn && bConversionNeededForReturn )
+ {
+ uno_copyAndConvertData(
+ pReturn ,
+ pRemoteReturn,
+ pReturnType,
+ p->m_mapRemote2Uno.get() );
+ uno_destructData( pRemoteReturn , pReturnType , remote_release );
+ }
+
+ sal_Int32 j;
+ for( j = 0 ; j < nArgCount ; j ++ )
+ {
+ if( pbConversionNeeded[j] )
+ {
+ if( pbIsIn[j] ) {
+ if( pbIsOut[j] ) {
+ uno_destructData( ppArgs[j] ,
+ ppArgType[j] ,
+ 0 );
+ uno_copyAndConvertData( ppArgs[j] ,
+ ppRemoteArgs[j],
+ ppArgType[j],
+ p->m_mapRemote2Uno.get() );
+ }
+ }
+ else // pure out
+ {
+ uno_copyAndConvertData( ppArgs[j] ,
+ ppRemoteArgs[j],
+ ppArgType[j],
+ p->m_mapRemote2Uno.get() );
+ }
+ uno_destructData( ppRemoteArgs[j],
+ ppArgType[j],
+ remote_release );
+ }
+ }
+ *ppException = 0;
+ }
+ else
+ {
+ // -----------------------
+ // an exception occured
+ // -----------------------
+ typelib_TypeDescription *pAnyType = 0;
+ getCppuType( (::com::sun::star::uno::Any*) 0 ).getDescription( &pAnyType );
+ uno_copyAndConvertData( *ppException ,
+ pAny ,
+ pAnyType,
+ p->m_mapRemote2Uno.get() );
+ uno_destructData( pAny , pAnyType , remote_release );
+ typelib_typedescription_release( pAnyType );
+
+ // destruct remote in parameters ( out parameters have not been constructed )
+ for( i = 0 ; i < nArgCount ; i ++ )
+ {
+ if( pbConversionNeeded[i] && pbIsIn[i] )
+ {
+ uno_destructData( ppRemoteArgs[i],
+ ppArgType[i],
+ remote_release );
+ }
+ }
+ }
+
+ //--------------------------
+ // release all acquired types
+ //--------------------------
+ if( pReturnType )
+ {
+ TYPELIB_DANGER_RELEASE( pReturnType );
+ }
+ for( i = 0 ; i < nArgCount ; i ++ )
+ {
+ TYPELIB_DANGER_RELEASE( ppArgType[ i] );
+ }
+
+}
+
+Remote2UnoProxy::Remote2UnoProxy( remote_Interface *pRemoteI,
+ rtl_uString *pOid,
+ typelib_InterfaceTypeDescription *pType,
+ uno_Environment *pEnvUno,
+ uno_Environment *pEnvRemote ) :
+ m_sOid( pOid ),
+ m_pType( pType ),
+ m_pRemoteI( pRemoteI ),
+ m_pEnvUno( pEnvUno ),
+ m_pEnvRemote( pEnvRemote ),
+ m_mapRemote2Uno( pEnvRemote, pEnvUno ),
+ m_mapUno2Remote( pEnvUno , pEnvRemote ),
+ m_nRef( 1 )
+{
+ typelib_typedescription_acquire( (typelib_TypeDescription * ) m_pType );
+ m_pEnvUno->acquire( m_pEnvUno );
+ m_pEnvRemote->acquire( m_pEnvRemote );
+
+ acquire = acquireRemote2UnoProxy;
+ release = releaseRemote2UnoProxy;
+ pDispatcher = dispatchRemote2UnoProxy;
+
+ m_pEnvRemote->pExtEnv->registerInterface(
+ m_pEnvRemote->pExtEnv,
+ (void**)&m_pRemoteI,
+ m_sOid.pData,
+ m_pType );
+ m_pRemoteI->acquire( m_pRemoteI );
+
+#if OSL_DEBUG_LEVEL > 1
+ thisCounter.acquire();
+#endif
+}
+
+Remote2UnoProxy::~Remote2UnoProxy()
+{
+ // revoke external ref (oid)
+ m_pEnvRemote->pExtEnv->revokeInterface( m_pEnvRemote->pExtEnv , m_pRemoteI );
+
+ typelib_typedescription_release( (typelib_TypeDescription * )m_pType );
+ m_pRemoteI->release( m_pRemoteI );
+ m_pEnvUno->release( m_pEnvUno );
+ m_pEnvRemote->release( m_pEnvRemote );
+#if OSL_DEBUG_LEVEL > 1
+ thisCounter.release();
+#endif
+}
+
+} // end namespace bridge_remote
+
+/* vim:set shiftwidth=4 softtabstop=4 expandtab: */
diff --git a/bridges/source/remote/static/remote.cxx b/bridges/source/remote/static/remote.cxx
new file mode 100644
index 000000000000..24e7674f8cf1
--- /dev/null
+++ b/bridges/source/remote/static/remote.cxx
@@ -0,0 +1,164 @@
+/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
+/*************************************************************************
+ *
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * Copyright 2000, 2010 Oracle and/or its affiliates.
+ *
+ * OpenOffice.org - a multi-platform office productivity suite
+ *
+ * This file is part of OpenOffice.org.
+ *
+ * OpenOffice.org is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU Lesser General Public License version 3
+ * only, as published by the Free Software Foundation.
+ *
+ * OpenOffice.org is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU Lesser General Public License version 3 for more details
+ * (a copy is included in the LICENSE file that accompanied this code).
+ *
+ * You should have received a copy of the GNU Lesser General Public License
+ * version 3 along with OpenOffice.org. If not, see
+ * <http://www.openoffice.org/license.html>
+ * for a copy of the LGPLv3 License.
+ *
+ ************************************************************************/
+
+// MARKER(update_precomp.py): autogen include statement, do not remove
+#include "precompiled_bridges.hxx"
+#include <bridges/remote/remote.hxx>
+#include <bridges/remote/counter.hxx>
+
+#if OSL_DEBUG_LEVEL > 1
+static MyCounter thisCounter( "DEBUG : Remote2RemoteStub");
+#endif
+
+using namespace bridges_remote;
+
+extern "C" {
+
+static void SAL_CALL thisRelease( remote_Interface *pThis )
+{
+ Remote2RemoteStub *p = ( Remote2RemoteStub * ) pThis;
+ if (! osl_decrementInterlockedCount( &(p->m_nRef) ))
+ {
+ p->m_pEnvRemote->pExtEnv->revokeInterface( p->m_pEnvRemote->pExtEnv, pThis );
+
+ }
+}
+
+static void SAL_CALL thisDispatch(
+ remote_Interface * pRemoteI,
+ typelib_TypeDescription const * pMemberType,
+ void * pReturn,
+ void * pArgs[],
+ uno_Any ** ppException )
+{
+ Remote2RemoteStub *pThis = ( Remote2RemoteStub * ) pRemoteI;
+
+ pThis->m_dispatch( pThis->m_pEnvRemote,
+ pMemberType,
+ pThis->m_sOid.pData,
+ pThis->m_pType,
+ pReturn,
+ pArgs,
+ ppException );
+}
+
+}
+
+namespace bridges_remote {
+
+void acquireRemote2RemoteStub( remote_Interface *pThis )
+{
+ Remote2RemoteStub *p = ( Remote2RemoteStub * ) pThis;
+ if( 1 == osl_incrementInterlockedCount( &(p->m_nRef) ) )
+ {
+ p->m_pEnvRemote->pExtEnv->registerProxyInterface(
+ p->m_pEnvRemote->pExtEnv,
+ (void**)&pThis,
+ freeRemote2RemoteStub,
+ p->m_sOid.pData,
+ p->m_pType );
+ OSL_ASSERT( (remote_Interface *)p == pThis );
+ }
+}
+
+void freeRemote2RemoteStub(uno_ExtEnvironment *, void * stub) {
+ delete static_cast< Remote2RemoteStub * >(stub);
+}
+
+Remote2RemoteStub::Remote2RemoteStub( rtl_uString *pOid,
+ typelib_InterfaceTypeDescription *pType,
+ uno_Environment *pEnvRemote,
+ requestClientSideDispatcher dispatch ) :
+ m_sOid( pOid ),
+ m_pType( (typelib_InterfaceTypeDescription * ) pType ),
+ m_nRef( 1 ),
+ m_pEnvRemote( pEnvRemote ),
+ m_dispatch( dispatch ),
+ m_nReleaseRemote( 1 )
+{
+ typelib_typedescription_acquire( ( typelib_TypeDescription * ) m_pType );
+ m_pEnvRemote->acquire( m_pEnvRemote );
+
+ acquire = acquireRemote2RemoteStub;
+ release = thisRelease;
+ pDispatcher = thisDispatch;
+#if OSL_DEBUG_LEVEL > 1
+ thisCounter.acquire();
+#endif
+}
+
+Remote2RemoteStub::~Remote2RemoteStub()
+{
+
+ // send a release via the connection !
+ sal_Bool bNeedsRelease = sal_False;
+ if( ! m_pType->aBase.bComplete )
+ {
+ // m_pType may be exchanged during complete, so it needs to be acquired
+ // (MT : Another thread may use m_pType during e.g. dispatch ! ).
+ typelib_typedescription_acquire( (typelib_TypeDescription*)m_pType );
+ bNeedsRelease = sal_True;
+ typelib_typedescription_complete( (typelib_TypeDescription **) &m_pType );
+ }
+
+ uno_Any any;
+ uno_Any *pAny = &any;
+
+ typelib_TypeDescription *pReleaseMethod = 0;
+ typelib_typedescriptionreference_getDescription(
+ &pReleaseMethod ,
+ m_pType->ppAllMembers[REMOTE_RELEASE_METHOD_INDEX] );
+ for( int i = 0 ; i < m_nReleaseRemote ; i ++ )
+ {
+ thisDispatch( this,
+ pReleaseMethod,
+ 0,
+ 0,
+ &pAny );
+ }
+ typelib_typedescription_release( pReleaseMethod );
+ if( bNeedsRelease )
+ {
+ typelib_typedescription_release( (typelib_TypeDescription * ) m_pType );
+ }
+
+ typelib_typedescription_release( (typelib_TypeDescription * ) m_pType );
+ m_pEnvRemote->release( m_pEnvRemote );
+#if OSL_DEBUG_LEVEL > 1
+ thisCounter.release();
+#endif
+}
+
+void Remote2RemoteStub::releaseRemote()
+{
+ osl_incrementInterlockedCount( &m_nReleaseRemote );
+}
+
+} // end namespace bridges_remote
+
+/* vim:set shiftwidth=4 softtabstop=4 expandtab: */
diff --git a/bridges/source/remote/static/remote_types.cxx b/bridges/source/remote/static/remote_types.cxx
new file mode 100644
index 000000000000..95f023508ee4
--- /dev/null
+++ b/bridges/source/remote/static/remote_types.cxx
@@ -0,0 +1,99 @@
+/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
+/*************************************************************************
+ *
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * Copyright 2000, 2010 Oracle and/or its affiliates.
+ *
+ * OpenOffice.org - a multi-platform office productivity suite
+ *
+ * This file is part of OpenOffice.org.
+ *
+ * OpenOffice.org is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU Lesser General Public License version 3
+ * only, as published by the Free Software Foundation.
+ *
+ * OpenOffice.org is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU Lesser General Public License version 3 for more details
+ * (a copy is included in the LICENSE file that accompanied this code).
+ *
+ * You should have received a copy of the GNU Lesser General Public License
+ * version 3 along with OpenOffice.org. If not, see
+ * <http://www.openoffice.org/license.html>
+ * for a copy of the LGPLv3 License.
+ *
+ ************************************************************************/
+
+// MARKER(update_precomp.py): autogen include statement, do not remove
+#include "precompiled_bridges.hxx"
+#include "remote_types.hxx"
+
+namespace bridges_remote {
+
+sal_Bool SAL_CALL remote_relatesToInterface2( typelib_TypeDescription * pTypeDescr )
+{
+ switch (pTypeDescr->eTypeClass)
+ {
+ case typelib_TypeClass_SEQUENCE:
+ {
+ switch (((typelib_IndirectTypeDescription *)pTypeDescr)->pType->eTypeClass)
+ {
+ case typelib_TypeClass_SEQUENCE:
+ case typelib_TypeClass_STRUCT:
+ case typelib_TypeClass_EXCEPTION:
+ {
+ typelib_TypeDescription * pTD = 0;
+ TYPELIB_DANGER_GET( &pTD, ((typelib_IndirectTypeDescription *)pTypeDescr)->pType );
+ sal_Bool bRel = remote_relatesToInterface( pTD );
+ TYPELIB_DANGER_RELEASE( pTD );
+ return bRel;
+ }
+ default:
+ break;
+ }
+ }
+ case typelib_TypeClass_STRUCT:
+ case typelib_TypeClass_EXCEPTION:
+ {
+ // ...optimized... to avoid getDescription() calls!
+ typelib_CompoundTypeDescription * pComp = (typelib_CompoundTypeDescription *)pTypeDescr;
+ typelib_TypeDescriptionReference ** pTypes = pComp->ppTypeRefs;
+ for ( sal_Int32 nPos = pComp->nMembers; nPos--; )
+ {
+ switch (pTypes[nPos]->eTypeClass)
+ {
+ case typelib_TypeClass_INTERFACE:
+ case typelib_TypeClass_UNION: // might relate to interface
+ case typelib_TypeClass_ANY: // might relate to interface
+ return sal_True;
+ case typelib_TypeClass_SEQUENCE:
+ case typelib_TypeClass_STRUCT:
+ case typelib_TypeClass_EXCEPTION:
+ {
+ typelib_TypeDescription * pTD = 0;
+ TYPELIB_DANGER_GET( &pTD, pTypes[nPos] );
+ sal_Bool bRel = remote_relatesToInterface( pTD );
+ TYPELIB_DANGER_RELEASE( pTD );
+ if (bRel)
+ return sal_True;
+ break;
+ }
+ default:
+ break;
+ }
+ }
+ if (pComp->pBaseTypeDescription)
+ return remote_relatesToInterface( (typelib_TypeDescription *)pComp->pBaseTypeDescription );
+ break;
+ }
+ default:
+ OSL_ASSERT( 0 );
+ }
+ return sal_False;
+}
+
+}
+
+/* vim:set shiftwidth=4 softtabstop=4 expandtab: */
diff --git a/bridges/source/remote/static/remote_types.hxx b/bridges/source/remote/static/remote_types.hxx
new file mode 100644
index 000000000000..024f38037349
--- /dev/null
+++ b/bridges/source/remote/static/remote_types.hxx
@@ -0,0 +1,92 @@
+/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
+/*************************************************************************
+ *
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * Copyright 2000, 2010 Oracle and/or its affiliates.
+ *
+ * OpenOffice.org - a multi-platform office productivity suite
+ *
+ * This file is part of OpenOffice.org.
+ *
+ * OpenOffice.org is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU Lesser General Public License version 3
+ * only, as published by the Free Software Foundation.
+ *
+ * OpenOffice.org is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU Lesser General Public License version 3 for more details
+ * (a copy is included in the LICENSE file that accompanied this code).
+ *
+ * You should have received a copy of the GNU Lesser General Public License
+ * version 3 along with OpenOffice.org. If not, see
+ * <http://www.openoffice.org/license.html>
+ * for a copy of the LGPLv3 License.
+ *
+ ************************************************************************/
+#ifndef _BRIDGES_REMOTE_TYPES_HXX_
+#define _BRIDGES_REMOTE_TYPES_HXX_
+
+#include <osl/diagnose.h>
+#include <sal/types.h>
+#include <typelib/typedescription.h>
+
+namespace bridges_remote
+{
+
+inline sal_Bool SAL_CALL remote_relatesToInterface( typelib_TypeDescription *pTypeDescr );
+sal_Bool SAL_CALL remote_relatesToInterface2( typelib_TypeDescription * pTypeDescr );
+
+
+/** Determines whether given type might relate or relates to an interface,
+ i.e. values of this type are interface or may contain interface(s).<br>
+ @param pTypeDescr type description of type
+ @return true if type might relate to an interface, false otherwise
+*/
+inline sal_Bool SAL_CALL remote_relatesToInterface( typelib_TypeDescription * pTypeDescr )
+{
+ switch (pTypeDescr->eTypeClass)
+ {
+ case typelib_TypeClass_SEQUENCE:
+ switch (((typelib_IndirectTypeDescription *)pTypeDescr)->pType->eTypeClass)
+ {
+ case typelib_TypeClass_INTERFACE:
+ case typelib_TypeClass_UNION: // might relate to interface
+ case typelib_TypeClass_ANY: // might relate to interface
+ return sal_True;
+ case typelib_TypeClass_SEQUENCE:
+ case typelib_TypeClass_STRUCT:
+ case typelib_TypeClass_EXCEPTION:
+ return remote_relatesToInterface2( pTypeDescr );
+ default:
+ return sal_False;
+ }
+ case typelib_TypeClass_STRUCT:
+ case typelib_TypeClass_EXCEPTION:
+ return remote_relatesToInterface2( pTypeDescr );
+ case typelib_TypeClass_UNION: // might relate to interface
+ case typelib_TypeClass_ANY: // might relate to interface
+ case typelib_TypeClass_INTERFACE:
+ return sal_True;
+ default:
+ return sal_False;
+ }
+}
+
+/** Determines whether given type is a cpp simple type, e.g. int, enum.<br>
+ @param pTypeDescr type description of type
+ @return true if type is a cpp simple type, false otherwise
+*/
+inline sal_Bool SAL_CALL remote_isSimpleType( typelib_TypeDescription * pTypeDescr )
+{
+ return (pTypeDescr->eTypeClass <= typelib_TypeClass_ENUM &&
+ pTypeDescr->eTypeClass != typelib_TypeClass_STRING &&
+ pTypeDescr->eTypeClass != typelib_TypeClass_ANY &&
+ pTypeDescr->eTypeClass != typelib_TypeClass_TYPE);
+}
+
+}
+#endif
+
+/* vim:set shiftwidth=4 softtabstop=4 expandtab: */
diff --git a/bridges/source/remote/static/stub.cxx b/bridges/source/remote/static/stub.cxx
new file mode 100644
index 000000000000..ee6d33184eca
--- /dev/null
+++ b/bridges/source/remote/static/stub.cxx
@@ -0,0 +1,339 @@
+/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
+/*************************************************************************
+ *
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * Copyright 2000, 2010 Oracle and/or its affiliates.
+ *
+ * OpenOffice.org - a multi-platform office productivity suite
+ *
+ * This file is part of OpenOffice.org.
+ *
+ * OpenOffice.org is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU Lesser General Public License version 3
+ * only, as published by the Free Software Foundation.
+ *
+ * OpenOffice.org is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU Lesser General Public License version 3 for more details
+ * (a copy is included in the LICENSE file that accompanied this code).
+ *
+ * You should have received a copy of the GNU Lesser General Public License
+ * version 3 along with OpenOffice.org. If not, see
+ * <http://www.openoffice.org/license.html>
+ * for a copy of the LGPLv3 License.
+ *
+ ************************************************************************/
+
+// MARKER(update_precomp.py): autogen include statement, do not remove
+#include "precompiled_bridges.hxx"
+#include <sal/alloca.h>
+#include <osl/diagnose.h>
+
+#include <uno/data.h>
+#include <uno/mapping.hxx>
+
+#include <bridges/remote/stub.hxx>
+#include <bridges/remote/proxy.hxx>
+#include <bridges/remote/context.h>
+#include <bridges/remote/bridgeimpl.hxx>
+
+#include "remote_types.hxx"
+
+#if OSL_DEBUG_LEVEL > 1
+#include <bridges/remote/counter.hxx>
+static MyCounter thisCounter( "DEBUG : Uno2RemoteStub");
+#endif
+
+using namespace ::com::sun::star::uno;
+using namespace bridges_remote;
+
+extern "C" {
+
+void SAL_CALL thisRelease( remote_Interface *pThis )
+{
+ Uno2RemoteStub *p = ( Uno2RemoteStub * ) pThis;
+ if (! osl_decrementInterlockedCount( &(p->m_nRef) ))
+ {
+ p->m_pEnvRemote->pExtEnv->revokeInterface( p->m_pEnvRemote->pExtEnv, pThis );
+ }
+}
+
+void SAL_CALL thisDispatch(
+ remote_Interface * pRemoteI,
+ typelib_TypeDescription const * pType,
+ void * pReturn,
+ void * ppArgs[],
+ uno_Any ** ppException )
+{
+ Uno2RemoteStub *p = ( Uno2RemoteStub * ) pRemoteI;
+
+ RemoteThreadCounter counter( p->m_pEnvRemote );
+
+ typelib_InterfaceMethodTypeDescription *pMethodType = 0;
+ typelib_InterfaceAttributeTypeDescription *pAttributeType = 0;
+ typelib_TypeDescription *pReturnType = 0;
+ typelib_TypeDescription **ppArgType = 0;
+ sal_Int32 nArgCount = 0;
+ sal_Bool *pbIsIn = 0;
+ sal_Bool *pbIsOut = 0;
+ sal_Bool bConversionNeededForReturn = sal_False;
+ sal_Bool *pbConversionNeeded = 0;
+
+ sal_Int32 i;
+ //--------------------------------
+ // Collect all needed types !
+ //--------------------------------
+ if( typelib_TypeClass_INTERFACE_ATTRIBUTE == pType->eTypeClass )
+ {
+ pAttributeType = ( typelib_InterfaceAttributeTypeDescription * ) pType;
+ if( pReturn )
+ {
+ TYPELIB_DANGER_GET( &pReturnType , pAttributeType->pAttributeTypeRef );
+ bConversionNeededForReturn = remote_relatesToInterface( pReturnType );
+ }
+ else
+ {
+ nArgCount = 1;
+ ppArgType = (typelib_TypeDescription **) alloca( sizeof( void * ) );
+ pbIsIn = ( sal_Bool * ) alloca( sizeof( sal_Bool ) );
+ pbIsOut = ( sal_Bool * ) alloca( sizeof( sal_Bool ) );
+ pbConversionNeeded = ( sal_Bool * ) alloca( sizeof( sal_Bool ) );
+ pbIsIn[0] = sal_True;
+ pbIsOut[0] = sal_False;
+ ppArgType[0] = 0;
+ TYPELIB_DANGER_GET( &( ppArgType[0] ) , pAttributeType->pAttributeTypeRef );
+ pbConversionNeeded[0] = remote_relatesToInterface( ppArgType[0] );
+ }
+ }
+ if( typelib_TypeClass_INTERFACE_METHOD == pType->eTypeClass )
+ {
+ pMethodType = ( typelib_InterfaceMethodTypeDescription * ) pType;
+ TYPELIB_DANGER_GET( &pReturnType , pMethodType->pReturnTypeRef );
+ bConversionNeededForReturn = remote_relatesToInterface( pReturnType );
+ nArgCount = pMethodType->nParams;
+ ppArgType = (typelib_TypeDescription **) alloca( sizeof( void * ) * nArgCount );
+ pbIsIn = (sal_Bool * ) alloca( sizeof( sal_Bool ) * nArgCount );
+ pbIsOut = (sal_Bool * ) alloca( sizeof( sal_Bool ) * nArgCount );
+ pbConversionNeeded = ( sal_Bool * ) alloca( sizeof( sal_Bool ) * nArgCount );
+
+ for( i = 0 ; i < nArgCount ; i ++ )
+ {
+ ppArgType[i] = 0;
+ TYPELIB_DANGER_GET( & (ppArgType[i]) , pMethodType->pParams[i].pTypeRef );
+ pbIsIn[i] = pMethodType->pParams[i].bIn;
+ pbIsOut[i] = pMethodType->pParams[i].bOut;
+ pbConversionNeeded[i] = remote_relatesToInterface( ppArgType[i] );
+ }
+ }
+
+ // create Mapping
+
+ void *pUnoReturn = 0;
+ void **ppUnoArgs = 0;
+
+ if( pReturnType )
+ {
+ if( bConversionNeededForReturn )
+ {
+ pUnoReturn = alloca( pReturnType->nSize );
+ }
+ else
+ {
+ pUnoReturn = pReturn;
+ }
+ }
+
+ ppUnoArgs = (void **) alloca( nArgCount * sizeof( void * ) );
+ for( i = 0 ; i < nArgCount ; i ++ )
+ {
+ if( pbConversionNeeded[i] )
+ {
+ ppUnoArgs[i] = alloca( ppArgType[i]->nSize );
+ if( pbIsIn[i] )
+ {
+ uno_copyAndConvertData(
+ ppUnoArgs[i],
+ ppArgs[i],
+ ppArgType[i],
+ p->m_mapRemote2Uno.get()
+ );
+ }
+ }
+ else
+ {
+ ppUnoArgs[i] = ppArgs[i];
+ }
+ }
+
+ // do the call
+ uno_Any any;
+ uno_Any *pAny = &any;
+
+ p->m_pUnoI->pDispatcher( p->m_pUnoI,
+ pType,
+ pUnoReturn,
+ ppUnoArgs,
+ &pAny);
+
+ if( ! pAny )
+ {
+ // ------------------
+ // No Exception
+ // ------------------
+
+ // Map return value
+ if( pReturnType && bConversionNeededForReturn )
+ {
+ uno_copyAndConvertData(
+ pReturn ,
+ pUnoReturn,
+ pReturnType,
+ p->m_mapUno2Remote.get() );
+ uno_destructData( pUnoReturn , pReturnType, 0 );
+ }
+
+ // map arguments
+ for( i = 0 ; i < nArgCount ; i ++ )
+ {
+ if( pbConversionNeeded[i] )
+ {
+ if( pbIsIn[i] ) {
+ if( pbIsOut[i] ) {
+ uno_destructData(
+ ppArgs[i] ,
+ ppArgType[i] ,
+ remote_release );
+ uno_copyAndConvertData( ppArgs[i] ,
+ ppUnoArgs[i],
+ ppArgType[i],
+ p->m_mapUno2Remote.get() );
+ }
+ }
+ else // pure out
+ {
+ uno_copyAndConvertData( ppArgs[i] ,
+ ppUnoArgs[i],
+ ppArgType[i],
+ p->m_mapUno2Remote.get() );
+ }
+ uno_destructData( ppUnoArgs[i],
+ ppArgType[i],
+ 0 );
+ }
+ }
+ *ppException = 0;
+ }
+ else
+ {
+ // -----------------------
+ // an exception occured
+ // -----------------------
+ typelib_TypeDescription *pAnyType = 0;
+ getCppuType( (Any*) 0 ).getDescription( &pAnyType );
+ uno_copyAndConvertData( *ppException ,
+ pAny ,
+ pAnyType,
+ p->m_mapUno2Remote.get() );
+ uno_destructData( pAny , pAnyType , 0 );
+ typelib_typedescription_release( pAnyType );
+
+ // destruct uno in parameters ( out parameters have not been constructed )
+ for( i = 0 ; i < nArgCount ; i ++ )
+ {
+ if( pbConversionNeeded[i] && pbIsIn[i] )
+ {
+ uno_destructData( ppUnoArgs[i],
+ ppArgType[i],
+ 0 );
+ }
+ }
+ }
+
+ //--------------------------
+ // release all acquired types
+ //--------------------------
+ if( pReturnType )
+ {
+ TYPELIB_DANGER_RELEASE( pReturnType );
+ }
+ for( i = 0 ; i < nArgCount ; i ++ )
+ {
+ TYPELIB_DANGER_RELEASE( ppArgType[ i] );
+ }
+}
+
+}
+
+namespace bridges_remote {
+
+void acquireUno2RemoteStub( remote_Interface *pThis )
+{
+ Uno2RemoteStub *p = ( Uno2RemoteStub * ) pThis;
+ if( 1 == osl_incrementInterlockedCount( &(p->m_nRef) ) )
+ {
+
+ p->m_pEnvRemote->pExtEnv->registerProxyInterface(
+ p->m_pEnvRemote->pExtEnv,
+ (void**)&pThis,
+ freeUno2RemoteStub,
+ p->m_sOid.pData,
+ p->m_pType );
+
+ OSL_ASSERT( (remote_Interface*) p == pThis );
+ }
+}
+
+void freeUno2RemoteStub(uno_ExtEnvironment *, void * stub) {
+ delete static_cast< Uno2RemoteStub * >(stub);
+}
+
+Uno2RemoteStub::Uno2RemoteStub( uno_Interface *pUnoI,
+ rtl_uString *pOid,
+ typelib_InterfaceTypeDescription *pType,
+ uno_Environment *pEnvUno,
+ uno_Environment *pEnvRemote ) :
+ m_sOid( pOid ),
+ m_pType( pType ),
+ m_pUnoI( pUnoI ),
+ m_nRef( 1 ),
+ m_pEnvUno( pEnvUno ),
+ m_pEnvRemote( pEnvRemote ),
+ m_mapRemote2Uno( pEnvRemote, pEnvUno ),
+ m_mapUno2Remote( pEnvUno, pEnvRemote )
+{
+ typelib_typedescription_acquire( (typelib_TypeDescription * )m_pType );
+ m_pEnvUno->acquire( m_pEnvUno );
+ m_pEnvRemote->acquire( m_pEnvRemote );
+
+ acquire = acquireUno2RemoteStub;
+ release = thisRelease;
+ pDispatcher = thisDispatch;
+
+ m_pEnvUno->pExtEnv->registerInterface( m_pEnvUno->pExtEnv,
+ (void **)&m_pUnoI,
+ m_sOid.pData,
+ m_pType );
+ m_pUnoI->acquire( m_pUnoI );
+#if OSL_DEBUG_LEVEL > 1
+ thisCounter.acquire();
+#endif
+}
+
+Uno2RemoteStub::~Uno2RemoteStub()
+{
+ m_pEnvUno->pExtEnv->revokeInterface( m_pEnvUno->pExtEnv , m_pUnoI );
+
+ typelib_typedescription_release( (typelib_TypeDescription * )m_pType );
+ m_pUnoI->release( m_pUnoI );
+ m_pEnvUno->release( m_pEnvUno );
+ m_pEnvRemote->release( m_pEnvRemote );
+#if OSL_DEBUG_LEVEL > 1
+ thisCounter.release();
+#endif
+}
+
+} // end namespace bridges_remote
+
+/* vim:set shiftwidth=4 softtabstop=4 expandtab: */