1 /************************************************************** 2 * 3 * Licensed to the Apache Software Foundation (ASF) under one 4 * or more contributor license agreements. See the NOTICE file 5 * distributed with this work for additional information 6 * regarding copyright ownership. The ASF licenses this file 7 * to you under the Apache License, Version 2.0 (the 8 * "License"); you may not use this file except in compliance 9 * with the License. You may obtain a copy of the License at 10 * 11 * http://www.apache.org/licenses/LICENSE-2.0 12 * 13 * Unless required by applicable law or agreed to in writing, 14 * software distributed under the License is distributed on an 15 * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 16 * KIND, either express or implied. See the License for the 17 * specific language governing permissions and limitations 18 * under the License. 19 * 20 *************************************************************/ 21 22 23 24 #include "componentmodule.hxx" 25 #include <tools/resmgr.hxx> 26 #ifndef _SOLAR_HRC 27 #include <svl/solar.hrc> 28 #endif 29 #include <comphelper/sequence.hxx> 30 #include <tools/debug.hxx> 31 32 #define ENTER_MOD_METHOD() \ 33 ::osl::MutexGuard aGuard(s_aMutex); \ 34 ensureImpl() 35 36 //......................................................................... 37 namespace COMPMOD_NAMESPACE 38 { 39 //......................................................................... 40 41 using namespace ::com::sun::star::uno; 42 using namespace ::com::sun::star::lang; 43 using namespace ::com::sun::star::registry; 44 using namespace ::comphelper; 45 using namespace ::cppu; 46 47 //========================================================================= 48 //= OModuleImpl 49 //========================================================================= 50 /** implementation for <type>OModule</type>. not threadsafe, has to be guarded by it's owner 51 */ 52 class OModuleImpl 53 { 54 ResMgr* m_pRessources; 55 sal_Bool m_bInitialized; 56 ByteString m_sFilePrefix; 57 58 public: 59 /// ctor 60 OModuleImpl(); 61 ~OModuleImpl(); 62 63 /// get the manager for the ressources of the module 64 ResMgr* getResManager(); setResourceFilePrefix(const::rtl::OString & _rPrefix)65 void setResourceFilePrefix(const ::rtl::OString& _rPrefix) { m_sFilePrefix = _rPrefix; } 66 }; 67 68 //------------------------------------------------------------------------- OModuleImpl()69 OModuleImpl::OModuleImpl() 70 :m_pRessources(NULL) 71 ,m_bInitialized(sal_False) 72 { 73 } 74 75 //------------------------------------------------------------------------- ~OModuleImpl()76 OModuleImpl::~OModuleImpl() 77 { 78 if (m_pRessources) 79 delete m_pRessources; 80 } 81 82 //------------------------------------------------------------------------- getResManager()83 ResMgr* OModuleImpl::getResManager() 84 { 85 // note that this method is not threadsafe, which counts for the whole class ! 86 if (!m_pRessources && !m_bInitialized) 87 { 88 DBG_ASSERT(m_sFilePrefix.Len(), "OModuleImpl::getResManager: no resource file prefix!"); 89 // create a manager with a fixed prefix 90 ByteString aMgrName = m_sFilePrefix; 91 92 m_pRessources = ResMgr::CreateResMgr(aMgrName.GetBuffer()); 93 DBG_ASSERT(m_pRessources, 94 (ByteString("OModuleImpl::getResManager: could not create the resource manager (file name: ") 95 += aMgrName 96 += ByteString(")!")).GetBuffer()); 97 98 m_bInitialized = sal_True; 99 } 100 return m_pRessources; 101 } 102 103 //========================================================================= 104 //= OModule 105 //========================================================================= 106 ::osl::Mutex OModule::s_aMutex; 107 sal_Int32 OModule::s_nClients = 0; 108 OModuleImpl* OModule::s_pImpl = NULL; 109 ::rtl::OString OModule::s_sResPrefix; 110 //------------------------------------------------------------------------- getResManager()111 ResMgr* OModule::getResManager() 112 { 113 ENTER_MOD_METHOD(); 114 return s_pImpl->getResManager(); 115 } 116 117 //------------------------------------------------------------------------- setResourceFilePrefix(const::rtl::OString & _rPrefix)118 void OModule::setResourceFilePrefix(const ::rtl::OString& _rPrefix) 119 { 120 ::osl::MutexGuard aGuard(s_aMutex); 121 s_sResPrefix = _rPrefix; 122 if (s_pImpl) 123 s_pImpl->setResourceFilePrefix(_rPrefix); 124 } 125 126 //------------------------------------------------------------------------- registerClient()127 void OModule::registerClient() 128 { 129 ::osl::MutexGuard aGuard(s_aMutex); 130 ++s_nClients; 131 } 132 133 //------------------------------------------------------------------------- revokeClient()134 void OModule::revokeClient() 135 { 136 ::osl::MutexGuard aGuard(s_aMutex); 137 if (!--s_nClients && s_pImpl) 138 { 139 delete s_pImpl; 140 s_pImpl = NULL; 141 } 142 } 143 144 //------------------------------------------------------------------------- ensureImpl()145 void OModule::ensureImpl() 146 { 147 if (s_pImpl) 148 return; 149 s_pImpl = new OModuleImpl(); 150 s_pImpl->setResourceFilePrefix(s_sResPrefix); 151 } 152 153 //-------------------------------------------------------------------------- 154 //- registration helper 155 //-------------------------------------------------------------------------- 156 157 Sequence< ::rtl::OUString >* OModule::s_pImplementationNames = NULL; 158 Sequence< Sequence< ::rtl::OUString > >* OModule::s_pSupportedServices = NULL; 159 Sequence< sal_Int64 >* OModule::s_pCreationFunctionPointers = NULL; 160 Sequence< sal_Int64 >* OModule::s_pFactoryFunctionPointers = NULL; 161 162 //-------------------------------------------------------------------------- registerComponent(const::rtl::OUString & _rImplementationName,const Sequence<::rtl::OUString> & _rServiceNames,ComponentInstantiation _pCreateFunction,FactoryInstantiation _pFactoryFunction)163 void OModule::registerComponent( 164 const ::rtl::OUString& _rImplementationName, 165 const Sequence< ::rtl::OUString >& _rServiceNames, 166 ComponentInstantiation _pCreateFunction, 167 FactoryInstantiation _pFactoryFunction) 168 { 169 if (!s_pImplementationNames) 170 { 171 OSL_ENSURE(!s_pSupportedServices && !s_pCreationFunctionPointers && !s_pFactoryFunctionPointers, 172 "OModule::registerComponent : inconsistent state (the pointers (1)) !"); 173 s_pImplementationNames = new Sequence< ::rtl::OUString >; 174 s_pSupportedServices = new Sequence< Sequence< ::rtl::OUString > >; 175 s_pCreationFunctionPointers = new Sequence< sal_Int64 >; 176 s_pFactoryFunctionPointers = new Sequence< sal_Int64 >; 177 } 178 OSL_ENSURE(s_pImplementationNames && s_pSupportedServices && s_pCreationFunctionPointers && s_pFactoryFunctionPointers, 179 "OModule::registerComponent : inconsistent state (the pointers (2)) !"); 180 181 OSL_ENSURE( (s_pImplementationNames->getLength() == s_pSupportedServices->getLength()) 182 && (s_pImplementationNames->getLength() == s_pCreationFunctionPointers->getLength()) 183 && (s_pImplementationNames->getLength() == s_pFactoryFunctionPointers->getLength()), 184 "OModule::registerComponent : inconsistent state !"); 185 186 sal_Int32 nOldLen = s_pImplementationNames->getLength(); 187 s_pImplementationNames->realloc(nOldLen + 1); 188 s_pSupportedServices->realloc(nOldLen + 1); 189 s_pCreationFunctionPointers->realloc(nOldLen + 1); 190 s_pFactoryFunctionPointers->realloc(nOldLen + 1); 191 192 s_pImplementationNames->getArray()[nOldLen] = _rImplementationName; 193 s_pSupportedServices->getArray()[nOldLen] = _rServiceNames; 194 s_pCreationFunctionPointers->getArray()[nOldLen] = reinterpret_cast<sal_Int64>(_pCreateFunction); 195 s_pFactoryFunctionPointers->getArray()[nOldLen] = reinterpret_cast<sal_Int64>(_pFactoryFunction); 196 } 197 198 //-------------------------------------------------------------------------- revokeComponent(const::rtl::OUString & _rImplementationName)199 void OModule::revokeComponent(const ::rtl::OUString& _rImplementationName) 200 { 201 if (!s_pImplementationNames) 202 { 203 OSL_ASSERT("OModule::revokeComponent : have no class infos ! Are you sure called this method at the right time ?"); 204 return; 205 } 206 OSL_ENSURE(s_pImplementationNames && s_pSupportedServices && s_pCreationFunctionPointers && s_pFactoryFunctionPointers, 207 "OModule::revokeComponent : inconsistent state (the pointers) !"); 208 OSL_ENSURE( (s_pImplementationNames->getLength() == s_pSupportedServices->getLength()) 209 && (s_pImplementationNames->getLength() == s_pCreationFunctionPointers->getLength()) 210 && (s_pImplementationNames->getLength() == s_pFactoryFunctionPointers->getLength()), 211 "OModule::revokeComponent : inconsistent state !"); 212 213 sal_Int32 nLen = s_pImplementationNames->getLength(); 214 const ::rtl::OUString* pImplNames = s_pImplementationNames->getConstArray(); 215 for (sal_Int32 i=0; i<nLen; ++i, ++pImplNames) 216 { 217 if (pImplNames->equals(_rImplementationName)) 218 { 219 removeElementAt(*s_pImplementationNames, i); 220 removeElementAt(*s_pSupportedServices, i); 221 removeElementAt(*s_pCreationFunctionPointers, i); 222 removeElementAt(*s_pFactoryFunctionPointers, i); 223 break; 224 } 225 } 226 227 if (s_pImplementationNames->getLength() == 0) 228 { 229 delete s_pImplementationNames; s_pImplementationNames = NULL; 230 delete s_pSupportedServices; s_pSupportedServices = NULL; 231 delete s_pCreationFunctionPointers; s_pCreationFunctionPointers = NULL; 232 delete s_pFactoryFunctionPointers; s_pFactoryFunctionPointers = NULL; 233 } 234 } 235 236 //-------------------------------------------------------------------------- getComponentFactory(const::rtl::OUString & _rImplementationName,const Reference<XMultiServiceFactory> & _rxServiceManager)237 Reference< XInterface > OModule::getComponentFactory( 238 const ::rtl::OUString& _rImplementationName, 239 const Reference< XMultiServiceFactory >& _rxServiceManager) 240 { 241 OSL_ENSURE(_rxServiceManager.is(), "OModule::getComponentFactory : invalid argument (service manager) !"); 242 OSL_ENSURE(_rImplementationName.getLength(), "OModule::getComponentFactory : invalid argument (implementation name) !"); 243 244 if (!s_pImplementationNames) 245 { 246 OSL_ASSERT("OModule::getComponentFactory : have no class infos ! Are you sure called this method at the right time ?"); 247 return NULL; 248 } 249 OSL_ENSURE(s_pImplementationNames && s_pSupportedServices && s_pCreationFunctionPointers && s_pFactoryFunctionPointers, 250 "OModule::getComponentFactory : inconsistent state (the pointers) !"); 251 OSL_ENSURE( (s_pImplementationNames->getLength() == s_pSupportedServices->getLength()) 252 && (s_pImplementationNames->getLength() == s_pCreationFunctionPointers->getLength()) 253 && (s_pImplementationNames->getLength() == s_pFactoryFunctionPointers->getLength()), 254 "OModule::getComponentFactory : inconsistent state !"); 255 256 257 Reference< XInterface > xReturn; 258 259 260 sal_Int32 nLen = s_pImplementationNames->getLength(); 261 const ::rtl::OUString* pImplName = s_pImplementationNames->getConstArray(); 262 const Sequence< ::rtl::OUString >* pServices = s_pSupportedServices->getConstArray(); 263 const sal_Int64* pComponentFunction = s_pCreationFunctionPointers->getConstArray(); 264 const sal_Int64* pFactoryFunction = s_pFactoryFunctionPointers->getConstArray(); 265 266 for (sal_Int32 i=0; i<nLen; ++i, ++pImplName, ++pServices, ++pComponentFunction, ++pFactoryFunction) 267 { 268 if (pImplName->equals(_rImplementationName)) 269 { 270 const FactoryInstantiation FactoryInstantiationFunction = reinterpret_cast<const FactoryInstantiation>(*pFactoryFunction); 271 const ComponentInstantiation ComponentInstantiationFunction = reinterpret_cast<const ComponentInstantiation>(*pComponentFunction); 272 273 xReturn = FactoryInstantiationFunction( _rxServiceManager, *pImplName, ComponentInstantiationFunction, *pServices, NULL); 274 if (xReturn.is()) 275 { 276 xReturn->acquire(); 277 return xReturn.get(); 278 } 279 } 280 } 281 282 return NULL; 283 } 284 285 286 //......................................................................... 287 } // namespace COMPMOD_NAMESPACE 288 //......................................................................... 289 290