comparison Implab/Parallels/SharedLock.cs @ 129:471f596b2603 v2

Added SharedLock to synchronization routines
author cin
date Thu, 29 Jan 2015 18:31:06 +0300
parents
children 671f60cd0250
comparison
equal deleted inserted replaced
128:6241bff0cd64 129:471f596b2603
1 using System;
2 using System.Threading;
3 using System.Diagnostics;
4
5 namespace Implab.Parallels {
6 /// <summary>
7 /// Implements a lightweight mechanism to aquire a shared or an exclusive lock.
8 /// </summary>
9 public class SharedLock {
10 readonly object m_lock = new object();
11 int m_locks;
12 bool m_exclusive;
13
14 public bool LockExclusive(int timeout) {
15 lock (m_lock) {
16 if (m_locks > 0 && !Monitor.Wait(m_lock, timeout))
17 return false;
18 m_exclusive = true;
19 m_locks = 1;
20 }
21 }
22
23 public void LockExclusive() {
24 LockExclusive(-1);
25 }
26
27 public bool LockShared(int timeout) {
28 lock (m_lock) {
29 if (!m_exclusive) {
30 m_locks++;
31 return true;
32 }
33
34 if (m_lock == 0) {
35 m_exclusive = false;
36 m_locks = 1;
37 return true;
38 }
39
40 if (Monitor.Wait(m_lock, timeout)) {
41 Debug.Assert(m_locks == 0);
42 m_locks = 1;
43 m_exclusive = false;
44 return true;
45 }
46 return false;
47 }
48 }
49
50 public void LockShared() {
51 LockShared(-1);
52 }
53
54 public void ReleaseShared() {
55 lock (m_lock) {
56 if (m_exclusive || m_locks <= 0)
57 throw new InvalidOperationException();
58 m_locks--;
59 if (m_locks == 0)
60 Monitor.PulseAll(m_lock);
61 }
62 }
63
64 public void ReleaseExclusive() {
65 lock (m_lock) {
66 if (!m_exclusive && m_locks != 1)
67 throw new InvalidOperationException();
68 m_locks = 0;
69 Monitor.PulseAll(m_lock);
70 }
71 }
72
73 }
74 }
75