FreeBSDのRST挙動

友人から「FreeBSDは不正なシーケンス番号のRSTを受けた場合でもセッションを切ってしまう」、と言われたので、まさかいまどきそんなこともあるまい、と思い調べてみました。FreeBSD 6.1Rのnetinet/tcp_input.cを見てみると、

static int tcp_insecure_rst = 0;
SYSCTL_INT(_net_inet_tcp, OID_AUTO, insecure_rst, CTLFLAG_RW,
    &tcp_insecure_rst, 0,
    "Follow the old (insecure) criteria for accepting RST packets.");
 
                                          :
                                          :
 
        if (thflags & TH_RST) {
                if ((SEQ_GEQ(th->th_seq, tp->last_ack_sent) &&
                    SEQ_LT(th->th_seq, tp->last_ack_sent + tp->rcv_wnd)) ||
                    (tp->rcv_wnd == 0 && tp->last_ack_sent == th->th_seq)) {
                        switch (tp->t_state) {
 
                        case TCPS_SYN_RECEIVED:
                                so->so_error = ECONNREFUSED;
                                goto close;
 
                        case TCPS_ESTABLISHED:
                                if (tp->last_ack_sent != th->th_seq &&
                                    tcp_insecure_rst == 0) {
                                        tcpstat.tcps_badrst++;
                                        goto drop;
                                }
                                          :
                                          :

てな感じになっているので、ESTABLISHEDになっているところにRSTが来た場合、自分が最後に送ったACKと異なるシーケンス番号を持ったRSTが来てもBad RSTのカウンタだけ上げてドロップすることが分かりました。sysctlでこの挙動をコントロールできるようになっているところを見ると、確かに過去は友人のような動作をしていたみたいです。

一安心です。

「FreeBSDのRST挙動」への2件のフィードバック

  1. コードもきちんと見るとは、すごいです。
    FreeBSDのコードは初めて見ました。
    ただ、意味はばっちりわかるのは僕もその筋の人って事ですかね。
     
    sysctlでオン(1)するとオペレーションできるのってCLIと同じですから・・・
     
     

  2. kazuさん
    > ただ、意味はばっちりわかるのは僕もその筋の人って事ですかね。
     
    思いっきりその筋の人でしょ 🙂
     
     

コメントを残す

メールアドレスが公開されることはありません。 * が付いている欄は必須項目です

このサイトはスパムを低減するために Akismet を使っています。コメントデータの処理方法の詳細はこちらをご覧ください