changed: auto add updateData callback to stages so that stagedata can be updated...
[opensg.git] / Source / Base / Threading / OSGThreadManager.cpp
blob29aaf13e3f4c0c16016fc1751133415a91c774f1
1 /*---------------------------------------------------------------------------*\
2 * OpenSG *
3 * *
4 * *
5 * Copyright (C) 2000-2003 by the OpenSG Forum *
6 * *
7 * www.opensg.org *
8 * *
9 * contact: dirk@opensg.org, gerrit.voss@vossg.org, jbehr@zgdv.de *
10 * *
11 \*---------------------------------------------------------------------------*/
12 /*---------------------------------------------------------------------------*\
13 * License *
14 * *
15 * This library is free software; you can redistribute it and/or modify it *
16 * under the terms of the GNU Library General Public License as published *
17 * by the Free Software Foundation, version 2. *
18 * *
19 * This library is distributed in the hope that it will be useful, but *
20 * WITHOUT ANY WARRANTY; without even the implied warranty of *
21 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU *
22 * Library General Public License for more details. *
23 * *
24 * You should have received a copy of the GNU Library General Public *
25 * License along with this library; if not, write to the Free Software *
26 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. *
27 * *
28 \*---------------------------------------------------------------------------*/
29 /*---------------------------------------------------------------------------*\
30 * Changes *
31 * *
32 * *
33 * *
34 * *
35 * *
36 * *
37 \*---------------------------------------------------------------------------*/
39 #include <cstdlib>
40 #include <cstdio>
42 #include "OSGConfig.h"
44 #if defined(OSG_USE_SPROC)
45 #include <cerrno>
46 #endif
48 #include <iostream>
50 #include "OSGThreadManager.h"
51 #include "OSGBaseInitFunctions.h"
53 #include "OSGThread.h"
55 OSG_USING_NAMESPACE
57 ThreadManager *ThreadManager::_pThreadManager = NULL;
58 BaseThreadRefPtr ThreadManager::_pAppThread = NULL;
60 bool ThreadManager::_bShutdownInProgress = false;
62 Char8 *ThreadManager::_szAppThreadType = NULL;
65 /*-------------------------- Get / Set ------------------------------------*/
67 void ThreadManager::setAppThreadType(const Char8 *szAppThreadType)
69 osgStringDup(szAppThreadType, _szAppThreadType);
73 ThreadManager *ThreadManager::the(void)
75 if(_pThreadManager == NULL)
76 _pThreadManager = new ThreadManager();
78 return _pThreadManager;
82 BaseThread *ThreadManager::getAppThread(void)
84 return _pAppThread;
88 /*-------------------- Create Threading Elements --------------------------*/
90 BaseThreadTransitPtr ThreadManager::getThread(const Char8 *szName,
91 UInt32 bGlobal,
92 const Char8 *szTypeName)
94 BaseThreadTransitPtr returnValue(NULL);
96 _storePLock->acquire();
98 returnValue = _sThreadStore.getMPField(szName, szTypeName, bGlobal != 0);
100 _storePLock->release();
102 return returnValue;
105 BarrierTransitPtr ThreadManager::getBarrier(const Char8 *szName,
106 UInt32 bGlobal,
107 const Char8 *szTypeName)
109 BarrierTransitPtr returnValue(NULL);
111 _storePLock->acquire();
113 returnValue = _sBarrierStore.getMPField(szName, szTypeName, bGlobal != 0);
115 _storePLock->release();
117 return returnValue;
120 CondVarTransitPtr ThreadManager::getCondVar(const Char8 *szName,
121 UInt32 bGlobal,
122 const Char8 *szTypeName)
124 CondVarTransitPtr returnValue(NULL);
126 _storePLock->acquire();
128 returnValue = _sCondVarStore.getMPField(szName, szTypeName, bGlobal != 0);
130 _storePLock->release();
132 return returnValue;
135 LockTransitPtr ThreadManager::getLock(const Char8 *szName,
136 UInt32 bGlobal,
137 const Char8 *szTypeName)
139 LockTransitPtr returnValue(NULL);
141 _storePLock->acquire();
143 returnValue = _sLockStore.getMPField(szName, szTypeName, bGlobal != 0);
145 _storePLock->release();
147 return returnValue;
150 LockPoolTransitPtr ThreadManager::getLockPool(const Char8 *szName,
151 UInt32 bGlobal,
152 const Char8 *szTypeName)
154 LockPoolTransitPtr returnValue(NULL);
156 _storePLock->acquire();
158 returnValue = _sLockPoolStore.getMPField(szName, szTypeName, bGlobal != 0);
160 _storePLock->release();
162 return returnValue;
165 SemaphoreTransitPtr ThreadManager::getSemaphore(const Char8 *szName,
166 UInt32 bGlobal,
167 const Char8 *szTypeName)
169 SemaphoreTransitPtr returnValue(NULL);
171 _storePLock->acquire();
173 returnValue = _sSemaphoreStore.getMPField(szName, szTypeName, bGlobal != 0);
175 _storePLock->release();
177 return returnValue;
180 BaseThread *ThreadManager::findThread(const Char8 *szName)
182 BaseThread *returnValue = NULL;
184 _storePLock->acquire();
186 returnValue = _sThreadStore.findMPField(szName);
188 _storePLock->release();
190 return returnValue;
193 Barrier *ThreadManager::findBarrier(const Char8 *szName)
195 Barrier *returnValue = NULL;
197 _storePLock->acquire();
199 returnValue = _sBarrierStore.findMPField(szName);
201 _storePLock->release();
203 return returnValue;
206 CondVar *ThreadManager::findCondVar(const Char8 *szName)
208 CondVar *returnValue = NULL;
210 _storePLock->acquire();
212 returnValue = _sCondVarStore.findMPField(szName);
214 _storePLock->release();
216 return returnValue;
219 Lock *ThreadManager::findLock(const Char8 *szName)
221 Lock *returnValue = NULL;
223 _storePLock->acquire();
225 returnValue = _sLockStore.findMPField(szName);
227 _storePLock->release();
229 return returnValue;
232 LockPool *ThreadManager::findLockPool(const Char8 *szName)
234 LockPool *returnValue = NULL;
236 _storePLock->acquire();
238 returnValue = _sLockPoolStore.findMPField(szName);
240 _storePLock->release();
242 return returnValue;
245 Semaphore *ThreadManager::findSemaphore(const Char8 *szName)
247 Semaphore *returnValue = NULL;
249 _storePLock->acquire();
251 returnValue = _sSemaphoreStore.findMPField(szName);
253 _storePLock->release();
255 return returnValue;
258 void ThreadManager::dump(void)
260 ThreadStore::MPFieldMapCIt tI = _sThreadStore._mFieldMap.begin();
261 ThreadStore::MPFieldMapCIt tE = _sThreadStore._mFieldMap.end ();
263 for(; tI != tE; ++tI)
265 FLOG(("ThreadManager::dump: "
266 "thread [%s|%p] is still alive ([%d]). \n",
267 (*tI).first.c_str(),
268 (*tI).second,
269 (*tI).second->exists()));
272 BarrierStore::MPFieldMapCIt bI = _sBarrierStore._mFieldMap.begin();
273 BarrierStore::MPFieldMapCIt bE = _sBarrierStore._mFieldMap.end ();
275 for(; bI != bE; ++bI)
277 FINFO(("ThreadManager::dump: "
278 "barrier [%s|%p] is still alive\n",
279 (*bI).first.c_str(),
280 (*bI).second));
284 CondVarStore::MPFieldMapCIt cI = _sCondVarStore._mFieldMap.begin();
285 CondVarStore::MPFieldMapCIt cE = _sCondVarStore._mFieldMap.end ();
287 for(; cI != cE; ++cI)
289 FLOG(("ThreadManager::dump: "
290 "condvar [%s|%p] is still alive\n",
291 (*cI).first.c_str(),
292 (*cI).second));
296 LockStore::MPFieldMapCIt lI = _sLockStore._mFieldMap.begin();
297 LockStore::MPFieldMapCIt lE = _sLockStore._mFieldMap.end ();
299 for(; lI != lE; ++lI)
301 FLOG(("ThreadManager::dump: "
302 "lock [%s|%p] is still alive\n",
303 (*lI).first.c_str(),
304 (*lI).second));
307 LockPoolStore::MPFieldMapCIt lpI = _sLockPoolStore._mFieldMap.begin();
308 LockPoolStore::MPFieldMapCIt lpE = _sLockPoolStore._mFieldMap.end ();
310 for(; lpI != lpE; ++lpI)
312 FLOG(("ThreadManager::dump: "
313 "lockpool [%s|%p] is still alive\n",
314 (*lpI).first.c_str(),
315 (*lpI).second));
319 SemaphoreStore::MPFieldMapCIt sI = _sSemaphoreStore._mFieldMap.begin();
320 SemaphoreStore::MPFieldMapCIt sE = _sSemaphoreStore._mFieldMap.end ();
322 for(; sI != sE; ++sI)
324 FLOG(("ThreadManager::dump: "
325 "semaphore [%s|%p] is still alive\n",
326 (*sI).first.c_str(),
327 (*sI).second));
330 FLOG(
331 ("Sizes: ThreadStore: %"PRISize" BarrierStore: %"PRISize
332 " CondVarStore: %"PRISize" LockStore: %"PRISize" LockPoolStore: %"
333 PRISize" SemaphoreStore: %"PRISize"\n",
334 _sThreadStore ._mFieldMap.size(),
335 _sBarrierStore ._mFieldMap.size(),
336 _sCondVarStore ._mFieldMap.size(),
337 _sLockStore ._mFieldMap.size(),
338 _sLockPoolStore ._mFieldMap.size(),
339 _sSemaphoreStore._mFieldMap.size()));
342 /*------------------------------- Get -------------------------------------*/
344 #if defined(OSG_USE_SPROC)
345 usptr_t *ThreadManager::getArena(void)
347 return _pArena;
349 #endif
351 /*------------------------------ Helper -----------------------------------*/
353 bool ThreadManager::initialize(void)
355 return the()->init();
358 bool ThreadManager::terminate (void)
360 bool returnValue = the()->shutdown();
362 delete _pThreadManager;
364 _pThreadManager = NULL;
366 return returnValue;
369 void ThreadManager::remove(BaseThread *pThread)
371 if(_bShutdownInProgress == true)
372 return;
374 _storePLock->acquire();
376 _sThreadStore.removeMPField(pThread);
378 _storePLock->release();
381 void ThreadManager::remove(Barrier *pBarrier)
383 if(_bShutdownInProgress == true)
384 return;
386 _storePLock->acquire();
388 _sBarrierStore.removeMPField(pBarrier);
390 _storePLock->release();
393 void ThreadManager::remove(CondVar *pCondVar)
395 if(_bShutdownInProgress == true)
396 return;
398 _storePLock->acquire();
400 _sCondVarStore.removeMPField(pCondVar);
402 _storePLock->release();
405 void ThreadManager::remove(Lock *pLock)
407 if(_bShutdownInProgress == true)
408 return;
410 _storePLock->acquire();
412 _sLockStore.removeMPField(pLock);
414 _storePLock->release();
417 void ThreadManager::remove(LockPool *pLockPool)
419 if(_bShutdownInProgress == true)
420 return;
422 _storePLock->acquire();
424 _sLockPoolStore.removeMPField(pLockPool);
426 _storePLock->release();
429 void ThreadManager::remove(Semaphore *pSemaphore)
431 if(_bShutdownInProgress == true)
432 return;
434 _storePLock->acquire();
436 _sSemaphoreStore.removeMPField(pSemaphore);
438 _storePLock->release();
441 UInt32 ThreadManager::registerThreadType(MPThreadType *pType)
443 return _sThreadStore.registerMPType(pType);
446 UInt32 ThreadManager::registerBarrierType(MPBarrierType *pType)
448 return _sBarrierStore.registerMPType(pType);
451 UInt32 ThreadManager::registerCondVarType(MPCondVarType *pType)
453 return _sCondVarStore.registerMPType(pType);
456 UInt32 ThreadManager::registerLockType(MPLockType *pType)
458 return _sLockStore.registerMPType(pType);
461 UInt32 ThreadManager::registerLockPoolType(MPLockPoolType *pType)
463 return _sLockPoolStore.registerMPType(pType);
466 UInt32 ThreadManager::registerSemaphoreType(MPSemaphoreType *pType)
468 return _sSemaphoreStore.registerMPType(pType);
471 #ifdef __sgi
472 #pragma set woff 1209
473 #endif
475 bool ThreadManager::init(void)
477 bool returnValue = true;
479 FDEBUG(("OSGThreadManager init\n"))
481 #if defined(OSG_USE_SPROC)
482 usconfig(CONF_AUTOGROW, 1);
483 usconfig(CONF_INITUSERS, 20);
484 usconfig(CONF_INITSIZE, 10 * 1048576);
485 usconfig(CONF_CHMOD, 0666);
487 _pArena = usinit("/dev/zero");
489 if(_pArena == NULL)
491 SFATAL << "OSGTM : could not initialize arena " << errno << std::endl;
492 returnValue = false;
494 else
496 SINFO << "OSGTM : got arena " << _pArena << std::endl;
498 #endif
500 _storePLock = _sLockStore.getMPField("OSGTMStoreLock", "OSGLock", true);
502 if(_storePLock == NULL)
504 SFATAL << "OSGTM : could not get table lock" << std::endl;
506 returnValue = false;
508 else
510 SINFO << "OSGTM : got table lock " << _storePLock << std::endl;
513 if(_szAppThreadType == NULL)
515 FINFO(("OSGTM : create -OSGBaseThread- app thread\n"));
517 _pAppThread = getThread("OSGAppThread", true, "OSGBaseThread");
519 else
521 FINFO(("OSGTM : create -%s- app thread\n", _szAppThreadType));
523 _pAppThread = getThread("OSGAppThread", true, _szAppThreadType);
526 FFASSERT((_pAppThread != NULL), 1,
527 ("OSGTM : could not get application thread \n"););
530 FINFO(("OSGTM : got application thread %p\n", _pAppThread.get()));
532 _pAppThread->init();
534 return returnValue;
537 #ifdef __sgi
538 #pragma reset woff 1209
539 #endif
541 bool ThreadManager::shutdown(void)
543 FDEBUG(("OSGThreadManager shutdown\n"))
545 _bShutdownInProgress = true;
547 _pAppThread->shutdown();
549 _pAppThread = NULL;
551 #ifdef OSG_DEBUG
553 ThreadStore::MPFieldMapCIt tI = _sThreadStore._mFieldMap.begin();
554 ThreadStore::MPFieldMapCIt tE = _sThreadStore._mFieldMap.end ();
556 for(; tI != tE; ++tI)
558 if(tI->first != "OSGAppThread")
560 FWARNING(("ThreadManager::shutdown: "
561 "thread [%s|%p] is still alive ([%d]). \n",
562 (*tI).first.c_str(),
563 (*tI).second,
564 (*tI).second->exists()));
568 BarrierStore::MPFieldMapCIt bI = _sBarrierStore._mFieldMap.begin();
569 BarrierStore::MPFieldMapCIt bE = _sBarrierStore._mFieldMap.end ();
571 for(; bI != bE; ++bI)
573 FWARNING(("ThreadManager::shutdown: "
574 "barrier [%s|%p] is still alive\n",
575 (*bI).first.c_str(),
576 (*bI).second));
580 CondVarStore::MPFieldMapCIt cI = _sCondVarStore._mFieldMap.begin();
581 CondVarStore::MPFieldMapCIt cE = _sCondVarStore._mFieldMap.end ();
583 for(; cI != cE; ++cI)
585 FWARNING(("ThreadManager::shutdown: "
586 "condvar [%s|%p] is still alive\n",
587 (*cI).first.c_str(),
588 (*cI).second));
592 LockStore::MPFieldMapCIt lI = _sLockStore._mFieldMap.begin();
593 LockStore::MPFieldMapCIt lE = _sLockStore._mFieldMap.end ();
595 for(; lI != lE; ++lI)
597 if(lI->first != "OSGTMStoreLock" &&
598 lI->first != "OSG::Log::_pLogLock" )
600 FWARNING(("ThreadManager::shutdown: "
601 "lock [%s|%p] is still alive\n",
602 (*lI).first.c_str(),
603 (*lI).second));
607 LockPoolStore::MPFieldMapCIt lpI = _sLockPoolStore._mFieldMap.begin();
608 LockPoolStore::MPFieldMapCIt lpE = _sLockPoolStore._mFieldMap.end ();
610 for(; lpI != lpE; ++lpI)
612 FWARNING(("ThreadManager::shutdown: "
613 "lockpool [%s|%p] is still alive\n",
614 (*lpI).first.c_str(),
615 (*lpI).second));
619 SemaphoreStore::MPFieldMapCIt sI = _sSemaphoreStore._mFieldMap.begin();
620 SemaphoreStore::MPFieldMapCIt sE = _sSemaphoreStore._mFieldMap.end ();
622 for(; sI != sE; ++sI)
624 FWARNING(("ThreadManager::shutdown: "
625 "semaphore [%s|%p] is still alive\n",
626 (*sI).first.c_str(),
627 (*sI).second));
630 #endif
632 FDEBUG(
633 ("Sizes: ThreadStore: %"PRISize" BarrierStore: %"PRISize
634 " CondVarStore: %"PRISize" LockStore: %"PRISize" LockPoolStore: %"
635 PRISize" SemaphoreStore: %"PRISize"\n",
636 _sThreadStore ._mFieldMap.size(),
637 _sBarrierStore ._mFieldMap.size(),
638 _sCondVarStore ._mFieldMap.size(),
639 _sLockStore ._mFieldMap.size(),
640 _sLockPoolStore ._mFieldMap.size(),
641 _sSemaphoreStore._mFieldMap.size()));
643 _sThreadStore .clear();
644 _sBarrierStore .clear();
645 _sCondVarStore .clear();
646 _sLockStore .clear();
647 _sLockPoolStore .clear();
648 _sSemaphoreStore.clear();
650 Thread::terminateThreading();
652 #if defined(OSG_USE_SPROC)
653 if(_pArena != NULL)
654 usdetach(_pArena);
655 #endif
657 return true;
660 /*--------------------------- Constructors --------------------------------*/
662 ThreadManager::ThreadManager(void) :
663 _sThreadStore ( ),
664 _sBarrierStore ( ),
665 _sCondVarStore ( ),
666 _sLockStore ( ),
667 _sLockPoolStore ( ),
668 _sSemaphoreStore( ),
670 _storePLock (NULL)
672 #if defined(OSG_USE_SPROC)
673 _pArena = NULL;
674 #endif
677 /*---------------------------- Destructo ----------------------------------*/
679 ThreadManager::~ThreadManager(void)
681 delete [] _szAppThreadType;