サードパーティのサーバーが、セットアップしたEC2インスタンスにUDPパケットを送信し、それらのパケットをローカルマシンにルーティングしようとしています。
クライアントはこれらのパケットをポート8975に送信します
そのために、最初にec2インスタンスへのSSHトンネルを確立しました
ssh -4 -L 10000:localhost:10000 -i ~/.ssh/xxxx.pem [email protected]
私のリモートマシン-このコマンドを使用して、ポート8975で受信したパケットを10000にルーティングしました
netcat -l -u -p 8975 > /tmp/udp2tcp | netcat -l -p 10000 < /tmp/udp2tcp
udp2tcp
はfifoファイルです
私のローカルマシンで-受信したtcp
パケットを取得して、UDPに戻しています
netcat localhost 10000 > /tmp/tcp2udp | netcat -l -u -p 8975 < /tmp/tcp2udp
netcat localhost 10000
を実行すると、ローカルマシンに流入するパケットを確認できます
しかし、何らかの理由で、UDPとしてポート8975にルーティングされるパケットはありません-何をする必要があるのか正確にはわかりません
Sudo tcpdump -i any -S -vvv port 10000
を実行すると
これは私がパケットをフロギンすることを示しています
15:39:10.053013 IP (tos 0x0, ttl 64, id 64725, offset 0, flags [DF], proto TCP (6), length 52)
localhost.48974 > localhost.webmin: Flags [.], cksum 0xfe28 (incorrect -> 0x5674), ack 1261213200, win 10567, options [nop,nop,TS val 1064223053 ecr 1064223053], length 0
sudoを実行するとtcpdump -i any -S -v port 8975
-何も表示されません
SSHポート転送の代わりに、ポイントツーポイントトンネルデバイス、SSH、および以下で説明する手順を使用して、これらのUDPパケットをローカルマシンに転送できます。
EC2インスタンスで、次の手順を実行します。
/etc/ssh/sshd_config
ファイルで、構成パラメーターPermitTunnel
をpoint-to-point
またはyes
のいずれかに設定します。
パブリックネットワークからUDPパケットを受信するポイントツーポイントトンネルデバイスを作成します。
$ Sudo ip tuntap add dev tun8975 mode tun user ubuntu
$ Sudo ip addr add dev tun8975 172.16.19.22 peer 172.16.19.21
$ Sudo ip link set dev tun8975 up
このようなUDPパケットをトンネルデバイスに転送するようにIPTABLESまたはNFTABLESを構成します
$ Sudo iptables -t nat -A PREROUTING '!' -i tun8975 -p udp --dport 8975 -j DNAT --to-destination 172.16.19.21:8975
$ Sudo nft add rule ip nat PREROUTING iifname '!=' "tun8975" udp dport 8975 dnat to 172.16.19.21:8975
カーネルがネットワークインターフェイス間のIPパケット転送を許可していることを確認します。
$ Sudo sysctl -w net.ipv4.ip_forward=1
その後、ローカルマシンで次の手順を実行します。
SSHが転送されたUDPパケットを出力するために使用するポイントツーポイントトンネルデバイスを作成します。
$ Sudo ip tuntap add dev tun8975 mode tun
$ Sudo ip addr add dev tun8975 172.16.19.21 peer 172.16.19.22
$ Sudo ip link set dev tun8975 up
SSHに、安全なチャネルを介してトンネルデバイス間でトラフィックを転送するように要求します。
$ Sudo ssh -4 -o Tunnel=point-to-point -w 8975:8975 -i ~/.ssh/xxxx.pem [email protected]
コミュニケーションの問題を解決するためのあなたのアプローチには2つの問題があります。
最初の問題は、ローカルマシンで実行されるコマンドにあります。 netcat
コマンドパイプラインのUDP部分の-l
フラグを削除し、ローカルマシンの別のプロセス(別のnetcat
など)がUDPポート8975をリッスンし、そのポートに送信されたデータグラムを受信する必要があると思います。このシナリオのnetcat
は、クライアントモードで実行され、そのようなデータグラムを生成します。
2番目の問題は、これらのコマンドラインの構成方法にあります。
$ netcat -l -u -p 8975 > /tmp/udp2tcp | netcat -l -p 10000 < /tmp/udp2tcp
$ netcat localhost 10000 > /tmp/tcp2udp | netcat -l -u -p 8975 < /tmp/tcp2udp
それらはリダイレクトとパイプラインを混合します。私はパイプラインとリダイレクトセクションを Bash)から読みましたがマニュアルページ そして、リダイレクトの前にパイプラインが処理されることがわかったので、シェルがそのような構文を使用して標準ストリームを接続する方法を理解できません。
netcat
は、標準入力からソケットの送信側にデータを転送し、ソケットの受信側から標準出力にデータを転送することで機能します。これは、そのようなソケットがリモートサーバーに接続するクライアントソケットであるか、リモートクライアントからの接続を受け入れるサーバーソケットであるかに関係なく行われます。そのため、TCPとUDPソケット間でデータを転送するには、標準ストリームを適切に接続する必要があります。つまり、TCPのSTDOUTを接続する必要があります。 netcat
からUDPのSTDINnetcat
およびUDPのSTDOUTnetcat
からTCPnetcat
のSTDINに同時に。
おそらく、実行しているコマンドラインはすでにその目的を達成しています。それにもかかわらず、次のコマンドを使用して、より明示的なデータ転送を提案します。
リモートマシン上
$ cat /tmp/udp2tcp | netcat -l -u -p 8975 | netcat -l -p 10000 > /tmp/udp2tcp
ローカルマシン上
$ cat /tmp/tcp2udp | netcat localhost 10000 | netcat -u localhost 8975 > /tmp/tcp2udp
どちらの場合も、無名パイプは最初のnetcat
のSTDOUTを2番目のnetcat
のSTDINに接続し、名前付きパイプ(fifo)は2番目のnetcat
のSTDOUTを最初のnetcat
のSTDINに接続します。
コマンドライン引数に-4
フラグを追加して、IPv4スタックのみを使用するようにnetcat
に指示することを検討してください。これは、UDPポート8975をリッスンしているプロセスがIPv6と互換性がない場合に役立つ可能性があります。