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_unotools.hxx" 30 31 #include <unotools/componentfactory.hxx> 32 #include <comphelper/processfactory.hxx> 33 #include <com/sun/star/lang/XSingleServiceFactory.hpp> 34 #include <com/sun/star/lang/XMultiServiceFactory.hpp> 35 36 #ifndef _COM_SUN_STAR_REGISTRY_XREGISTRYKEY_HDL_ 37 #include <com/sun/star/registry/XRegistryKey.hpp> 38 #endif 39 40 #include <cppuhelper/factory.hxx> 41 42 #include <uno/environment.h> 43 #include <uno/mapping.hxx> 44 45 #include <rtl/ustring.hxx> 46 #include <osl/module.h> 47 48 49 50 51 using namespace ::com::sun::star; 52 using namespace ::com::sun::star::uno; 53 using namespace ::com::sun::star::lang; 54 using namespace ::com::sun::star::registry; 55 using namespace ::rtl; 56 57 58 namespace utl 59 { 60 61 Reference< XInterface > getComponentInstance( 62 const OUString & rLibraryName, 63 const OUString & rImplementationName 64 ) 65 { 66 Reference< XInterface > xI; 67 Reference< XMultiServiceFactory > xMSF = ::comphelper::getProcessServiceFactory(); 68 if ( xMSF.is() ) 69 xI = xMSF->createInstance( rImplementationName ); 70 if( !xI.is() ) 71 { 72 Reference< XSingleServiceFactory > xSSF = 73 loadLibComponentFactory( rLibraryName, rImplementationName, 74 Reference< XMultiServiceFactory >(), Reference< XRegistryKey >() ); 75 xI = xSSF->createInstance(); 76 } 77 return xI; 78 } 79 80 81 Reference< XSingleServiceFactory > loadLibComponentFactory( 82 const OUString & rLibName, 83 const OUString & rImplName, 84 const Reference< XMultiServiceFactory > & xSF, 85 const Reference< XRegistryKey > & xKey 86 ) 87 { 88 Reference< XSingleServiceFactory > xRet; 89 90 oslModule lib = osl_loadModule( rLibName.pData, SAL_LOADMODULE_LAZY | SAL_LOADMODULE_GLOBAL ); 91 if (lib) 92 { 93 void * pSym; 94 95 // ========================= LATEST VERSION ========================= 96 OUString aGetEnvName( RTL_CONSTASCII_USTRINGPARAM(COMPONENT_GETENV) ); 97 if (pSym = osl_getSymbol( lib, aGetEnvName.pData )) 98 { 99 uno_Environment * pCurrentEnv = 0; 100 uno_Environment * pEnv = 0; 101 const sal_Char * pEnvTypeName = 0; 102 (*((component_getImplementationEnvironmentFunc)pSym))( &pEnvTypeName, &pEnv ); 103 104 sal_Bool bNeedsMapping = 105 (pEnv || 0 != rtl_str_compare( pEnvTypeName, CPPU_CURRENT_LANGUAGE_BINDING_NAME )); 106 107 OUString aEnvTypeName( OUString::createFromAscii( pEnvTypeName ) ); 108 109 if (bNeedsMapping) 110 { 111 if (! pEnv) 112 uno_getEnvironment( &pEnv, aEnvTypeName.pData, 0 ); 113 if (pEnv) 114 { 115 OUString aCppEnvTypeName( RTL_CONSTASCII_USTRINGPARAM(CPPU_CURRENT_LANGUAGE_BINDING_NAME) ); 116 uno_getEnvironment( &pCurrentEnv, aCppEnvTypeName.pData, 0 ); 117 if (pCurrentEnv) 118 bNeedsMapping = (pEnv != pCurrentEnv); 119 } 120 } 121 122 OUString aGetFactoryName( RTL_CONSTASCII_USTRINGPARAM(COMPONENT_GETFACTORY) ); 123 if (pSym = osl_getSymbol( lib, aGetFactoryName.pData )) 124 { 125 OString aImplName( OUStringToOString( rImplName, RTL_TEXTENCODING_ASCII_US ) ); 126 127 if (bNeedsMapping) 128 { 129 if (pEnv && pCurrentEnv) 130 { 131 Mapping aCurrent2Env( pCurrentEnv, pEnv ); 132 Mapping aEnv2Current( pEnv, pCurrentEnv ); 133 134 if (aCurrent2Env.is() && aEnv2Current.is()) 135 { 136 void * pSMgr = aCurrent2Env.mapInterface( 137 xSF.get(), ::getCppuType( (const Reference< XMultiServiceFactory > *)0 ) ); 138 void * pKey = aCurrent2Env.mapInterface( 139 xKey.get(), ::getCppuType( (const Reference< XRegistryKey > *)0 ) ); 140 141 void * pSSF = (*((component_getFactoryFunc)pSym))( 142 aImplName.getStr(), pSMgr, pKey ); 143 144 if (pKey) 145 (*pEnv->pExtEnv->releaseInterface)( pEnv->pExtEnv, pKey ); 146 if (pSMgr) 147 (*pEnv->pExtEnv->releaseInterface)( pEnv->pExtEnv, pSMgr ); 148 149 if (pSSF) 150 { 151 aEnv2Current.mapInterface( 152 reinterpret_cast< void ** >( &xRet ), 153 pSSF, ::getCppuType( (const Reference< XSingleServiceFactory > *)0 ) ); 154 (*pEnv->pExtEnv->releaseInterface)( pEnv->pExtEnv, pSSF ); 155 } 156 } 157 } 158 } 159 else 160 { 161 XSingleServiceFactory * pRet = (XSingleServiceFactory *) 162 (*((component_getFactoryFunc)pSym))( 163 aImplName.getStr(), xSF.get(), xKey.get() ); 164 if (pRet) 165 { 166 xRet = pRet; 167 pRet->release(); 168 } 169 } 170 } 171 172 if (pEnv) 173 (*pEnv->release)( pEnv ); 174 if (pCurrentEnv) 175 (*pCurrentEnv->release)( pCurrentEnv ); 176 } 177 178 179 if (! xRet.is()) 180 osl_unloadModule( lib ); 181 } 182 183 return xRet; 184 } 185 186 } // namespace utl 187