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 // MARKER(update_precomp.py): autogen include statement, do not remove 25 #include "precompiled_sot.hxx" 26 27 #define _SOT_FACTORY_CXX 28 #define SOT_STRING_LIST 29 30 #include <sot/factory.hxx> 31 #include <tools/debug.hxx> 32 #include <tools/string.hxx> 33 #include <sot/object.hxx> 34 #include <sot/sotdata.hxx> 35 #include <sot/clsids.hxx> 36 #include <rtl/instance.hxx> 37 #include <com/sun/star/datatransfer/DataFlavor.hpp> 38 39 /************** class SotData_Impl *********************************************/ 40 /************************************************************************* 41 |* SotData_Impl::SotData_Impl 42 |* 43 |* Beschreibung 44 *************************************************************************/ 45 SotData_Impl::SotData_Impl() 46 : nSvObjCount( 0 ) 47 , pObjectList( NULL ) 48 , pFactoryList( NULL ) 49 , pSotObjectFactory( NULL ) 50 , pSotStorageStreamFactory( NULL ) 51 , pSotStorageFactory( NULL ) 52 , pDataFlavorList( NULL ) 53 { 54 } 55 /************************************************************************* 56 |* SOTDATA() 57 |* 58 |* Beschreibung 59 *************************************************************************/ 60 namespace { struct ImplData : public rtl::Static<SotData_Impl, ImplData> {}; } 61 SotData_Impl * SOTDATA() 62 { 63 return &ImplData::get(); 64 } 65 66 /************************************************************************* 67 |* SotFactory::DeInit() 68 |* 69 |* Beschreibung 70 *************************************************************************/ 71 void SotFactory::DeInit() 72 { 73 SotData_Impl * pSotData = SOTDATA(); 74 75 if( pSotData->nSvObjCount ) 76 { 77 #ifdef DBG_UTIL 78 ByteString aStr( "Objects alive: " ); 79 aStr.Append( ByteString::CreateFromInt32( pSotData->nSvObjCount ) ); 80 DBG_WARNING( aStr.GetBuffer() ); 81 82 /* 83 SotObjectList *pObjList = pSotData->pObjectList; 84 85 if( pObjList ) 86 { 87 SotObject * p = pObjList->First(); 88 while( p ) 89 { 90 String aStr( "Factory: " ); 91 aStr += p->GetSvFactory()->GetClassName(); 92 aStr += " Count: "; 93 aStr += p->GetRefCount(); 94 DBG_TRACE( "\tReferences:" ); 95 p->TestObjRef( sal_False ); 96 #ifdef TEST_INVARIANT 97 DBG_TRACE( "\tInvariant:" ); 98 p->TestInvariant( sal_True ); 99 #endif 100 p = pObjList->Next(); 101 } 102 } 103 */ 104 #endif 105 return; 106 } 107 108 // Muss von hinten nach vorne zerstoert werden. Das ist die umgekehrte 109 // Reihenfolge der Erzeugung 110 SotFactoryList* pFactoryList = pSotData->pFactoryList; 111 if( pFactoryList ) 112 { 113 SotFactory * pFact = pFactoryList->Last(); 114 while( NULL != (pFact = pFactoryList->Remove()) ) 115 { 116 delete pFact; 117 pFact = pFactoryList->Last(); 118 } 119 delete pFactoryList; 120 pSotData->pFactoryList = NULL; 121 } 122 123 delete pSotData->pObjectList; 124 pSotData->pObjectList = NULL; 125 if( pSotData->pDataFlavorList ) 126 { 127 128 for( sal_uLong i = 0, nMax = pSotData->pDataFlavorList->Count(); i < nMax; i++ ) 129 delete (::com::sun::star::datatransfer::DataFlavor*) pSotData->pDataFlavorList->GetObject( i ); 130 delete pSotData->pDataFlavorList; 131 pSotData->pDataFlavorList = NULL; 132 } 133 //delete pSOTDATA(); 134 //SOTDATA() = NULL; 135 } 136 137 138 /************** class SotFactory *****************************************/ 139 /************************************************************************* 140 |* SotFactory::SotFactory() 141 |* 142 |* Beschreibung 143 *************************************************************************/ 144 TYPEINIT0(SotFactory); 145 146 SotFactory::SotFactory( const SvGlobalName & rName, 147 const String & rClassName, 148 CreateInstanceType pCreateFuncP ) 149 : SvGlobalName ( rName ) 150 , nSuperCount ( 0 ) 151 , pSuperClasses ( NULL ) 152 , pCreateFunc ( pCreateFuncP ) 153 , aClassName ( rClassName ) 154 { 155 #ifdef DBG_UTIL 156 SvGlobalName aEmptyName; 157 if( aEmptyName != *this ) 158 { // wegen Sfx-BasicFactories 159 DBG_ASSERT( aEmptyName != *this, "create factory without SvGlobalName" ); 160 if( Find( *this ) ) 161 { 162 /* 163 String aStr( GetClassName() ); 164 aStr += ", UniqueName: "; 165 aStr += GetHexName(); 166 aStr += ", create factories with the same unique name"; 167 DBG_ERROR( aStr ); 168 */ 169 DBG_ERROR( "create factories with the same unique name" ); 170 } 171 } 172 #endif 173 SotData_Impl * pSotData = SOTDATA(); 174 if( !pSotData->pFactoryList ) 175 pSotData->pFactoryList = new SotFactoryList(); 176 // muss nach hinten, wegen Reihenfolge beim zerstoeren 177 pSotData->pFactoryList->Insert( this, LIST_APPEND ); 178 } 179 180 181 //========================================================================= 182 SotFactory::~SotFactory() 183 { 184 delete [] pSuperClasses; 185 } 186 187 188 /************************************************************************* 189 |* SotFactory:: 190 |* 191 |* Beschreibung Zugriffsmethoden auf SotData_Impl-Daten 192 *************************************************************************/ 193 sal_uInt32 SotFactory::GetSvObjectCount() 194 { 195 return SOTDATA()->nSvObjCount; 196 } 197 198 199 const SotFactoryList * SotFactory::GetFactoryList() 200 { 201 return SOTDATA()->pFactoryList; 202 } 203 204 /************************************************************************* 205 |* SotFactory::Find() 206 |* 207 |* Beschreibung 208 *************************************************************************/ 209 const SotFactory* SotFactory::Find( const SvGlobalName & rFactName ) 210 { 211 SvGlobalName aEmpty; 212 SotData_Impl * pSotData = SOTDATA(); 213 if( rFactName != aEmpty && pSotData->pFactoryList ) 214 { 215 SotFactory * pFact = pSotData->pFactoryList->First(); 216 while( pFact ) 217 { 218 if( *pFact == rFactName ) 219 return pFact; 220 pFact = pSotData->pFactoryList->Next(); 221 } 222 } 223 224 return 0; 225 } 226 227 /************************************************************************* 228 |* SotFactory::PutSuperClass() 229 |* 230 |* Beschreibung 231 *************************************************************************/ 232 void SotFactory::PutSuperClass( const SotFactory * pFact ) 233 { 234 nSuperCount++; 235 if( !pSuperClasses ) 236 pSuperClasses = new const SotFactory * [ nSuperCount ]; 237 else 238 { 239 const SotFactory ** pTmp = new const SotFactory * [ nSuperCount ]; 240 memcpy( (void *)pTmp, (void *)pSuperClasses, 241 sizeof( void * ) * (nSuperCount -1) ); 242 delete [] pSuperClasses; 243 pSuperClasses = pTmp; 244 } 245 pSuperClasses[ nSuperCount -1 ] = pFact; 246 } 247 248 249 /************************************************************************* 250 |* SotFactory::IncSvObjectCount() 251 |* 252 |* Beschreibung 253 *************************************************************************/ 254 void SotFactory::IncSvObjectCount( SotObject * pObj ) 255 { 256 SotData_Impl * pSotData = SOTDATA(); 257 pSotData->nSvObjCount++; 258 if( !pSotData->pObjectList ) 259 pSotData->pObjectList = new SotObjectList(); 260 if( pObj ) 261 pSotData->pObjectList->Insert( pObj ); 262 } 263 264 265 /************************************************************************* 266 |* SotFactory::DecSvObjectCount() 267 |* 268 |* Beschreibung 269 *************************************************************************/ 270 void SotFactory::DecSvObjectCount( SotObject * pObj ) 271 { 272 SotData_Impl * pSotData = SOTDATA(); 273 pSotData->nSvObjCount--; 274 if( pObj ) 275 pSotData->pObjectList->Remove( pObj ); 276 if( !pSotData->nSvObjCount ) 277 { 278 //keine internen und externen Referenzen mehr 279 } 280 } 281 282 283 /************************************************************************* 284 |* SotFactory::TestInvariant() 285 |* 286 |* Beschreibung 287 *************************************************************************/ 288 void SotFactory::TestInvariant() 289 { 290 #ifdef TEST_INVARIANT 291 SotData_Impl * pSotData = SOTDATA(); 292 if( pSotData->pObjectList ) 293 { 294 sal_uLong nCount = pSotData->pObjectList->Count(); 295 for( sal_uLong i = 0; i < nCount ; i++ ) 296 { 297 pSotData->pObjectList->GetObject( i )->TestInvariant( sal_False ); 298 } 299 } 300 #endif 301 } 302 303 /************************************************************************* 304 |* SotFactory::CreateInstance() 305 |* 306 |* Beschreibung 307 *************************************************************************/ 308 void * SotFactory::CreateInstance( SotObject ** ppObj ) const 309 { 310 DBG_ASSERT( pCreateFunc, "SotFactory::CreateInstance: pCreateFunc == 0" ); 311 return pCreateFunc( ppObj ); 312 } 313 314 //========================================================================= 315 void * SotFactory::CastAndAddRef 316 ( 317 SotObject * pObj /* Das Objekt von dem der Typ gepr"uft wird. */ 318 ) const 319 /* [Beschreibung] 320 321 Ist eine Optimierung, damit die Ref-Klassen k"urzer implementiert 322 werden k"onnen. pObj wird auf den Typ der Factory gecastet. 323 In c++ (wenn es immer erlaubt w"are) w"urde der void * wie im 324 Beispiel gebildet. 325 Factory der Klasse SvPersist. 326 void * p = (void *)(SvPersist *)pObj; 327 328 [R"uckgabewert] 329 330 void *, NULL, pObj war NULL oder das Objekt war nicht vom Typ 331 der Factory. 332 Ansonsten wird pObj zuerst auf den Typ der Factory 333 gecastet und dann auf void *. 334 335 [Querverweise] 336 337 <SotObject::CastAndAddRef> 338 */ 339 { 340 return pObj ? pObj->CastAndAddRef( this ) : NULL; 341 } 342 343 /************************************************************************* 344 |* SotFactory::Is() 345 |* 346 |* Beschreibung 347 *************************************************************************/ 348 sal_Bool SotFactory::Is( const SotFactory * pSuperCl ) const 349 { 350 if( this == pSuperCl ) 351 return sal_True; 352 353 for( sal_uInt16 i = 0; i < nSuperCount; i++ ) 354 { 355 if( pSuperClasses[ i ]->Is( pSuperCl ) ) 356 return sal_True; 357 } 358 return sal_False; 359 } 360 361 362 363 364