こちらが続編になります。Windows 7でCIFS遅延が解決した
Windows 7 <-> Windows 2008 R2で通信をする際にWindows 7からWindows 2008 R2 へアップロードするときに極端にパフォーマンスが遅い。
- ダウンロード: 6.4MB/s
- アップロード: 150kB/s
パケットをWiresharkで確認してみる。
エラーがいくつか出ている。
- TCP Dup ACK
- TCP Fast Retransmission
- TCP segment of a reassembled PDU
- TCP Out-of-Order
とりあえずエラーが出ているのはわかったので個別に調べる。
TCP DupACKs and TCP Fast RetransmitsによればTCP Dup ACK, TCP Fast Retransmissionは対で発生するエラーリカバリーの動作だ。このメッセージが出るときにはパケットロスが発生している。その結果受信側は待っているACKを送信者側に送る。これがTCP Dup ACK。このパケットを受け取ると送信者側は優先的に該当パケットを送る。これがTCP Fast Retransmissin。
ではサーバーに対してパケットロスが発生してるかをping -tコマンドで確認してみた。
全く発生していない。。。
TCP Out-of-orderは受信がパケットを順番には受け取れていないことをしめす。ここで順番が守られていないというのはどういう意味か。
- 順番に受け取れていないけど最終的には受け取れている。
- そもそも届かない。
どちらかではあるが、ここでDup ACKが発生していることを考えると後者の”そもそも受け取れていない”と考えられる。
結局はパケットロスが発生しているから受け取れないとなってしまい、そもそも原因がわからない。
では、TCP segment of a reassembled PDUはどうか。これはMSSを超えたためにTCPレイヤで分割されたことを意味する。ふむふむ、MSSはTCPで通信する際に格納できるユーザーデータの最大サイズを示す。
MSS = Ethernetのフレームサイズ(1518) – IPヘッダ(20) -TCPヘッダ(20) = 1460
よってサーバー側がサイズ1460以上でデータを送信していると推測される。
ではMSSを超えた通信が発生した可能性を考えていろいろ調べたところ以下の記述を見つけた。
If you turn off the “Allow subdissector to desegment TCP streams” option in the TCP dissector’s options you’ll find that Wireshark interprets this differently:
Why does WireShark think this frame is a TCP segment of a reassembled PDU
設定を変えてみる
確かにretransmissionがなくなり、その代わり Continuationになった。
ただ実際にログを確認するとretransmissionでDup ACKが消えていることがわかったのでこの設定はいらないようだ。
ではこのエラーがWindows 7特有のTCPレイヤ上の問題と考えたらどうだろうか。Windows 7独自のパラメータがあるかもしれない。見つけたのが下記のホームページ。
Windows 7 Network Slow – 6 Easy Ways to Make it Fast
一通り試してみたがやはり結果は変わらない。
では別のレイヤで起きている可能性を考えてみた。pingでは問題が起きていないことから下位のIPレイヤではなく、上位。この場合にはSMBのプロトコルが怪しい。
調べてみるとWindows 7 / Windows 2008になってからSMBのバージョンがV2になったことがわかった。
この辺でWindows上のSMBについての技術情報が詳しい。
- Windows Server 2012 R2: Which version of the SMB protocol (SMB 1.0, SMB 2.0, SMB 2.1, SMB 3.0 or SMB 3.02) are you using?
- How to enable and disable SMBv1, SMBv2, and SMBv3 in Windows Vista, Windows Server 2008, Windows 7, Windows Server 2008 R2, Windows 8, and Windows Server 2012
ではSMBプロトコルをV1にしてみたらどうか。
To disable SMBv2 and SMBv3 on the SMB server, run the following cmdlet:
Set-ItemProperty -Path “HKLM:\SYSTEM\CurrentControlSet\Services\LanmanServer\Parameters” SMB2 -Type DWORD -Value 0 -Force