diff options
author | Tor Lillqvist <tml@iki.fi> | 2011-08-08 17:34:53 +0300 |
---|---|---|
committer | Tor Lillqvist <tml@iki.fi> | 2011-08-08 17:39:38 +0300 |
commit | b16ab7a751c04049b4171df412f1ef0f4f9b02f2 (patch) | |
tree | 60279050d19627adad307c653457b4f5b169232a | |
parent | cf3eac39e12f85043e5beb686b9abb9e94dda34d (diff) |
Add invokeStaticComponentFactory() for statically linked components
Will be used for iOS at least.
Factor out the part of loadSharedLibComponentFactory() that handle the
symbol that has been successfully looked up.
-rw-r--r-- | cppuhelper/inc/cppuhelper/shlib.hxx | 21 | ||||
-rw-r--r-- | cppuhelper/source/gcc3.map | 1 | ||||
-rw-r--r-- | cppuhelper/source/shlib.cxx | 205 |
3 files changed, 150 insertions, 77 deletions
diff --git a/cppuhelper/inc/cppuhelper/shlib.hxx b/cppuhelper/inc/cppuhelper/shlib.hxx index 9c12d2d039e9..21529bc8ba75 100644 --- a/cppuhelper/inc/cppuhelper/shlib.hxx +++ b/cppuhelper/inc/cppuhelper/shlib.hxx @@ -28,6 +28,7 @@ #ifndef _CPPUHELPER_SHLIB_HXX_ #define _CPPUHELPER_SHLIB_HXX_ +#include <osl/module.hxx> #include <com/sun/star/lang/XMultiServiceFactory.hpp> #include <com/sun/star/registry/XRegistryKey.hpp> #include <com/sun/star/loader/CannotActivateFactoryException.hpp> @@ -93,6 +94,26 @@ SAL_CALL loadSharedLibComponentFactory( ::rtl::OUString const & rPrefix ) SAL_THROW( (::com::sun::star::loader::CannotActivateFactoryException) ); +/** Gets the factory out of an already loaded (for instance statically linked) component. + + @param pGetter the component's component_getFactory function + @param rImplName implementation to be retrieved from the library + @param xMgr service manager to be provided to the component + @param xKey registry key to be provided to the component + @param rPrefix optional component prefix + @return + factory instance (::com::sun::star::lang::XSingleComponentFactory or + ::com::sun::star::lang::XSingleComponentFactory) +*/ +::com::sun::star::uno::Reference< ::com::sun::star::uno::XInterface > +SAL_CALL invokeStaticComponentFactory( + oslGenericFunction pGetter, + ::rtl::OUString const & rImplName, + ::com::sun::star::uno::Reference< ::com::sun::star::lang::XMultiServiceFactory > const & xMgr, + ::com::sun::star::uno::Reference< ::com::sun::star::registry::XRegistryKey > const & xKey, + ::rtl::OUString const & rPrefix ) + SAL_THROW( (::com::sun::star::loader::CannotActivateFactoryException) ); + /** Invokes component_writeInfo() function of specified component library. You can give either a fully qualified libname or single lib name. The libname need not be pre/postfixed (e.g. xxx.dll). You can give parameter rPath to force lookup of the library in a specific diff --git a/cppuhelper/source/gcc3.map b/cppuhelper/source/gcc3.map index 156fcc12f28f..24f4efea5c3d 100644 --- a/cppuhelper/source/gcc3.map +++ b/cppuhelper/source/gcc3.map @@ -157,6 +157,7 @@ _ZN4cppu28createRegistryServiceFactoryERKN3rtl8OUStringES3_hS3_; _ZN4cppu28createSingleComponentFactoryEPFN3com3sun4star3uno9ReferenceINS3_10XInterfaceEEERKNS4_INS3_17XComponentContextEEEERKN3rtl8OUStringERKNS3_8SequenceISE_EEP16_rtl_ModuleCount; _ZN4cppu29WeakComponentImplHelper_queryERKN3com3sun4star3uno4TypeEPNS_10class_dataEPvPNS_27WeakComponentImplHelperBaseE; _ZN4cppu29installTypeDescriptionManagerERKN3com3sun4star3uno9ReferenceINS2_9container23XHierarchicalNameAccessEEE; +_ZN4cppu28invokeStaticComponentFactoryEPFvvERKN3rtl8OUStringERKN3com3sun4star3uno9ReferenceINS8_4lang20XMultiServiceFactoryEEERKNSA_INS8_8registry12XRegistryKeyEEES5_; _ZN4cppu29loadSharedLibComponentFactoryERKN3rtl8OUStringES3_S3_RKN3com3sun4star3uno9ReferenceINS6_4lang20XMultiServiceFactoryEEERKNS8_INS6_8registry12XRegistryKeyEEE; _ZN4cppu29loadSharedLibComponentFactoryERKN3rtl8OUStringES3_S3_RKN3com3sun4star3uno9ReferenceINS6_4lang20XMultiServiceFactoryEEERKNS8_INS6_8registry12XRegistryKeyEEES3_; _ZN4cppu30ImplHelper_getImplementationIdEPNS_10class_dataE; diff --git a/cppuhelper/source/shlib.cxx b/cppuhelper/source/shlib.cxx index 9f6ff0c1c78a..ec8304dc250e 100644 --- a/cppuhelper/source/shlib.cxx +++ b/cppuhelper/source/shlib.cxx @@ -345,6 +345,102 @@ Reference< XInterface > SAL_CALL loadSharedLibComponentFactory( return loadSharedLibComponentFactory( rLibName, rPath, rImplName, xMgr, xKey, rtl::OUString() ); } +namespace +{ + +Reference< XInterface > invokeComponentFactory( + oslGenericFunction pGetter, + oslModule lib, + OUString const & rModulePath, + OUString const & rImplName, + Reference< ::com::sun::star::lang::XMultiServiceFactory > const & xMgr, + Reference< ::com::sun::star::registry::XRegistryKey > const & xKey, + OUString const & rPrefix, + OUString &rExcMsg ) +{ + Reference< XInterface > xRet; + uno::Environment currentEnv(Environment::getCurrent()); + uno::Environment env; + OUString aEnvTypeName; + + getLibEnv(lib, &env, &aEnvTypeName, currentEnv, rImplName, rPrefix); + + OString aImplName( + OUStringToOString( rImplName, RTL_TEXTENCODING_ASCII_US ) ); + + if (!env.is()) + env = uno::Environment(aEnvTypeName); + + if (env.is() && currentEnv.is()) + { +#if OSL_DEBUG_LEVEL > 1 + { + rtl::OString modPath(rtl::OUStringToOString(rModulePath, RTL_TEXTENCODING_ASCII_US)); + rtl::OString implName(rtl::OUStringToOString(rImplName, RTL_TEXTENCODING_ASCII_US)); + rtl::OString envDcp(rtl::OUStringToOString(env.getTypeName(), RTL_TEXTENCODING_ASCII_US)); + + fprintf(stderr, "loadSharedLibComponentFactory envDcp: %-12.12s implName: %30.30s modPath: %-15.15s\n", envDcp.getStr(), implName.getStr() + (implName.getLength() > 30 ? implName.getLength() - 30 : 0), modPath.getStr()); + } +#endif + + Mapping aCurrent2Env( currentEnv, env ); + Mapping aEnv2Current( env, currentEnv ); + + if (aCurrent2Env.is() && aEnv2Current.is()) + { + void * pSMgr = aCurrent2Env.mapInterface( + xMgr.get(), ::getCppuType( &xMgr ) ); + void * pKey = aCurrent2Env.mapInterface( + xKey.get(), ::getCppuType( &xKey ) ); + + void * pSSF = NULL; + + env.invoke(s_getFactory, pGetter, &aImplName, pSMgr, pKey, &pSSF); + + if (pKey) + { + (env.get()->pExtEnv->releaseInterface)( + env.get()->pExtEnv, pKey ); + } + if (pSMgr) + { + (*env.get()->pExtEnv->releaseInterface)( + env.get()->pExtEnv, pSMgr ); + } + + if (pSSF) + { + aEnv2Current.mapInterface( + reinterpret_cast< void ** >( &xRet ), + pSSF, ::getCppuType( &xRet ) ); + (env.get()->pExtEnv->releaseInterface)( + env.get()->pExtEnv, pSSF ); + } + else + { + rExcMsg = rModulePath; + rExcMsg += OUSTR(": cannot get factory of " + "demanded implementation: "); + rExcMsg += OStringToOUString( + aImplName, RTL_TEXTENCODING_ASCII_US ); + } + } + else + { + rExcMsg = + OUSTR("cannot get uno mappings: C++ <=> UNO!"); + } + } + else + { + rExcMsg = OUSTR("cannot get uno environments!"); + } + + return xRet; +} + +} // namespace + Reference< XInterface > SAL_CALL loadSharedLibComponentFactory( OUString const & rLibName, OUString const & rPath, OUString const & rImplName, @@ -384,89 +480,13 @@ Reference< XInterface > SAL_CALL loadSharedLibComponentFactory( Reference< XInterface > xRet; - uno::Environment currentEnv(Environment::getCurrent()); - uno::Environment env; - - OUString aEnvTypeName; - OUString aExcMsg; - getLibEnv(lib, &env, &aEnvTypeName, currentEnv, rImplName, rPrefix); - OUString aGetFactoryName = rPrefix + OUSTR(COMPONENT_GETFACTORY); oslGenericFunction pSym = osl_getFunctionSymbol( lib, aGetFactoryName.pData ); if (pSym != 0) { - OString aImplName( - OUStringToOString( rImplName, RTL_TEXTENCODING_ASCII_US ) ); - - if (!env.is()) - env = uno::Environment(aEnvTypeName); - - if (env.is() && currentEnv.is()) - { -#if OSL_DEBUG_LEVEL > 1 - { - rtl::OString libName(rtl::OUStringToOString(rLibName, RTL_TEXTENCODING_ASCII_US)); - rtl::OString implName(rtl::OUStringToOString(rImplName, RTL_TEXTENCODING_ASCII_US)); - rtl::OString envDcp(rtl::OUStringToOString(env.getTypeName(), RTL_TEXTENCODING_ASCII_US)); - - fprintf(stderr, "loadSharedLibComponentFactory envDcp: %-12.12s implName: %30.30s libName: %-15.15s\n", envDcp.getStr(), implName.getStr() + (implName.getLength() > 30 ? implName.getLength() - 30 : 0), libName.getStr()); - } -#endif - - Mapping aCurrent2Env( currentEnv, env ); - Mapping aEnv2Current( env, currentEnv ); - - if (aCurrent2Env.is() && aEnv2Current.is()) - { - void * pSMgr = aCurrent2Env.mapInterface( - xMgr.get(), ::getCppuType( &xMgr ) ); - void * pKey = aCurrent2Env.mapInterface( - xKey.get(), ::getCppuType( &xKey ) ); - - void * pSSF = NULL; - - env.invoke(s_getFactory, pSym, &aImplName, pSMgr, pKey, &pSSF); - - if (pKey) - { - (env.get()->pExtEnv->releaseInterface)( - env.get()->pExtEnv, pKey ); - } - if (pSMgr) - { - (*env.get()->pExtEnv->releaseInterface)( - env.get()->pExtEnv, pSMgr ); - } - - if (pSSF) - { - aEnv2Current.mapInterface( - reinterpret_cast< void ** >( &xRet ), - pSSF, ::getCppuType( &xRet ) ); - (env.get()->pExtEnv->releaseInterface)( - env.get()->pExtEnv, pSSF ); - } - else - { - aExcMsg = aModulePath; - aExcMsg += OUSTR(": cannot get factory of " - "demanded implementation: "); - aExcMsg += OStringToOUString( - aImplName, RTL_TEXTENCODING_ASCII_US ); - } - } - else - { - aExcMsg = - OUSTR("cannot get uno mappings: C++ <=> UNO!"); - } - } - else - { - aExcMsg = OUSTR("cannot get uno environments!"); - } + xRet = invokeComponentFactory( pSym, lib, aModulePath, rImplName, xMgr, xKey, rPrefix, aExcMsg ); } else { @@ -492,6 +512,37 @@ Reference< XInterface > SAL_CALL loadSharedLibComponentFactory( return xRet; } +Reference< XInterface > SAL_CALL invokeStaticComponentFactory( + oslGenericFunction pGetter, + OUString const & rImplName, + Reference< ::com::sun::star::lang::XMultiServiceFactory > const & xMgr, + Reference< ::com::sun::star::registry::XRegistryKey > const & xKey, + OUString const & rPrefix ) + SAL_THROW( (::com::sun::star::loader::CannotActivateFactoryException) ) +{ + Reference< XInterface > xRet; + oslModule pExe; + OUString aExePath(OUSTR("MAIN")); + osl_getModuleHandle( NULL, &pExe ); + OUString aExcMsg; + + xRet = invokeComponentFactory( pGetter, pExe, aExePath, rImplName, xMgr, xKey, rPrefix, aExcMsg ); + + if (! xRet.is()) + { +#if OSL_DEBUG_LEVEL > 1 + out( "### cannot activate factory: " ); + out( aExcMsg ); + out( "\n" ); +#endif + throw loader::CannotActivateFactoryException( + aExcMsg, + Reference< XInterface >() ); + } + + return xRet; +} + //============================================================================== extern "C" { static void s_writeInfo(va_list * pParam) { |