1

MRI でパスし、JRuby 1.7+ で失敗するパイプから読み取るための簡単なテスト ケースがあります。これは、 JRUBY-6986で重大なバグとして報告されています。

tl;dr 16kb (16384 バイト) のファイルがパイプから完全に読み取られ、16kb + 1 バイトのファイルが失敗するのはなぜですか? 別のシステムでは、しきい値が 72kb (73728 バイト) であることがわかりました。

$ ruby​​ testpipe.rb 16384
開始...ハングしませんでした!
$ ruby​​ testpipe.rb 16385
開始中...^C

そこで、スクリプトは 16kb + 1 バイトでハングしました。

require 'open3'
path = "test.txt"
File.open(path, 'w') { |f| f.write('Z' * ARGV[0].to_i) }
STDOUT.write "Starting..."
Open3.popen3('cat', path) do |stdin, stdout, stderr|
  stdin.close
  readers = [stdout, stderr]
  while readers.any?
    ready = IO.select(readers, [], readers)
    # no writers
    # ready[1].each { ... }
    ready[0].each do |fd|
      if fd.eof?
        fd.close
        readers.delete fd
      else
        # read from pipe one byte at a time
        fd.readpartial 1
      end
    end
  end
end
puts "didn't hang!"

オペレーティング システムまたは JVM バッファ サイズによって、異なるシグナルが送信される原因になっている可能性はありIO.selectますか?

PS。Working With UNIX processesの著者であるJesse Storimerに再確認したところ、彼は私の使用法が正しいと信じています。IO.select

4

0 に答える 0