summaryrefslogtreecommitdiff
path: root/framework
diff options
context:
space:
mode:
Diffstat (limited to 'framework')
-rw-r--r--framework/inc/threadhelp/lockhelper.hxx229
-rw-r--r--framework/source/threadhelp/lockhelper.cxx582
2 files changed, 811 insertions, 0 deletions
diff --git a/framework/inc/threadhelp/lockhelper.hxx b/framework/inc/threadhelp/lockhelper.hxx
new file mode 100644
index 000000000000..f274ac0c81db
--- /dev/null
+++ b/framework/inc/threadhelp/lockhelper.hxx
@@ -0,0 +1,229 @@
+/*************************************************************************
+ *
+ * $RCSfile: lockhelper.hxx,v $
+ *
+ * $Revision: 1.1 $
+ *
+ * last change: $Author: as $ $Date: 2001-06-11 10:11:46 $
+ *
+ * The Contents of this file are made available subject to the terms of
+ * either of the following licenses
+ *
+ * - GNU Lesser General Public License Version 2.1
+ * - Sun Industry Standards Source License Version 1.1
+ *
+ * Sun Microsystems Inc., October, 2000
+ *
+ * GNU Lesser General Public License Version 2.1
+ * =============================================
+ * Copyright 2000 by Sun Microsystems, Inc.
+ * 901 San Antonio Road, Palo Alto, CA 94303, USA
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License version 2.1, as published by the Free Software Foundation.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston,
+ * MA 02111-1307 USA
+ *
+ *
+ * Sun Industry Standards Source License Version 1.1
+ * =================================================
+ * The contents of this file are subject to the Sun Industry Standards
+ * Source License Version 1.1 (the "License"); You may not use this file
+ * except in compliance with the License. You may obtain a copy of the
+ * License at http://www.openoffice.org/license.html.
+ *
+ * Software provided under this License is provided on an "AS IS" basis,
+ * WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING,
+ * WITHOUT LIMITATION, WARRANTIES THAT THE SOFTWARE IS FREE OF DEFECTS,
+ * MERCHANTABLE, FIT FOR A PARTICULAR PURPOSE, OR NON-INFRINGING.
+ * See the License for the specific provisions governing your rights and
+ * obligations concerning the Software.
+ *
+ * The Initial Developer of the Original Code is: Sun Microsystems, Inc.
+ *
+ * Copyright: 2000 by Sun Microsystems, Inc.
+ *
+ * All Rights Reserved.
+ *
+ * Contributor(s): _______________________________________
+ *
+ *
+ ************************************************************************/
+
+#ifndef __FRAMEWORK_THREADHELP_LOCKHELPER_HXX_
+#define __FRAMEWORK_THREADHELP_LOCKHELPER_HXX_
+
+//_________________________________________________________________________________________________________________
+// my own includes
+//_________________________________________________________________________________________________________________
+
+#ifndef __FRAMEWORK_THREADHELP_INONCOPYABLE_H_
+#include <threadhelp/inoncopyable.h>
+#endif
+
+#ifndef __FRAMEWORK_THREADHELP_IMUTEX_H_
+#include <threadhelp/imutex.h>
+#endif
+
+#ifndef __FRAMEWORK_THREADHELP_IRWLOCK_H_
+#include <threadhelp/irwlock.h>
+#endif
+
+#ifndef __FRAMEWORK_THREADHELP_FAIRRWLOCK_HXX_
+#include <threadhelp/fairrwlock.hxx>
+#endif
+
+//_________________________________________________________________________________________________________________
+// interface includes
+//_________________________________________________________________________________________________________________
+
+//_________________________________________________________________________________________________________________
+// other includes
+//_________________________________________________________________________________________________________________
+
+#ifndef _OSL_MUTEX_HXX_
+#include <osl/mutex.hxx>
+#endif
+
+#ifndef _VOS_MUTEX_HXX_
+#include <vos/mutex.hxx>
+#endif
+
+//_________________________________________________________________________________________________________________
+// namespace
+//_________________________________________________________________________________________________________________
+
+namespace framework{
+
+//_________________________________________________________________________________________________________________
+// const
+//_________________________________________________________________________________________________________________
+
+/*-************************************************************************************************************//**
+ @descr If you use a lock or mutex as a member of your class and whish to use it earlier then other ones
+ you should have a look on this implementation. You must use it as the first base class
+ of your implementation - because base classes are initialized by his order and before your
+ member! Thats why ist a good place to declare your thread help member so.
+*//*-*************************************************************************************************************/
+enum ELockType
+{
+ E_NOTHING = 0 ,
+ E_OWNMUTEX = 1 ,
+ E_SOLARMUTEX = 2 ,
+ E_FAIRRWLOCK = 3
+};
+
+#define ENVVAR_LOCKTYPE DECLARE_ASCII("LOCKTYPE_FRAMEWORK")
+#define FALLBACK_LOCKTYPE E_OWNMUTEX
+
+//_________________________________________________________________________________________________________________
+// declarations
+//_________________________________________________________________________________________________________________
+
+/*-************************************************************************************************************//**
+ @short helper to set right lock in right situation
+ @descr This helper support different types of locking:
+ a) no locks - transparent for user!
+ This could be usefull for simluation or single threaded environments!
+ b) own mutex
+ An object use his own osl-mutex to be threadsafe. Usefull for easy and exclusiv locking.
+ c) solar mutex
+ An object use our solar mutex and will be a part of a greater safed "threadsafe code block".
+ Could be usefull for simulation and testing of higher modules!
+ d) fair rw-lock
+ An object use an implementation of a fair rw-lock. This increase granularity of t hreadsafe mechanism
+ and should be used for high performance threadsafe code!
+
+ @attention We support two interfaces - "IMutex" and "IRWLock". Don't mix using of it!
+ A guard implementation should use one interface only!
+
+ @implements IMutex
+ @implements IRWLock
+
+ @base INonCopyable
+ IMutex
+ IRWLock
+
+ @devstatus draft
+*//*-*************************************************************************************************************/
+class LockHelper : public IMutex
+ , public IRWLock
+ , private INonCopyable
+{
+ //-------------------------------------------------------------------------------------------------------------
+ // public methods
+ //-------------------------------------------------------------------------------------------------------------
+ public:
+
+ //-------------------------------------------------------------------------------------------------------------
+ // ctor/dtor
+ //-------------------------------------------------------------------------------------------------------------
+ LockHelper( ::vos::IMutex* pSolarMutex = NULL );
+ virtual ~LockHelper( );
+
+ //-------------------------------------------------------------------------------------------------------------
+ // interface ::framework::IMutex
+ //-------------------------------------------------------------------------------------------------------------
+ virtual void acquire();
+ virtual void release();
+
+ //-------------------------------------------------------------------------------------------------------------
+ // interface ::framework::IRWLock
+ //-------------------------------------------------------------------------------------------------------------
+ virtual void acquireReadAccess ();
+ virtual void releaseReadAccess ();
+ virtual void acquireWriteAccess ();
+ virtual void releaseWriteAccess ();
+ virtual void downgradeWriteAccess();
+
+ //-------------------------------------------------------------------------------------------------------------
+ // something else
+ //-------------------------------------------------------------------------------------------------------------
+ static LockHelper& getGlobalLock ( ::vos::IMutex* pSolarMutex = NULL );
+ ::osl::Mutex& getShareableOslMutex( );
+
+ //-------------------------------------------------------------------------------------------------------------
+ // private methods
+ //-------------------------------------------------------------------------------------------------------------
+ private:
+
+ static ELockType& implts_getLockType();
+
+ //-------------------------------------------------------------------------------------------------------------
+ // private member
+ // a) Make some member mutable for using in const functions!
+ // b) "m_eLockType" define, which of follow members is used!
+ // You can use "m_pFairRWLock" as a fair rw-lock (multiple reader / one writer / looks for incoming order of threads too) ...
+ // or you can use a normal osl mutex ("m_pOwnMutex") ...
+ // ... or the solarmuex as "m_pSolarMutex" (must be set from outside! because some components must be vcl-free!)
+ // ... but sometimes you need a shareable osl mutex!
+ // In this case you has some problems: i ) If your lock type is set to E_OWNMUTEX => it's easy; you can use your member "m_pOwnMutex" - it's a osl mutex.
+ // Creation and using of "m_pShareableOslMutex" isn't neccessary!
+ // ii ) Otherwise you have no osl mutex ... so you must create "m_pShareableOslMutex" and use it twice!
+ // In this case you must lock two member everytime - "m_pShareableMutex" AND "m_pFairRWLock" or "m_pSolarMutex" or ...
+ // It isn't realy fine - but the only possible way.
+ // iii) There exist another special case - E_NOTHING is set! Then we should create this shareable mutex ...
+ // nad you can use it ... but this implmentation ignore it.
+ //-------------------------------------------------------------------------------------------------------------
+ private:
+
+ ELockType m_eLockType ;
+
+ mutable FairRWLock* m_pFairRWLock ;
+ mutable ::osl::Mutex* m_pOwnMutex ;
+ mutable ::vos::IMutex* m_pSolarMutex ;
+ mutable ::osl::Mutex* m_pShareableOslMutex ;
+};
+
+} // namespace framework
+
+#endif // #ifndef __FRAMEWORK_THREADHELP_LOCKHELPER_HXX_
diff --git a/framework/source/threadhelp/lockhelper.cxx b/framework/source/threadhelp/lockhelper.cxx
new file mode 100644
index 000000000000..949ab3779a60
--- /dev/null
+++ b/framework/source/threadhelp/lockhelper.cxx
@@ -0,0 +1,582 @@
+/*************************************************************************
+ *
+ * $RCSfile: lockhelper.cxx,v $
+ *
+ * $Revision: 1.1 $
+ *
+ * last change: $Author: as $ $Date: 2001-06-11 10:12:01 $
+ *
+ * The Contents of this file are made available subject to the terms of
+ * either of the following licenses
+ *
+ * - GNU Lesser General Public License Version 2.1
+ * - Sun Industry Standards Source License Version 1.1
+ *
+ * Sun Microsystems Inc., October, 2000
+ *
+ * GNU Lesser General Public License Version 2.1
+ * =============================================
+ * Copyright 2000 by Sun Microsystems, Inc.
+ * 901 San Antonio Road, Palo Alto, CA 94303, USA
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License version 2.1, as published by the Free Software Foundation.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston,
+ * MA 02111-1307 USA
+ *
+ *
+ * Sun Industry Standards Source License Version 1.1
+ * =================================================
+ * The contents of this file are subject to the Sun Industry Standards
+ * Source License Version 1.1 (the "License"); You may not use this file
+ * except in compliance with the License. You may obtain a copy of the
+ * License at http://www.openoffice.org/license.html.
+ *
+ * Software provided under this License is provided on an "AS IS" basis,
+ * WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING,
+ * WITHOUT LIMITATION, WARRANTIES THAT THE SOFTWARE IS FREE OF DEFECTS,
+ * MERCHANTABLE, FIT FOR A PARTICULAR PURPOSE, OR NON-INFRINGING.
+ * See the License for the specific provisions governing your rights and
+ * obligations concerning the Software.
+ *
+ * The Initial Developer of the Original Code is: Sun Microsystems, Inc.
+ *
+ * Copyright: 2000 by Sun Microsystems, Inc.
+ *
+ * All Rights Reserved.
+ *
+ * Contributor(s): _______________________________________
+ *
+ *
+ ************************************************************************/
+
+//_________________________________________________________________________________________________________________
+// my own includes
+//_________________________________________________________________________________________________________________
+
+#ifndef __FRAMEWORK_THREADHELP_LOCKHELPER_HXX_
+#include <threadhelp/lockhelper.hxx>
+#endif
+
+#ifndef __FRAMEWORK_GENERAL_H_
+#include <general.h>
+#endif
+
+#ifndef __FRAMEWORK_MACROS_DEBUG_HXX_
+#include <macros/debug.hxx>
+#endif
+
+//_________________________________________________________________________________________________________________
+// interface includes
+//_________________________________________________________________________________________________________________
+
+//_________________________________________________________________________________________________________________
+// other includes
+//_________________________________________________________________________________________________________________
+
+#ifndef _VOS_PROCESS_HXX_
+#include <vos/process.hxx>
+#endif
+
+//_________________________________________________________________________________________________________________
+// namespace
+//_________________________________________________________________________________________________________________
+
+namespace framework{
+
+//_________________________________________________________________________________________________________________
+// const
+//_________________________________________________________________________________________________________________
+
+//_________________________________________________________________________________________________________________
+// declarations
+//_________________________________________________________________________________________________________________
+
+/*-************************************************************************************************************//**
+ @short use ctor to initialize instance
+ @descr We must initialize our member "m_eLockType". This value specify handling of locking.
+ User use this helper as parameter for a guard creation.
+ These guard use "m_eLockType" to set lock in the right way by using right mutex or rw-lock.
+
+ @seealso enum ELockType
+ @seealso class ReadGuard
+ @seealso class WriteGuard
+
+ @param "rSolarMutex", for some components we must be "vcl-free"! So we can't work with our solar mutex
+ directly. User must set his reference at this instance - so we can work with it!
+ @return -
+
+ @onerror -
+*//*-*************************************************************************************************************/
+LockHelper::LockHelper( ::vos::IMutex* pSolarMutex )
+ : m_pOwnMutex ( NULL )
+ , m_pSolarMutex ( NULL )
+ , m_pFairRWLock ( NULL )
+ , m_pShareableOslMutex( NULL )
+{
+ m_eLockType = implts_getLockType();
+ switch( m_eLockType )
+ {
+ //case E_NOTHING : // There is nothing to do ...
+ case E_OWNMUTEX : {
+ m_pOwnMutex = new ::osl::Mutex;
+ }
+ break;
+ case E_SOLARMUTEX : {
+ if( pSolarMutex == NULL )
+ {
+ m_pSolarMutex = new ::vos::OMutex;
+ }
+ else
+ {
+ m_pSolarMutex = pSolarMutex;
+ }
+ }
+ break;
+ case E_FAIRRWLOCK : {
+ m_pFairRWLock = new FairRWLock;
+ }
+ break;
+ #ifdef ENABLE_ASSERTIONS
+ default : LOG_ASSERT2( m_eLockType!=E_NOTHING, "LockHelper::ctor()", "Invalid lock type found .. so code will not be threadsafe!" )
+ #endif
+ }
+}
+
+/*-************************************************************************************************************//**
+ @short default dtor to release safed pointer
+ @descr We have created dynamical mutex- or lock-member ... or we hold a pointer to external objects.
+ We must release it!
+
+ @seealso ctor()
+
+ @param -
+ @return -
+
+ @onerror -
+*//*-*************************************************************************************************************/
+LockHelper::~LockHelper()
+{
+ if( m_pOwnMutex != NULL )
+ {
+ delete m_pOwnMutex;
+ m_pOwnMutex = NULL;
+ }
+ if( m_pSolarMutex != NULL )
+ {
+ m_pSolarMutex = NULL;
+ }
+ if( m_pFairRWLock != NULL )
+ {
+ delete m_pFairRWLock;
+ m_pFairRWLock = NULL;
+ }
+ if( m_pShareableOslMutex != NULL )
+ {
+ delete m_pShareableOslMutex;
+ m_pShareableOslMutex = NULL;
+ }
+}
+
+/*-************************************************************************************************************//**
+ @interface IMutex
+ @short set an exclusiv lock
+ @descr We must match this lock call with current set lock type and used lock member.
+ If a mutex should be used - it will be easy ... but if a rw-lock should be used
+ we must simulate it as a write access!
+
+ @attention If a shareable osl mutex exist, he must be used as twice!
+ It's neccessary for some cppu-helper classes ...
+
+ @seealso method acquireWriteAccess()
+
+ @param -
+ @return -
+
+ @onerror -
+*//*-*************************************************************************************************************/
+void LockHelper::acquire()
+{
+ switch( m_eLockType )
+ {
+ //case E_NOTHING : // There is nothing to do ...
+ case E_OWNMUTEX : {
+ m_pOwnMutex->acquire();
+ }
+ break;
+ case E_SOLARMUTEX : {
+ m_pSolarMutex->acquire();
+ }
+ break;
+ case E_FAIRRWLOCK : {
+ m_pFairRWLock->acquireWriteAccess();
+ }
+ break;
+ }
+}
+
+/*-************************************************************************************************************//**
+ @interface IMutex
+ @short release exclusiv lock
+ @descr We must match this unlock call with current set lock type and used lock member.
+ If a mutex should be used - it will be easy ... but if a rw-lock should be used
+ we must simulate it as a write access!
+
+ @attention If a shareable osl mutex exist, he must be used as twice!
+ It's neccessary for some cppu-helper classes ...
+
+ @seealso method releaseWriteAccess()
+
+ @param -
+ @return -
+
+ @onerror -
+*//*-*************************************************************************************************************/
+void LockHelper::release()
+{
+ switch( m_eLockType )
+ {
+ //case E_NOTHING : // There is nothing to do ...
+ case E_OWNMUTEX : {
+ m_pOwnMutex->release();
+ }
+ break;
+ case E_SOLARMUTEX : {
+ m_pSolarMutex->release();
+ }
+ break;
+ case E_FAIRRWLOCK : {
+ m_pFairRWLock->releaseWriteAccess();
+ }
+ break;
+ }
+}
+
+/*-************************************************************************************************************//**
+ @interface IRWLock
+ @short set lock for reading
+ @descr A guard should call this method to acquire read access on your member.
+ Writing isn't allowed then - but nobody could check it for you!
+ We use m_eLockType to differ between all possible "lock-member"!!!
+
+ @attention If a shareable osl mutex exist, he must be used as twice!
+ It's neccessary for some cppu-helper classes ...
+
+ @seealso method releaseReadAccess()
+
+ @param -
+ @return -
+
+ @onerror -
+*//*-*************************************************************************************************************/
+void LockHelper::acquireReadAccess()
+{
+ switch( m_eLockType )
+ {
+ //case E_NOTHING : // There is nothing to do ...
+ case E_OWNMUTEX : {
+ m_pOwnMutex->acquire();
+ }
+ break;
+ case E_SOLARMUTEX : {
+ m_pSolarMutex->acquire();
+ }
+ break;
+ case E_FAIRRWLOCK : {
+ m_pFairRWLock->acquireReadAccess();
+ }
+ break;
+ }
+}
+
+/*-************************************************************************************************************//**
+ @interface IRWLock
+ @short reset lock for reading
+ @descr A guard should call this method to release read access on your member.
+ We use m_eLockType to differ between all possible "lock-member"!!!
+
+ @attention If a shareable osl mutex exist, he must be used as twice!
+ It's neccessary for some cppu-helper classes ...
+
+ @seealso method acquireReadAccess()
+
+ @param -
+ @return -
+
+ @onerror -
+*//*-*************************************************************************************************************/
+void LockHelper::releaseReadAccess()
+{
+ switch( m_eLockType )
+ {
+ //case E_NOTHING : // There is nothing to do ...
+ case E_OWNMUTEX : {
+ m_pOwnMutex->release();
+ }
+ break;
+ case E_SOLARMUTEX : {
+ m_pSolarMutex->release();
+ }
+ break;
+ case E_FAIRRWLOCK : {
+ m_pFairRWLock->releaseReadAccess();
+ }
+ break;
+ }
+}
+
+/*-************************************************************************************************************//**
+ @interface IRWLock
+ @short set lock for writing
+ @descr A guard should call this method to acquire write access on your member.
+ Reading is allowed too - of course.
+ After successfully calling of this method you are the only writer.
+ We use m_eLockType to differ between all possible "lock-member"!!!
+
+ @attention If a shareable osl mutex exist, he must be used as twice!
+ It's neccessary for some cppu-helper classes ...
+
+ @seealso method releaseWriteAccess()
+
+ @param -
+ @return -
+
+ @onerror -
+*//*-*************************************************************************************************************/
+void LockHelper::acquireWriteAccess()
+{
+ switch( m_eLockType )
+ {
+ //case E_NOTHING : // There is nothing to do ...
+ case E_OWNMUTEX : {
+ m_pOwnMutex->acquire();
+ }
+ break;
+ case E_SOLARMUTEX : {
+ m_pSolarMutex->acquire();
+ }
+ break;
+ case E_FAIRRWLOCK : {
+ m_pFairRWLock->acquireWriteAccess();
+ }
+ break;
+ }
+}
+
+/*-************************************************************************************************************//**
+ @interface IRWLock
+ @short reset lock for writing
+ @descr A guard should call this method to release write access on your member.
+ We use m_eLockType to differ between all possible "lock-member"!!!
+
+ @attention If a shareable osl mutex exist, he must be used as twice!
+ It's neccessary for some cppu-helper classes ...
+
+ @seealso method acquireWriteAccess()
+
+ @param -
+ @return -
+
+ @onerror -
+*//*-*************************************************************************************************************/
+void LockHelper::releaseWriteAccess()
+{
+ switch( m_eLockType )
+ {
+ //case E_NOTHING : // There is nothing to do ...
+ case E_OWNMUTEX : {
+ m_pOwnMutex->release();
+ }
+ break;
+ case E_SOLARMUTEX : {
+ m_pSolarMutex->release();
+ }
+ break;
+ case E_FAIRRWLOCK : {
+ m_pFairRWLock->releaseWriteAccess();
+ }
+ break;
+ }
+}
+
+/*-************************************************************************************************************//**
+ @interface IRWLock
+ @short downgrade a write access to a read access
+ @descr A guard should call this method to change a write to a read access.
+ New readers can work too - new writer are blocked!
+ We use m_eLockType to differ between all possible "lock-member"!!!
+
+ @attention Ignore shareable mutex(!) - because this call never should release a lock completly!
+ We change a write access to a read access only.
+
+ @attention a) Don't call this method if you are not a writer!
+ Results are not defined then ...
+ An upgrade can't be implemented realy ... because acquiring new access
+ will be the same - there no differences!
+ b) Without function if m_eLockTyp is different from E_FAIRRWLOCK(!) ...
+ because, a mutex don't support it realy.
+
+ @seealso -
+
+ @param -
+ @return -
+
+ @onerror -
+*//*-*************************************************************************************************************/
+void LockHelper::downgradeWriteAccess()
+{
+ switch( m_eLockType )
+ {
+ //case E_NOTHING : // There is nothing to do ...
+ //case E_OWNMUTEX : // Not supported for mutex!
+ //case E_SOLARMUTEX : // Not supported for mutex!
+ case E_FAIRRWLOCK : m_pFairRWLock->downgradeWriteAccess();
+ break;
+ }
+}
+
+/*-************************************************************************************************************//**
+ @short return a reference to a static lock helper
+ @descr Sometimes we need the global mutex or rw-lock! (e.g. in our own static methods)
+ But it's not a good idea to use these global one very often ...
+ Thats why we use this little helper method.
+ We create our own "class global static" lock.
+ It will be created at first call only!
+ All other requests use these created one then directly.
+
+ @seealso -
+
+ @param -
+ @return A reference to a static mutex/lock member.
+
+ @onerror No error should occure.
+*//*-*************************************************************************************************************/
+LockHelper& LockHelper::getGlobalLock( ::vos::IMutex* pSolarMutex )
+{
+ // Initialize static "member" only for one time!
+ // Algorithm:
+ // a) Start with an invalid lock (NULL pointer)
+ // b) If these method first called (lock not already exist!) ...
+ // c) ... we must create a new one. Protect follow code with the global mutex -
+ // (It must be - we create a static variable!)
+ // d) Check pointer again - because ... another instance of our class could be faster then these one!
+ // e) Create the new lock and set it for return on static variable.
+ // f) Return new created or already existing lock object.
+ static LockHelper* pLock = NULL;
+ if( pLock == NULL )
+ {
+ ::osl::MutexGuard aGuard( ::osl::Mutex::getGlobalMutex() );
+ if( pLock == NULL )
+ {
+ static LockHelper aLock( pSolarMutex );
+ pLock = &aLock;
+ }
+ }
+ return *pLock;
+}
+
+/*-************************************************************************************************************//**
+ @short return a reference to shared mutex member
+ @descr Sometimes we need a osl-mutex for sharing with our uno helper ...
+ What can we do?
+ a) If we have an initialized "own mutex" ... we can use it!
+ b) Otherwhise we must use a different mutex member :-(
+ I HOPE IT WORKS!
+
+ @seealso -
+
+ @param -
+ @return A reference to a shared mutex.
+
+ @onerror No error should occure.
+*//*-*************************************************************************************************************/
+::osl::Mutex& LockHelper::getShareableOslMutex()
+{
+ static ::osl::Mutex* pMutex = NULL;
+ if( pMutex == NULL )
+ {
+ ::osl::MutexGuard aGuard( ::osl::Mutex::getGlobalMutex() );
+ if( pMutex == NULL )
+ {
+ switch( m_eLockType )
+ {
+ case E_OWNMUTEX : {
+ pMutex = m_pOwnMutex;
+ }
+ break;
+ default : {
+ if( m_pShareableOslMutex == NULL )
+ {
+ m_pShareableOslMutex = new ::osl::Mutex;
+ }
+ pMutex = m_pShareableOslMutex;
+ }
+ break;
+ }
+ }
+ }
+ return *pMutex;
+}
+
+/*-************************************************************************************************************//**
+ @short search for right lock type, which should be used by an instance of this struct
+ @descr We must initialize our member "m_eLockType". This value specify handling of locking.
+ How we can do that? We search for an environment variable. We do it only for one time ....
+ because the environment is fix. So we safe this value and use it for all further requests.
+ If no variable could be found - we use a fallback!
+
+ @attention We have numbered all our enum values for ELockType. So we can use it as value of searched
+ environment variable too!
+
+ @seealso enum ELockType
+ @seealso environment LOCKTYPE
+
+ @param -
+ @return A reference to a created and right initialized lock type!
+
+ @onerror We use a fallback!
+*//*-*************************************************************************************************************/
+ELockType& LockHelper::implts_getLockType()
+{
+ // Initialize static "member" only for one time!
+ // Algorithm:
+ // a) Start with an invalid variable (NULL pointer)
+ // b) If these method first called (value not already exist!) ...
+ // c) ... we must create a new one. Protect follow code with the global mutex -
+ // (It must be - we create a static variable!)
+ // d) Check pointer again - because ... another instance of our class could be faster then these one!
+ // e) Create the new static variable, get value from the environment and set it
+ // f) Return new created or already existing static variable.
+ static ELockType* pType = NULL;
+ if( pType == NULL )
+ {
+ ::osl::MutexGuard aGuard( ::osl::Mutex::getGlobalMutex() );
+ if( pType == NULL )
+ {
+ static ELockType eType = FALLBACK_LOCKTYPE;
+
+ ::vos::OStartupInfo aEnvironment;
+ ::rtl::OUString sValue ;
+ if( aEnvironment.getEnvironment( ENVVAR_LOCKTYPE, sValue ) == ::vos::OStartupInfo::E_None )
+ {
+ eType = (ELockType)(sValue.toInt32());
+ }
+
+ LOG_LOCKTYPE( FALLBACK_LOCKTYPE, eType )
+
+ pType = &eType;
+ }
+ }
+ return *pType;
+}
+
+} // namespace framework