1 /************************************************************************* 2 * 3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. 4 * 5 * Copyright 2000, 2010 Oracle and/or its affiliates. 6 * 7 * OpenOffice.org - a multi-platform office productivity suite 8 * 9 * This file is part of OpenOffice.org. 10 * 11 * OpenOffice.org is free software: you can redistribute it and/or modify 12 * it under the terms of the GNU Lesser General Public License version 3 13 * only, as published by the Free Software Foundation. 14 * 15 * OpenOffice.org is distributed in the hope that it will be useful, 16 * but WITHOUT ANY WARRANTY; without even the implied warranty of 17 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 18 * GNU Lesser General Public License version 3 for more details 19 * (a copy is included in the LICENSE file that accompanied this code). 20 * 21 * You should have received a copy of the GNU Lesser General Public License 22 * version 3 along with OpenOffice.org. If not, see 23 * <http://www.openoffice.org/license.html> 24 * for a copy of the LGPLv3 License. 25 * 26 ************************************************************************/ 27 28 // MARKER(update_precomp.py): autogen include statement, do not remove 29 #include "precompiled_bridges.hxx" 30 31 #include "bridges/cpp_uno/shared/unointerfaceproxy.hxx" 32 33 #include "bridges/cpp_uno/shared/bridge.hxx" 34 35 #include "com/sun/star/uno/XInterface.hpp" 36 #include "osl/diagnose.h" 37 #include "osl/interlck.h" 38 #include "typelib/typedescription.h" 39 #include "uno/dispatcher.h" 40 41 namespace bridges { namespace cpp_uno { namespace shared { 42 43 void freeUnoInterfaceProxy(uno_ExtEnvironment * pEnv, void * pProxy) 44 { 45 UnoInterfaceProxy * pThis = 46 static_cast< UnoInterfaceProxy * >( 47 reinterpret_cast< uno_Interface * >( pProxy ) ); 48 if (pEnv != pThis->pBridge->getUnoEnv()) { 49 OSL_ASSERT(false); 50 } 51 52 (*pThis->pBridge->getCppEnv()->revokeInterface)( 53 pThis->pBridge->getCppEnv(), pThis->pCppI ); 54 pThis->pCppI->release(); 55 ::typelib_typedescription_release( 56 (typelib_TypeDescription *)pThis->pTypeDescr ); 57 pThis->pBridge->release(); 58 59 #if OSL_DEBUG_LEVEL > 1 60 *(int *)pProxy = 0xdeadbabe; 61 #endif 62 delete pThis; 63 } 64 65 void acquireProxy(uno_Interface * pUnoI) 66 { 67 if (1 == osl_incrementInterlockedCount( 68 & static_cast< UnoInterfaceProxy * >( pUnoI )->nRef )) 69 { 70 // rebirth of proxy zombie 71 // register at uno env 72 #if OSL_DEBUG_LEVEL > 1 73 void * pThis = pUnoI; 74 #endif 75 (*static_cast< UnoInterfaceProxy * >( pUnoI )->pBridge->getUnoEnv()-> 76 registerProxyInterface)( 77 static_cast< UnoInterfaceProxy * >( pUnoI )->pBridge->getUnoEnv(), 78 reinterpret_cast< void ** >( &pUnoI ), freeUnoInterfaceProxy, 79 static_cast< UnoInterfaceProxy * >( pUnoI )->oid.pData, 80 static_cast< UnoInterfaceProxy * >( pUnoI )->pTypeDescr ); 81 #if OSL_DEBUG_LEVEL > 1 82 OSL_ASSERT( pThis == pUnoI ); 83 #endif 84 } 85 } 86 87 void releaseProxy(uno_Interface * pUnoI) 88 { 89 if (! osl_decrementInterlockedCount( 90 & static_cast< UnoInterfaceProxy * >( pUnoI )->nRef )) 91 { 92 // revoke from uno env on last release 93 (*static_cast< UnoInterfaceProxy * >( pUnoI )->pBridge->getUnoEnv()-> 94 revokeInterface)( 95 static_cast< UnoInterfaceProxy * >( pUnoI )->pBridge->getUnoEnv(), 96 pUnoI ); 97 } 98 } 99 100 UnoInterfaceProxy * UnoInterfaceProxy::create( 101 bridges::cpp_uno::shared::Bridge * pBridge, 102 com::sun::star::uno::XInterface * pCppI, 103 typelib_InterfaceTypeDescription * pTypeDescr, 104 rtl::OUString const & rOId) SAL_THROW(()) 105 { 106 return new UnoInterfaceProxy(pBridge, pCppI, pTypeDescr, rOId); 107 } 108 109 UnoInterfaceProxy::UnoInterfaceProxy( 110 bridges::cpp_uno::shared::Bridge * pBridge_, 111 com::sun::star::uno::XInterface * pCppI_, 112 typelib_InterfaceTypeDescription * pTypeDescr_, rtl::OUString const & rOId_) 113 SAL_THROW(()) 114 : nRef( 1 ) 115 , pBridge( pBridge_ ) 116 , pCppI( pCppI_ ) 117 , pTypeDescr( pTypeDescr_ ) 118 , oid( rOId_ ) 119 { 120 pBridge->acquire(); 121 ::typelib_typedescription_acquire( (typelib_TypeDescription *)pTypeDescr ); 122 if (! ((typelib_TypeDescription *)pTypeDescr)->bComplete) 123 ::typelib_typedescription_complete( 124 (typelib_TypeDescription **)&pTypeDescr ); 125 OSL_ENSURE( 126 ((typelib_TypeDescription *)pTypeDescr)->bComplete, 127 "### type is incomplete!" ); 128 pCppI->acquire(); 129 (*pBridge->getCppEnv()->registerInterface)( 130 pBridge->getCppEnv(), reinterpret_cast< void ** >( &pCppI ), oid.pData, 131 pTypeDescr ); 132 133 // uno_Interface 134 acquire = acquireProxy; 135 release = releaseProxy; 136 pDispatcher = unoInterfaceProxyDispatch; 137 } 138 139 UnoInterfaceProxy::~UnoInterfaceProxy() 140 {} 141 142 } } } 143