この質問の最後に新しい詳細が追加されました。原因を突き止めている可能性があります。
UDP OpenVPNベースのVPNをtap
モードで設定しています(tap
が必要なのは、VPNにマルチキャストパケットを渡す必要があるためです。tun
ネットワーク)、インターネット上の少数のクライアント。 TCP接続がVPNを介してフリーズすることが頻繁にあります。つまり、TCP接続(たとえば、SSH接続ですが、他のプロトコルでは同様の問題)、およびセッション中のある時点で、トラフィックはそのTCPセッションを介して送信されなくなります。
これは、SSHセッションでls
コマンドを実行した場合や、長いログファイルをcat
した場合など、大量のデータ転送が発生するポイントに関連しているようです。一部のGoogle検索では、いくつかの回答が表示されます サーバーの障害に関するこの前の例のように 。これは、原因としてMTUの問題である可能性が高いことを示しています。トラフィックが多い期間、VPNはVPNエンドポイント間のパイプのどこかにドロップしました。上記のリンクされた回答は、問題を軽減するために次のOpenVPN構成設定を使用することを提案しています:
fragment 1400
mssfix
これにより、VPNで使用されるMTUを1400バイトに制限し、TCP最大セグメントサイズを修正して、それより大きいパケットが生成されないようにします。これにより、問題が少し緩和されるようですが、それでも頻繁にフリーズが見られます。fragment
ディレクティブの引数としていくつかのサイズを試しました:1200、1000、576、すべて同じような結果になります。2つの間の奇妙なネットワークトポロジーは考えられませんVPNサーバーがインターネットに直接接続されている pfSense マシンで実行されており、クライアントも別の場所でインターネットに直接接続されています。
もう1つの奇妙なパズルのピース:tracepath
ユーティリティを実行すると、問題が解決するようです。サンプル実行は次のようになります。
[~]$ tracepath -n 192.168.100.91
1: 192.168.100.90 0.039ms pmtu 1500
1: 192.168.100.91 40.823ms reached
1: 192.168.100.91 19.846ms reached
Resume: pmtu 1500 Hops 1 back 64
上記の実行は、VPN上の2つのクライアント間で行われました。192.168.100.90
から192.168.100.91
の宛先へのトレースを開始しました。リンクで使用されるMTUを制限するために、両方のクライアントにfragment 1200; mssfix;
が構成されました。上記の結果は、tracepath
が2つのクライアント間の1500バイトのパスMTUを検出できたことを示唆しているようです。 OpenVPN構成で指定されたフラグメンテーション設定により、これは多少小さくなると思います。その結果はやや奇妙なことがわかりました。
ただし、見知らぬ人もいます:TCP接続が停止した状態(たとえば、途中でフリーズしたディレクトリリストを含むSSHセッション)の場合)、上記のtracepath
コマンドを実行すると、接続が再び開始されます!これが当てはまる理由についての合理的な説明はわかりませんが、このように感じます最終的に問題を根絶するためのソリューションを指している可能性があります。
誰か他のことを試すための推奨事項はありますか?
編集:私は戻ってこれをもう少し見てみましたが、さらに混乱する情報しか見つかりませんでした:
上記のように、OpenVPN接続を1400バイトでフラグメント化するように設定しました。次に、インターネット経由でVPNに接続し、Wiresharkを使用して、ストールが発生している間にVPNサーバーに送信されたUDPパケットを調べました。指定された1400バイトカウントを超えるものはなかったため、断片化は適切に機能しているようです。
1400バイトのMTUで十分であることを確認するために、次の(Linux)コマンドを使用してVPNサーバーにpingを実行しました。
ping <Host> -s 1450 -M do
これは(私は信じています)フラグメンテーションを無効にして1450バイトのパケットを送信します(1600バイトのように明らかに大きすぎる値に設定した場合、少なくとも動作しないことを確認しました)。これらは問題なく動作するようです。問題なくホストから返信が届きます。
したがって、これはMTUの問題ではない可能性があります。他に何があるのか混乱しています!
編集2:うさぎの穴がさらに深くなり続けています。問題をもう少し特定しました。 VPNクライアントが使用する正確なOSに関連しているようです。私は問題を少なくとも3台のUbuntuマシン(バージョン12.04から13.04)で再現しました。大きなログファイルをcat
- ingするだけで、SSH接続のフリーズを1分程度で確実に複製できます。
ただし、CentOS 6マシンをクライアントとして使用して同じテストを実行しても、問題は発生しません!私は、Ubuntuマシンで使用していたのとまったく同じOpenVPNクライアントバージョンを使用してテストしました。接続がフリーズすることなく、何時間もログファイルをcat
できます。これは最終的な原因に関する洞察を提供するようですが、私はその洞察が何であるのかよくわかりません。
Wiresharkを使用してVPN上のトラフィックを調べました。私はTCP=エキスパートではないので、細かいことをどうするかわかりませんが、要点は、ある時点で、帯域幅が制限されているためにUDPパケットがドロップされることですVPNトンネル内でTCP=再送信が発生します。CentOSクライアントでは、これらの再送信が適切に行われ、問題なく動作します。ただし、Ubuntuクライアントのある時点で、リモートエンド同じTCPセグメントを繰り返し再送信し始めます(再送信のたびに送信遅延が増加します)。クライアントは、有効なように見えるものをTCP ACKをそれぞれに送信します再送信しますが、リモートエンドは引き続き同じTCPセグメントを定期的に送信し続けます。これにより、無限に拡張され、接続が停止します。私の質問は次のとおりです。
CentOSノードとさまざまなUbuntuリリースの一般的な違いの1つは、UbuntuのLinuxカーネルバージョンがはるかに新しいことです(Ubuntu 12.04の3.2から13.04の3.8へ)。新しいカーネルのバグへのポインタかもしれませんか?もしそうなら、問題を経験しているのは私だけではないでしょう。これは特にエキゾチックなセットアップのようには思えません。
このコマンドは私のためにそれを解決します:
$ Sudo ip link set dev tun0 mtu 1350 && echo ":)"
あなたはtun0設定を確認することができます
$ ip a s
乾杯!
TCPでウィンドウスケーリングを無効にします。
sysctl -w net.ipv4.tcp_window_scaling=0
その後、VPNを介したDebian/UbuntuシステムへのSSHが正常に機能します。
PuTTYを使用するWindowsでは、VPN接続のローカル接続に移動してMTUを変更する必要があります->ネットワークインターフェースの詳細(TAP Windowsアダプターなど)->詳細設定->プロパティ-> MTU(何かに変更) 1500未満)。再接続する必要がある場合があります。 WindowsとPuTTYで動作しました