パスワードを忘れた? アカウント作成
663648 journal

babyAの日記: recvfromではまりまくり

日記 by babyA

たとえばUDPソケットを使う簡単なサーバ
--
require 'socket'
require 'thread'

q = Queue.new
sk = UDPSocket.open
sk.bind("", 30905)
#受信スレッド
r = Thread.start {
            loop {
                dat, addr = sk.recvfrom(0xffff)
                p v = [dat, addr[2], addr[1]]
                q.push v
            }
        }
#送信スレッド
s = Thread.start {
            loop {
                dat, host, port = q.shift
                sk.send(dat, 0, host, port)
            }
        }
loop{ sleep(1) }
--
にクライアントから送信していると受信スレッドの
recvfromが先に進まなくなることがある。
Linux上では問題なし。
windows(cygwin版,mswin32版)だとうまくいかない。
調べてみると送信スレッドがsendするときに
クライアント側ソケットが既にない場合に必ず起きる。
Thread.abort_on_exception = true
でやってみたらrecvfromが例外を起こして受信スレッドが
死んでいることが判明。
windowsでは送信先にソケットが無いとこへsendすると
ICMPを受けてrecvfromが例外発生するのかな?(よくわかんないけど)

とりあえず
begin
    dat, addr = sk.recvfrom(0xffff)
rescue Exception
    retry
end
で例外を補足してやればうまくいく。
例外のtypeはruby1.6.8(cygwin),ruby1.8(mswin32)で
違うからExceptionで補足するのがよさげだ。

この議論は賞味期限が切れたので、アーカイブ化されています。 新たにコメントを付けることはできません。
typodupeerror

吾輩はリファレンスである。名前はまだ無い -- perlの中の人

読み込み中...