Main Page | Namespace List | Class Hierarchy | Class List | Directories | File List | Class Members | File Members

critsec.h

Go to the documentation of this file.
00001 /*
00002  * critsec.h
00003  *
00004  * Critical section mutex class.
00005  *
00006  * Portable Windows Library
00007  *
00008  * Copyright (C) 2004 Post Increment
00009  *
00010  * The contents of this file are subject to the Mozilla Public License
00011  * Version 1.0 (the "License"); you may not use this file except in
00012  * compliance with the License. You may obtain a copy of the License at
00013  * http://www.mozilla.org/MPL/
00014  *
00015  * Software distributed under the License is distributed on an "AS IS"
00016  * basis, WITHOUT WARRANTY OF ANY KIND, either express or implied. See
00017  * the License for the specific language governing rights and limitations
00018  * under the License.
00019  *
00020  * The Original Code is Portable Windows Library.
00021  *
00022  * The Initial Developer of the Original Code is Post Increment
00023  *
00024  * Contributor(s): ______________________________________.
00025  *
00026  * $Log: critsec.h,v $
00027  * Revision 1.9  2004/05/16 23:31:07  csoutheren
00028  * Updated API documentation
00029  *
00030  * Revision 1.8  2004/05/12 04:36:13  csoutheren
00031  * Fixed problems with using sem_wait and friends on systems that do not
00032  * support atomic integers
00033  *
00034  * Revision 1.7  2004/04/21 11:22:56  csoutheren
00035  * Modified to work with gcc 3.4.0
00036  *
00037  * Revision 1.6  2004/04/14 06:58:00  csoutheren
00038  * Fixed PAtomicInteger and PSmartPointer to use real atomic operations
00039  *
00040  * Revision 1.5  2004/04/12 03:35:26  csoutheren
00041  * Fixed problems with non-recursuve mutexes and critical sections on
00042  * older compilers and libc
00043  *
00044  * Revision 1.4  2004/04/12 00:58:45  csoutheren
00045  * Fixed PAtomicInteger on Linux, and modified PMutex to use it
00046  *
00047  * Revision 1.3  2004/04/12 00:36:04  csoutheren
00048  * Added new class PAtomicInteger and added Windows implementation
00049  *
00050  * Revision 1.2  2004/04/11 03:20:41  csoutheren
00051  * Added Unix implementation of PCriticalSection
00052  *
00053  * Revision 1.1  2004/04/11 02:55:17  csoutheren
00054  * Added PCriticalSection for Windows
00055  * Added compile time option for PContainer to use critical sections to provide thread safety under some circumstances
00056  *
00057  */
00058 
00059 #ifndef _PCRITICALSECTION
00060 #define _PCRITICALSECTION
00061 
00062 #if P_HAS_ATOMIC_INT
00063 #if P_NEEDS_GNU_CXX_NAMESPACE
00064 #define EXCHANGE_AND_ADD(v,i)   __gnu_cxx::__exchange_and_add(v,i)
00065 #else
00066 #define EXCHANGE_AND_ADD(v,i)   __exchange_and_add(v,i)
00067 #endif
00068 #endif
00069 
00076 class PCriticalSection : public PObject
00077 {
00078   PCLASSINFO(PCriticalSection, PObject);
00079 
00080   public:
00085     PINLINE PCriticalSection();
00086 
00089     PINLINE ~PCriticalSection();
00091 
00096     PINLINE void Enter();
00097 
00100     PINLINE void Leave();
00101 
00103 
00104   private:
00105     PCriticalSection & operator=(const PCriticalSection &) { return *this; }
00106 
00107 // Include platform dependent part of class
00108 #ifdef _WIN32
00109 #include "msos/ptlib/critsec.h"
00110 #else
00111 #include "unix/ptlib/critsec.h"
00112 #endif
00113 };
00114 
00115 
00116 class PEnterAndLeave {
00117   public:
00122     inline PEnterAndLeave(
00123       PCriticalSection & _critSec,   
00124       BOOL enter = TRUE                   
00125     )
00126     : critSec(_critSec)
00127     { if (enter) critSec.Enter(); }
00128 
00133     inline ~PEnterAndLeave()
00134     { critSec.Leave(); }
00135 
00136   protected:
00137     PCriticalSection & critSec;
00138 };
00139 
00140 
00149 class PAtomicInteger 
00150 {
00151 #if defined(_WIN32) || defined(DOC_PLUS_PLUS)
00152     public:
00155       inline PAtomicInteger(long v = 0)
00156         : value(v) { }
00157 
00165       BOOL IsZero() const                 { return value == 0; }
00166 
00172       inline long operator++()            { return InterlockedIncrement(&value); }
00173 
00179       inline long operator--()            { return InterlockedDecrement(&value); }
00180 
00184       inline operator long () const       { return value; }
00185 
00189       inline void SetValue(long v)        { value = v; }
00190     protected:
00191       long value;
00192 #elif P_HAS_ATOMIC_INT
00193     public:
00194       inline PAtomicInteger(int v = 0)
00195         : value(v) { }
00196       BOOL IsZero() const                { return value == 0; }
00197       inline int operator++()            { return EXCHANGE_AND_ADD(&value, 1) + 1; }
00198       inline int unsigned operator--()   { return EXCHANGE_AND_ADD(&value, -1) - 1; }
00199       inline operator int () const       { return value; }
00200       inline void SetValue(int v)        { value = v; }
00201     protected:
00202       _Atomic_word value;
00203 #else 
00204     protected:
00205       PCriticalSection critSec;
00206     public:
00207       inline PAtomicInteger(int v = 0)
00208         : value(v) { }
00209       BOOL IsZero() const                { return value == 0; }
00210       inline int operator++()            { PEnterAndLeave m(critSec); value++; return value;}
00211       inline int operator--()            { PEnterAndLeave m(critSec); value--; return value;}
00212       inline operator int () const       { return value; }
00213       inline void SetValue(int v)        { value = v; }
00214    private:
00215       PAtomicInteger & operator=(const PAtomicInteger & ref) { value = (int)ref; return *this; }
00216     protected:
00217       int value;
00218 #endif
00219 };
00220 
00221 #endif
00222 
00223 // End Of File ///////////////////////////////////////////////////////////////

Generated on Sat Dec 22 16:46:50 2007 for PWLib by  doxygen 1.4.2