SSH ProxyCommandに関するすべて

SSH ProxyCommandに関するすべて

次のProxyCommandの詳細な説明とそのタスクの具体的な詳細を探しています。可能であれば、徹底的に分析して改善するのに役立ちますか?他に何もない場合は、読みやすさのためです。

ProxyCommand ssh gatewayserver 'exec 3<>/dev/tcp/targetserver/22; cat <&3 & cat >&3;kill $!'

ベストアンサー1

/dev/tcp(私のシステムにはデバイスはありませんが、次のセクションに接続されているTCPソケットをbash割り当てる処理機能が組み込まれているようです。)/host/port

したがって、sshエージェントコマンドは、gatewayserver次のことを行うシェルを安全に実行します。

exec 3<>/dev/tcp/targetserver/22

つまり、ファイル記述子3にソケット(targetserver/に接続されている)を接続しますport。それから:

cat <&3 & cat >&3; kill $!

これは、ファイル記述子0(入力)と1(出力)とファイル記述子(入力と出力)3の間の双方向リダイレクト(2つの別々のプロセスを使用する)方法です。他のプロセスが返された後、kill $!バックグラウンドプロセスを終了します。cat <&3cat >&3

これらすべては、より標準的な内容にすぎません。

ProxyCommand ssh gatewayserver "tcpconnect targetserver port"

コマンドの代わりに/dev/tcp(または)関数を使用してください。bashtcpconnect


詳細は:

SSHが使用するプロキシコマンドは、リモートホストへの接続方法を定義するために使用されますtargetserver(Sshプロトコルが使用されるため、暗号化は実際には必要ありません)。超過このチャンネル)。私たちの場合は、そのターゲットホストへの接続を確立しようとしています(おそらくファイアウォールが直接gatewayserver接続をブロックしているため)。targetserver

だからプロセス

ssh gatewayserver 'exec 3<>/dev/tcp/targetserver/22; cat <&3 & cat >&3;kill $!'

始まります:

  • filedescriptor(fd)1(標準出力とも呼ばれる)は、SSHクライアントがターゲットホストにデータを送信するために使用されます。
  • fd 0(標準入力とも呼ばれる) は、SSH クライアントがリモートホストからデータを読み取るために使用されます。

ssh gatewayserver最初のホップでゲートウェイに初めて接続するために使用されます。ssh元のホスト上のプロセスのfd / fdを、0ゲートウェイホストで実行されているシェルのfd / fdに渡す新しいシェルをこのホストで起動します。このシェルで実行されるコマンドは次のとおりです。101

exec 3<>/dev/tcp/targetserver/22; cat <&3 & cat >&3;kill $!

コマンドがないと、exec何もしません。シェル自体の次のリダイレクトのみを適用します。一般的なリダイレクトは次のとおりです。

  • n>filefdをn次にリダイレクトします(省略した場合はfile書き込み専用で開く)。n1
  • n<filefdをn次にリダイレクトします(省略した場合はfile読みやすいように開きます)。n0
  • n<>filefdを(読み取りおよび書き込み用に開く)nにリダイレクトします。file
  • n>&mまたは に指定するn<&mと、n<>&mfd はn以前に fd が指したファイルにリダイレクトされますm

ここでは以下が使用されます。

exec 3<>/dev/tcp/targetserver/22

これは、新しく作成されたfdを3非常に特別なファイル/dev/tcp/targetserver/22(実際のファイルではないがbash自体が理解するファイル)にリダイレクトします。ここでbashはtargetserverポート22(サーバーが見つかると予想される場所)で通信するためにソケット(tcpプロトコルを使用する特別なファイル)を生成し、sshdファイルはfdで開きます(読み取りおよび書き込み用)3

これで、データをfd 0(クライアントのデータ)に「ポンプ」し、それをfd 3(宛先サーバーへの接続)に送信する必要があります。また、fdのデータを「ポンピング」3し、それをfd 1(クライアントの結果)に送り返すことで、逆方向通信を保証する必要があります。これら2つの「ポンプ」は、cat2つのプロセスを使用して設定される。

  • cat <&33 シェルのfdから読み書きします1。)
  • cat >&30 シェルのfdから読み書きします3。)

どちらもcat並列に実行する必要があるため、1つはバックグラウンドで実行する必要があります。ここでは、fd 0(おそらくtty)から読むことが前景に残りたいと思います。これは以下を提供します:

cat <&3 &  #run in the background
cat >&3; kill $!

kill $!バックグラウンドプロセスを終了するために使用されます($!最後のバックグラウンドプロセスのpidに拡張されます)。このようにしてクライアントがクラッシュすると、フォアグラウンドプロセスが終了し、killが実行され、最後のプロセスも終了します。

それだけです!私たちは次の橋を建設しました。

ソースホスト - (ssh)→ゲートウェイ - (ポンプ+ソケット)→ターゲットサーバー(ポート22)

一つssh user@targetserverについて起源ホストは次に接続できます。ターゲット先生はこの橋を通り過ぎます!

おすすめ記事