MacのJavaのTimeout付きconnectまじぱねーっすwww
http://sdc.sun.co.jp/java/docs/j2se/1.4/ja/docs/ja/api/java/net/Socket.html
昨日tcpdumpでキャプチャしてたんすけど、こいつ勝手にtimeoutした時にFINを飛ばすんスよwww
で相手側のルータからRSTが帰って来るっていうwwwもう勘弁して欲しいっすw
RFC793にも、勝手にFIN送るなんてどこにも書いて無いッスwwwどこが不味いんすかね、Darwinスかね??Javaですかね。この辺はJNIで実装してるんでしょうけど、何が潜り込んでるのか分からないのと、これどこにどうやって報告したら良いんだ??
あ、実際の所弊害が出ます。それは今日のエントリで。予想外の形で繋がるかもしれませんが。
こんな感じ(with tcpdump)
import java.io.*; import java.net.*; import java.util.*; public class Test { public static void main(String[] args) { try { String src_address = InetAddress.getLocalHost().getHostAddress(); Socket socket = new Socket(); socket.bind(new InetSocketAddress(src_address,0)); int src_port = socket.getLocalPort(); System.out.println("src_address:"+src_address); System.out.println("src_port:"+String.valueOf(src_port)); //タイムアウトする様なアドレスとポートを指定してください。 socket.connect(new InetSocketAddress("適当なアドレス",適当なポート),5*1000); } catch(Exception e) { System.out.println(e); } } }
で、tcpdumpの結果を張っておきます
14:27:24.228650 IP わたしの > あいての: S 3537820671:3537820671(0) win 65535 <mss 1460,nop,wscale 3,nop,nop,timestamp 513457137 0,sackOK,eol> 14:27:25.228154 IP わたしの > あいての: S 3537820671:3537820671(0) win 65535 <mss 1460,nop,wscale 3,nop,nop,timestamp 513457146 0,sackOK,eol> 14:27:26.228955 IP わたしの > あいての: S 3537820671:3537820671(0) win 65535 <mss 1460,nop,wscale 3,nop,nop,timestamp 513457156 0,sackOK,eol> 14:27:27.229786 IP わたしの > あいての: S 3537820671:3537820671(0) win 65535 <mss 1460,sackOK,eol> 14:27:28.230499 IP わたしの > あいての: S 3537820671:3537820671(0) win 65535 <mss 1460,sackOK,eol> 14:27:29.227487 IP わたしの > あいての: F 3537820672:3537820672(0) win 65535 <- なんじゃこりゃ!! Mac Leopard Version 10.5.6 uname Darwin Kernel Version 9.6.0 javac 1.5.0_16 java version "1.5.0_16" Java(TM) 2 Runtime Environment, Standard Edition (build 1.5.0_16-b06-284) Java HotSpot(TM) Client VM (build 1.5.0_16-133, mixed mode, sharing) javac 1.6.0_07 java version "1.6.0_07" Java(TM) SE Runtime Environment (build 1.6.0_07-b06-153) Java HotSpot(TM) 64-Bit Server VM (build 1.6.0_07-b06-57, mixed mode)
Leopard Javaでは、こいつを使ってNAPT越えしましょう
Hole Punchのstepでこんなのを使うべき。
少なくとも、async connect
private void dummyConnect(String src_address,int src_port, String dst_address,int dst_port, int timeOut) { try { SocketChannel channel = SocketChannel.open(); channel.configureBlocking(false); Socket socket = channel.socket(); socket.setReuseAddress(true); System.out.println("Start ReBinding NatTravServerSocket"); for(;;) { try { socket.bind(new InetSocketAddress(src_address,src_port)); break; } catch(Exception e) { continue; } } System.out.println("End ReBinding NatTravServerSocket"); System.out.println("Recipient's Start Test Connection to Initiator"); channel.connect(new InetSocketAddress(dst_address,dst_port)); Thread.sleep(timeOut); System.out.println("Recipient's End Test Connection to Initiator"); socket.close(); channel.close(); } catch(Exception e) { System.out.println(e); } } }
以上。