summaryrefslogtreecommitdiff
path: root/lib
diff options
context:
space:
mode:
authorfranz <Franz.Netykafka@runbox.com>2009-06-15 21:59:56 +0200
committerGiuseppe Bilotta <giuseppe.bilotta@gmail.com>2009-08-26 23:31:37 +0200
commit7cad4b67e17cc734d26fb1366bd90684cc13c470 (patch)
tree12620646f2d9c349e8be77f8df27e29a835fdf89 /lib
parent0b95114018f49dde6078e88935db54b2c8f20dd5 (diff)
ruby 1.9: monkeypatch MonitorMixin and ConditionVariable
ruby 1.9's ConditionVariable#wait is not implemented for timeout != nil, this patch adds an implementation for it (see ruby-core:15847) Also, since MonitorMixin is included into TCPSocket in rbot, and TCPSocket#send != Object#send in ruby 1.9, i changed that to use __send__.
Diffstat (limited to 'lib')
-rw-r--r--lib/rbot/compat19.rb70
1 files changed, 70 insertions, 0 deletions
diff --git a/lib/rbot/compat19.rb b/lib/rbot/compat19.rb
new file mode 100644
index 00000000..fbb68477
--- /dev/null
+++ b/lib/rbot/compat19.rb
@@ -0,0 +1,70 @@
+#-- vim:sw=2:et
+#++
+#
+# :title: ruby 1.9 compatibility (monkey)patches
+
+require 'timeout'
+require "thread"
+
+class ConditionVariable
+
+ def wait(mutex, timeout=nil)
+ begin
+ # TODO: mutex should not be used
+ @waiters_mutex.synchronize do
+ @waiters.push(Thread.current)
+ end
+ if timeout
+ elapsed = mutex.sleep timeout if timeout > 0.0
+ unless timeout > 0.0 and elapsed < timeout
+ t = @waiters_mutex.synchronize { @waiters.delete Thread.current }
+ signal unless t # if we got notified, pass it along
+ raise TimeoutError, "wait timed out"
+ end
+ else
+ mutex.sleep
+ end
+ end
+ nil
+ end
+
+end
+
+require 'monitor'
+
+module MonitorMixin
+
+ class ConditionVariable
+
+ def wait(timeout = nil)
+ #if timeout
+ # raise NotImplementedError, "timeout is not implemented yet"
+ #end
+ @monitor.__send__(:mon_check_owner)
+ count = @monitor.__send__(:mon_exit_for_cond)
+ begin
+ @cond.wait(@monitor.instance_variable_get("@mon_mutex"), timeout)
+ return true
+ ensure
+ @monitor.__send__(:mon_enter_for_cond, count)
+ end
+ end
+
+ def signal
+ @monitor.__send__(:mon_check_owner)
+ @cond.signal
+ end
+
+ def broadcast
+ @monitor.__send__(:mon_check_owner)
+ @cond.broadcast
+ end
+
+ end # ConditionVariable
+
+ def self.extend_object(obj)
+ super(obj)
+ obj.__send__(:mon_initialize)
+ end
+
+end # MonitorMixin