Mobile API Reference  MicroStrategy 2019
SpinLock.h
Go to the documentation of this file.
1 //==============================================================================================
2 // FILENAME : SpinLock.h
3 // AUTHOR : vovechkin
4 // CREATION : 2004-10-22
5 // Copyright (C) MicroStrategy Incorporated 2004
6 //==============================================================================================
7 #ifndef MBase_SpinLock_h
8 #define MBase_SpinLock_h
9 
10 #include "../Base/Atomic.h"
11 
12 #if defined(linux)
13 #include <sched.h> // for ::sched_yield
14 #endif
15 #include "../../PDCHeader/PDCunistd.h" // for ::sleep
16 
17 namespace MBase
18 {
22  class SpinLock
23  {
24  public:
25 
27  {
28  // 2004-10-22 vovechkin:
29  // it is important that the constructor be empty,
30  // because SpinLock is used by ModuleMainPtr, which
31  // has to have an empty C++ constructor.
32  }
33 
34  class SmartLock
35  {
36  public:
37 
38  SmartLock(SpinLock& irSpinLock):
39  mrSpinLock(irSpinLock),
40  mIsLocked(true)
41  {
42  mrSpinLock.Lock();
43  }
44 
45  ~SmartLock() throw()
46  {
47  if (mIsLocked)
48  {
49  mrSpinLock.Unlock();
50  }
51  }
52 
53  void Unlock() throw()
54  {
55  if (mIsLocked)
56  {
57  mrSpinLock.Unlock();
58  mIsLocked = false;
59  }
60  }
61 
62  private:
63 
64  SpinLock& mrSpinLock;
65  bool mIsLocked;
66  };
67 
68  private:
69 
70  friend class SmartLock;
71 
72  void Lock() throw()
73  {
74  // 2004-10-22 vovechkin
75  // since the constructor is empty (on purpose)
76  // we use 0x12345678 to differentiate from any
77  // other (uninitialized) value.
78  while (MBase::AtomicExchange(mValue, 0x12345678) == 0x12345678)
79  {
80  // 2004-10-23 vovechkin
81  // it would be better to use MBase::YieldToAnotherThread
82  // however, that would bring a link-dependency on Base,
83  // which many projects do not have.
84 #ifdef WIN32
85  ::Sleep(0);
86 #elif defined(linux)
87  // on Linux, sleep(0) does not do anything
88  ::sched_yield();
89 #else
90  ::sleep(0);
91 #endif
92  }
93  }
94 
95  void Unlock() throw()
96  {
97  MBase::AtomicExchange(mValue, 0);
98  }
99 
100  private:
101 
102  long mValue;
103  };
104 }
105 
106 #endif // MBase_SpinLock_h
DLL_BASE_EXIM void Sleep(unsigned long inMilliseconds)
SmartLock(SpinLock &irSpinLock)
Definition: SpinLock.h:38
SpinLock()
Definition: SpinLock.h:26
void Unlock()
Definition: SpinLock.h:53
~SmartLock()
Definition: SpinLock.h:45
long AtomicExchange(long &irVariable, long iNewValue)
Definition: Atomic.h:20
Definition: SpinLock.h:34
Definition: SpinLock.h:22
Definition: Allocator.h:47