| Module | Sync_m |
| In: |
lib/sync.rb
|
| RCS_ID | = | '-$Header$-' | ||
| UN | = | :UN | lock mode | |
| SH | = | :SH | ||
| EX | = | :EX |
| sync_ex_count | [RW] | |
| sync_ex_locker | [RW] | |
| sync_mode | [RW] | |
| sync_sh_locker | [RW] | |
| sync_upgrade_waiting | [RW] | |
| sync_waiting | [RW] |
# File lib/sync.rb, line 91
91: def Sync_m.append_features(cl)
92: super
93: unless cl.instance_of?(Module)
94: # do nothing for Modules
95: # make aliases and include the proper module.
96: define_aliases(cl)
97: end
98: end
# File lib/sync.rb, line 79
79: def Sync_m.define_aliases(cl)
80: cl.module_eval %q{
81: alias locked? sync_locked?
82: alias shared? sync_shared?
83: alias exclusive? sync_exclusive?
84: alias lock sync_lock
85: alias unlock sync_unlock
86: alias try_lock sync_try_lock
87: alias synchronize sync_synchronize
88: }
89: end
# File lib/sync.rb, line 100
100: def Sync_m.extend_object(obj)
101: super
102: obj.sync_extended
103: end
# File lib/sync.rb, line 105
105: def sync_extended
106: unless (defined? locked? and
107: defined? shared? and
108: defined? exclusive? and
109: defined? lock and
110: defined? unlock and
111: defined? try_lock and
112: defined? synchronize)
113: Sync_m.define_aliases(class<<self;self;end)
114: end
115: sync_initialize
116: end
# File lib/sync.rb, line 141
141: def sync_lock(m = EX)
142: return unlock if m == UN
143:
144: until (Thread.critical = true; sync_try_lock_sub(m))
145: if sync_sh_locker[Thread.current]
146: sync_upgrade_waiting.push [Thread.current, sync_sh_locker[Thread.current]]
147: sync_sh_locker.delete(Thread.current)
148: else
149: sync_waiting.push Thread.current
150: end
151: Thread.stop
152: end
153: Thread.critical = false
154: self
155: end
# File lib/sync.rb, line 227
227: def sync_synchronize(mode = EX)
228: begin
229: sync_lock(mode)
230: yield
231: ensure
232: sync_unlock
233: end
234: end
locking methods.
# File lib/sync.rb, line 132
132: def sync_try_lock(mode = EX)
133: return unlock if mode == UN
134:
135: Thread.critical = true
136: ret = sync_try_lock_sub(mode)
137: Thread.critical = false
138: ret
139: end
# File lib/sync.rb, line 157
157: def sync_unlock(m = EX)
158: Thread.critical = true
159: if sync_mode == UN
160: Thread.critical = false
161: Err::UnknownLocker.Fail(Thread.current)
162: end
163:
164: m = sync_mode if m == EX and sync_mode == SH
165:
166: runnable = false
167: case m
168: when UN
169: Thread.critical = false
170: Err::UnknownLocker.Fail(Thread.current)
171:
172: when EX
173: if sync_ex_locker == Thread.current
174: if (self.sync_ex_count = sync_ex_count - 1) == 0
175: self.sync_ex_locker = nil
176: if sync_sh_locker.include?(Thread.current)
177: self.sync_mode = SH
178: else
179: self.sync_mode = UN
180: end
181: runnable = true
182: end
183: else
184: Err::UnknownLocker.Fail(Thread.current)
185: end
186:
187: when SH
188: if (count = sync_sh_locker[Thread.current]).nil?
189: Err::UnknownLocker.Fail(Thread.current)
190: else
191: if (sync_sh_locker[Thread.current] = count - 1) == 0
192: sync_sh_locker.delete(Thread.current)
193: if sync_sh_locker.empty? and sync_ex_count == 0
194: self.sync_mode = UN
195: runnable = true
196: end
197: end
198: end
199: end
200:
201: if runnable
202: if sync_upgrade_waiting.size > 0
203: for k, v in sync_upgrade_waiting
204: sync_sh_locker[k] = v
205: end
206: wait = sync_upgrade_waiting
207: self.sync_upgrade_waiting = []
208: Thread.critical = false
209:
210: for w, v in wait
211: w.run
212: end
213: else
214: wait = sync_waiting
215: self.sync_waiting = []
216: Thread.critical = false
217: for w in wait
218: w.run
219: end
220: end
221: end
222:
223: Thread.critical = false
224: self
225: end
# File lib/sync.rb, line 246
246: def sync_initialize
247: @sync_mode = UN
248: @sync_waiting = []
249: @sync_upgrade_waiting = []
250: @sync_sh_locker = Hash.new
251: @sync_ex_locker = nil
252: @sync_ex_count = 0
253: end
# File lib/sync.rb, line 260
260: def sync_try_lock_sub(m)
261: case m
262: when SH
263: case sync_mode
264: when UN
265: self.sync_mode = m
266: sync_sh_locker[Thread.current] = 1
267: ret = true
268: when SH
269: count = 0 unless count = sync_sh_locker[Thread.current]
270: sync_sh_locker[Thread.current] = count + 1
271: ret = true
272: when EX
273: # in EX mode, lock will upgrade to EX lock
274: if sync_ex_locker == Thread.current
275: self.sync_ex_count = sync_ex_count + 1
276: ret = true
277: else
278: ret = false
279: end
280: end
281: when EX
282: if sync_mode == UN or
283: sync_mode == SH && sync_sh_locker.size == 1 && sync_sh_locker.include?(Thread.current)
284: self.sync_mode = m
285: self.sync_ex_locker = Thread.current
286: self.sync_ex_count = 1
287: ret = true
288: elsif sync_mode == EX && sync_ex_locker == Thread.current
289: self.sync_ex_count = sync_ex_count + 1
290: ret = true
291: else
292: ret = false
293: end
294: else
295: Thread.critical = false
296: Err::LockModeFailer.Fail mode
297: end
298: return ret
299: end