andre@0: /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 2 -*- */ andre@0: /* This Source Code Form is subject to the terms of the Mozilla Public andre@0: * License, v. 2.0. If a copy of the MPL was not distributed with this andre@0: * file, You can obtain one at http://mozilla.org/MPL/2.0/. */ andre@0: andre@0: #ifndef prolock_h___ andre@0: #define prolock_h___ andre@0: andre@0: #include "prtypes.h" andre@0: andre@0: PR_BEGIN_EXTERN_C andre@0: andre@0: /* andre@0: ** A locking mechanism, built on the existing PRLock definiion, andre@0: ** is provided that will permit applications to define a Lock andre@0: ** Hierarchy (or Lock Ordering) schema. An application designed andre@0: ** using the Ordered Lock functions will terminate with a andre@0: ** diagnostic message when a lock inversion condition is andre@0: ** detected. andre@0: ** andre@0: ** The lock ordering detection is complile-time enabled only. in andre@0: ** optimized builds of NSPR, the Ordered Lock functions map andre@0: ** directly to PRLock functions, providing no lock order andre@0: ** detection. andre@0: ** andre@0: ** The Ordered Lock Facility is compiled in when DEBUG is defined at andre@0: ** compile time. Ordered Lock can be forced on in optimized builds by andre@0: ** defining FORCE_NSPR_ORDERED_LOCK at compile time. Both the andre@0: ** application using Ordered Lock and NSPR must be compiled with the andre@0: ** facility enabled to achieve the desired results. andre@0: ** andre@0: ** Application designers should use the macro interfaces to the Ordered andre@0: ** Lock facility to ensure that it is compiled out in optimized builds. andre@0: ** andre@0: ** Application designers are responsible for defining their own andre@0: ** lock hierarchy. andre@0: ** andre@0: ** Ordered Lock is thread-safe and SMP safe. andre@0: ** andre@0: ** See Also: prlock.h andre@0: ** andre@0: ** /lth. 10-Jun-1998. andre@0: ** andre@0: */ andre@0: andre@0: /* andre@0: ** Opaque type for ordered lock. andre@0: ** ... Don't even think of looking in here. andre@0: ** andre@0: */ andre@0: andre@0: #if defined(DEBUG) || defined(FORCE_NSPR_ORDERED_LOCKS) andre@0: typedef void * PROrderedLock; andre@0: #else andre@0: /* andre@0: ** Map PROrderedLock and methods onto PRLock when ordered locking andre@0: ** is not compiled in. andre@0: ** andre@0: */ andre@0: #include "prlock.h" andre@0: andre@0: typedef PRLock PROrderedLock; andre@0: #endif andre@0: andre@0: /* ----------------------------------------------------------------------- andre@0: ** FUNCTION: PR_CreateOrderedLock() -- Create an Ordered Lock andre@0: ** andre@0: ** DESCRIPTION: PR_CreateOrderedLock() creates an ordered lock. andre@0: ** andre@0: ** INPUTS: andre@0: ** order: user defined order of this lock. andre@0: ** name: name of the lock. For debugging purposes. andre@0: ** andre@0: ** OUTPUTS: returned andre@0: ** andre@0: ** RETURNS: PR_OrderedLock pointer andre@0: ** andre@0: ** RESTRICTIONS: andre@0: ** andre@0: */ andre@0: #if defined(DEBUG) || defined(FORCE_NSPR_ORDERED_LOCKS) andre@0: #define PR_CREATE_ORDERED_LOCK(order,name)\ andre@0: PR_CreateOrderedLock((order),(name)) andre@0: #else andre@0: #define PR_CREATE_ORDERED_LOCK(order) PR_NewLock() andre@0: #endif andre@0: andre@0: NSPR_API(PROrderedLock *) andre@0: PR_CreateOrderedLock( andre@0: PRInt32 order, andre@0: const char *name andre@0: ); andre@0: andre@0: /* ----------------------------------------------------------------------- andre@0: ** FUNCTION: PR_DestroyOrderedLock() -- Destroy an Ordered Lock andre@0: ** andre@0: ** DESCRIPTION: PR_DestroyOrderedLock() destroys the ordered lock andre@0: ** referenced by lock. andre@0: ** andre@0: ** INPUTS: lock: pointer to a PROrderedLock andre@0: ** andre@0: ** OUTPUTS: the lock is destroyed andre@0: ** andre@0: ** RETURNS: void andre@0: ** andre@0: ** RESTRICTIONS: andre@0: ** andre@0: */ andre@0: #if defined(DEBUG) || defined(FORCE_NSPR_ORDERED_LOCKS) andre@0: #define PR_DESTROY_ORDERED_LOCK(lock) PR_DestroyOrderedLock((lock)) andre@0: #else andre@0: #define PR_DESTROY_ORDERED_LOCK(lock) PR_DestroyLock((lock)) andre@0: #endif andre@0: andre@0: NSPR_API(void) andre@0: PR_DestroyOrderedLock( andre@0: PROrderedLock *lock andre@0: ); andre@0: andre@0: /* ----------------------------------------------------------------------- andre@0: ** FUNCTION: PR_LockOrderedLock() -- Lock an ordered lock andre@0: ** andre@0: ** DESCRIPTION: PR_LockOrderedLock() locks the ordered lock andre@0: ** referenced by lock. If the order of lock is less than or equal andre@0: ** to the order of the highest lock held by the locking thread, andre@0: ** the function asserts. andre@0: ** andre@0: ** INPUTS: lock: a pointer to a PROrderedLock andre@0: ** andre@0: ** OUTPUTS: The lock is held or the function asserts. andre@0: ** andre@0: ** RETURNS: void andre@0: ** andre@0: ** RESTRICTIONS: andre@0: ** andre@0: */ andre@0: #if defined(DEBUG) || defined(FORCE_NSPR_ORDERED_LOCKS) andre@0: #define PR_LOCK_ORDERED_LOCK(lock) PR_LockOrderedLock((lock)) andre@0: #else andre@0: #define PR_LOCK_ORDERED_LOCK(lock) PR_Lock((lock)) andre@0: #endif andre@0: andre@0: NSPR_API(void) andre@0: PR_LockOrderedLock( andre@0: PROrderedLock *lock andre@0: ); andre@0: andre@0: /* ----------------------------------------------------------------------- andre@0: ** FUNCTION: PR_UnlockOrderedLock() -- unlock and Ordered Lock andre@0: ** andre@0: ** DESCRIPTION: PR_UnlockOrderedLock() unlocks the lock referenced andre@0: ** by lock. andre@0: ** andre@0: ** INPUTS: lock: a pointer to a PROrderedLock andre@0: ** andre@0: ** OUTPUTS: the lock is unlocked andre@0: ** andre@0: ** RETURNS: andre@0: ** PR_SUCCESS andre@0: ** PR_FAILURE andre@0: ** andre@0: ** RESTRICTIONS: andre@0: ** andre@0: */ andre@0: #if defined(DEBUG) || defined(FORCE_NSPR_ORDERED_LOCKS) andre@0: #define PR_UNLOCK_ORDERED_LOCK(lock) PR_UnlockOrderedLock((lock)) andre@0: #else andre@0: #define PR_UNLOCK_ORDERED_LOCK(lock) PR_Unlock((lock)) andre@0: #endif andre@0: andre@0: NSPR_API(PRStatus) andre@0: PR_UnlockOrderedLock( andre@0: PROrderedLock *lock andre@0: ); andre@0: andre@0: PR_END_EXTERN_C andre@0: andre@0: #endif /* prolock_h___ */