From: Yusuke ENDOH Date: 2010-05-11T03:24:52+09:00 Subject: [ruby-dev:41255] Re: MonitorMixin::ConditionVariable#wait timeout 遠藤です。 2010年5月11日1:06 KOSAKI Motohiro : > あ、確認ですが、ここでいっているraceというのはabstimeに変換した直後に > コンテキストスイッチしたらどうしよう、という話ですよね? pthread_cond_timedwait の RATIONALE で書かれていた問題の方です。 この問題は CLOCK_MONOTONIC だろうとシステムクロックだろうと同じように 発生するのではないかと思います。 「3 秒ごとに定期処理、シグナルされたらすぐに終了」の例だと、reltime 指定だと、 m.synchronize do t = Time.now + 3 until predicate t2 = Time.now # (A) cv.wait(m, t - t2) if t > t2 break if predicate if Time.now > t t += 3 # 定期処理をする end end # predicate が真になった end (A) の位置でコンテキストスイッチした場合、wait を呼び出す時には t2 の 値は現在時刻から古くなってしまっているため、タイムアウトは時刻 t より コンテキストスイッチしていた期間の分だけ確実に遅れてしまいます。 abstime 指定の場合、 m.synchronize do t = Time.now + 3 until predicate # (B) cv.wait(m, t) break if predicate if Time.now > t t += 3 # 定期処理をする end end # predicate が真になった end (B) の位置でコンテキストスイッチしても t の値に影響はないため、タイム アウトするのは時刻 t で、問題ありません。 なんだかよくわからなくなってきたので、reltime 指定の方がよいという例を コードで書いてみてもらえないでしょうか。 -- Yusuke Endoh