を使用しています
はFFIブロックRubyのスケジューラを介した通話を完全には、任意のスレッドを許可していないようです。これはRubyの緑色スレッドに関連している可能性があります。これを克服する
require 'ffi'
module Sleep
extend FFI::Library
ffi_lib FFI::Library::LIBC
attach_function :sleep, [:uint], :void
end
thread = Thread.start do
count = 1
while count <= 10
puts count
count += 1
sleep 0.5
end
end
puts "FFI sleep"
Sleep.sleep 5 # Everything blocks, second thread is run after sleep
puts "Ruby sleep"
sleep 5 # Scheduling works, other thread runs simultaneously
thread.join if thread.alive?
一つの方法、FFI通話を行うために別のプロセスをフォークし、その代わりに、タイムアウトを有することである。
以下の例では、Rubyの並行性はFFIを使用するときにどのように動作するかを示しています。フォークの子プロセスで
require 'ffi'
require 'timeout'
module Sleep
extend FFI::Library
ffi_lib FFI::Library::LIBC
attach_function :sleep, [:uint], :void
end
child_pid = Process.fork do
Signal.trap("INT") do
exit
end
Sleep.sleep 5
exit
end
begin
Timeout::timeout(2) do
Process.wait(child_pid)
end
rescue Timeout::Error
Process.kill("INT", child_pid)
end
、我々がやってに興味を持っているすべては、タイムアウトに達した場合には優しくシャットダウンするINT
信号のために待機している、そしてもちろん、FFIの呼び出しを行うこと。
親プロセスでは、子プロセスがタイムアウトしない限り、子プロセスをタイムアウトさせるだけで済みます。
はFFIの代替があるか、この問題を克服するための回避策があります。 –
私の回答を回避策で更新しました。 – gnab
回避策は機能しましたが、多くのプロセスが作成されました。時間の経過とともに、私のサーバーは使用不能になります。 –