使用MRI ruby 1.9我有一些像
这样的代码def foo()
puts "in foo"
loop do
puts "in foo loop"
end
end
def bar()
puts "in bar"
start_alsa_listener
end
foo_thread = Thread.new { foo }
bar_thread = Thread.new { bar }
foo_thread.join
bar_thread.join
start_alsa_listener是一个阻塞库调用,用于打开ALSA midi音序器并等待其上的输入事件。本质上,我希望我的代码能够不断地打印出“foo循环”,同时能够接收ALSA midi事件并将它们打印到控制台(start_alsa_listener在收到事件时会这样做)。
问题在于,当我运行上面的代码时,只要bar()运行它就永远不会将上下文切换回foo()。
start_alsa_listener是一个ruby C扩展,如下所示:
for(;;) {
poll(/* args */); /* wait for input data */
/* print data to console */
}
也许它与Ruby中的某些东西有关我在线程上做错了,或者可能与poll有关,或者可能与ALSA处理线程的方式有关。任何帮助表示赞赏。
答案 0 :(得分:3)
你所展示的循环将阻止整个解释器(假设poll
正在阻塞),就像史蒂夫所说的那样。您需要使用Ruby(MRI / YARV)C API中的rb_thread_blocking_region调用poll()。
答案 1 :(得分:2)
没有文本,这两个文本并行运行。 GIRL不会让两个线程同时使用C扩展运行,因为它无法知道它的线程安全。