blob: c3347b60b47c85d228b5ec19f0379953baf61b85 (
plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
|
#
# thread.rb - thread support classes
# $Date: 1996/05/21 09:29:21 $
# by Yukihiro Matsumoto <matz@caelum.co.jp>
#
unless defined? Thread
fail "Thread not available for this ruby interpreter"
end
unless defined? ThreadError
class ThreadError<Exception
end
end
class Mutex
def initialize
@waiting = []
@locked = FALSE;
end
def locked?
@locked
end
def try_lock
Thread.exclusive do
if not @locked
@locked=TRUE
return TRUE
end
end
FALSE
end
def lock
while not try_lock
@waiting.push Thread.current
Thread.stop
end
end
def unlock
@locked = FALSE
if w = @waiting.shift
w.run
end
end
def synchronize
begin
lock
yield
ensure
unlock
end
end
end
class SharedMutex<Mutex
def initialize
@locking = nil
@num_locks = 0;
super
end
def try_lock
if @locking == Thread.current
@num_locks += 1
return TRUE
end
if super
@num_locks = 1
@locking = Thread.current
TRUE
else
FALSE
end
end
def unlock
unless @locking == Thread.current
raise ThreadError, "cannot release shared mutex"
end
@num_locks -= 1
if @num_locks == 0
@locking = nil
super
end
end
end
class Queue
def initialize
@que = []
@waiting = []
end
def push(obj)
@que.push obj
if t = @waiting.shift
t.run
end
end
def pop non_block=FALSE
if @que.length == 0
raise ThreadError, "queue empty" if non_block
@waiting.push Thread.current
Thread.stop
end
@que.shift
end
def empty?
@que.length == 0
end
def length
@que.length
end
end
class Condition
def initialize
@waiting = []
end
def wait(mut)
Thread.exclusive do
mut.unlock
@waiting.push Thread.current
end
Thread.sleep
mut.lock
end
def signal
th = nil
Thread.exclusive do
th = @waiting.pop
end
th.run
end
def broadcast
w = @waiting
Thread.exclusive do
th = []
end
for th in w
th.run
end
end
end
|