用 Bash 取代 ProxyJump

用 Bash 取代 ProxyJump

我需要在一些遠端盒子上進行一些開發。幸運的是,我有 shell 存取權限,但我需要透過將 AllowTcpForwarding 設定為 false 的網關。

我在文檔中看到了一個高峰,它說:

AllowTcpForwarding 指定是否允許 TCP 轉送。預設值為“是”。請注意,停用 TCP 轉送並不會提高安全性,除非使用者也被拒絕 shell 訪問,因為他們始終可以安裝自己的轉發器。

我將如何安裝(或建置)我自己的轉發器?我的目標是建立一個使用 Pycharm 的遠端解釋器透過 SSH 並將其綁定到某個本地端口,資料通過 ssh 饋送,通過網關,然後到達實際運行程式碼的開發盒。我想我可以以某種方式利用 nc 或其他一些 unix 實用程式來幫助完成工作。

我知道我可以通過以下方式 ssh 到我的遠端盒子:

ssh -t user1@gateway ssh user2@devbox

但顯然這個選項在pycharm中不可用。我必須能夠打開一些本地端口,以便

ssh -p 12345 localhost
(or variant)

會將我連接到 user2@devbox。這將允許我配置遠端解釋器以使用連接埠12345連接localhost到遠端盒子。

答案1

只要能執行socat本地 和 on gateway(或甚至只是bashcaton gateway,請參閱最後一個範例!)並且允許不是使用pty是8位元乾淨的,可以透過ssh建立隧道。以下是 4 個範例,對先前的範例進行了改進:

基本範例工作一次

(讓它分叉將需要每個隧道一個 ssh 連接,這不好)。必須轉義:socat 才能接受 exec 指令:

  • 術語1:
    $ socat tcp-listen:12345,reuseaddr exec:'ssh user1@gateway exec socat - tcp\:devbox\:22',nofork
    
  • 術語2:
    $ ssh -p 12345 user2@localhost
    
  • 術語1:
    user1@gateway's password:
    
  • 術語2:
    user2@localhost's password: 
    

反轉第一個和第二個位址使套接字立即可用

socat必須保持負責,所以不nofork

  • 術語1:
    $ socat exec:'ssh user1@gateway exec socat - tcp\:devbox\:22' tcp-listen:12345,reuseaddr
    user1@gateway's password:
    
  • 術語2:
    $ ssh -p 12345 user2@localhost
    user2@localhost's password:
    

用一個ControlMasterSSH

A 允許在僅使用到網關的單一 SSH 連接時進行分叉,從而提供類似於通常連接埠轉送的行為:

  • 術語1:
    $ ssh -N -o ControlMaster=yes -o ControlPath=~/mysshcontrolsocket user1@gateway
    user1@gateway's password:
    
  • 術語2:
    $ socat tcp-listen:12345,reuseaddr,fork exec:'ssh -o ControlPath=~/mysshcontrolsocket user1@gateway exec socat - tcp\:devbox\:22'
    
  • 第3項:
    $ ssh -p 12345 user2@localhost
    user2@localhost's password:
    

bashcat可用gateway

透過使用bash內建tcp重定向,和兩個半雙工cat命令(用於全雙工結果),甚至不需要遠程socatnetcat.處理多層嵌套和轉義引號有點尷尬,也許可以做得更好,或者透過使用遠端bash腳本來簡化。必須注意分叉cat僅用於輸出:

  • 第 1 項(無變化):
    $ ssh -N -o ControlMaster=yes -o ControlPath=~/mysshcontrolsocket user1@gateway
    user1@gateway's password:
    
  • 術語2:
    $ socat tcp-listen:12345,reuseaddr,fork 'exec:ssh -T -o ControlPath=~/mysshcontrolsocket user1@gateway '\''exec bash -c \'\''"exec 2>/dev/null 8<>/dev/tcp/devbox/22; cat <&8 & cat >&8"\'\'\'
    
  • 第3項:
    $ ssh -p 12345 user2@localhost
    user2@localhost's password:
    

答案2

用 Bash 取代 ProxyJump

樓上的想法不錯!這是我的通用 ssh_config 版本代理跳轉不管用因為允許Tcp轉送設定為 no,我的預設 shell 是 BASH:

ProxyCommand=ssh -T user1@gateway "exec 3<>/dev/tcp/%h/%p 2<&- ; cat <&3 & cat >&3 ; kill $!"
  • -T禁用偽終端分配
  • 執行不會創建新進程(bash)
  • 3<>只是重定向到可用的檔案描述符
  • /dev/tcp/...會要求 bash 打開對應的 TCP 套接字。
  • %H%p將由您的 OpenSSH 客戶端評估為開發盒22
  • 2<&-將關閉 STDERR (您也可以將其重新導向至 /dev/null)
  • 貓<&3&將在背景讀取選定的檔案描述符3
  • 貓 >&3將在前台寫入我們的文件描述符
  • 殺掉$!會扼殺“閱讀”貓 <&3當您關閉/斷開連接時,命令在背景執行。否則它會繼續運行。

當 ProxyJump 在跳轉伺服器上被停用時,它可以代替我,但我真的不想在那裡轉發我的私鑰或在沒有額外加密等級的情況下輸入任何密碼。使用其他 SSH_AUTH_SOCK 作為 root 或透過按鍵完全記錄終端會話都是真實的事情。

但請務必確保您不會違反任何適用於您的政策!

答案3

喔不,我們差點忘了 Netcat!

如果您的跳轉主機上有 Netcat(任何版本),您可以在設定中使用它而不是 ProxyJump,通常如下所示:

ProxyCommand=ssh -T user1@gateway "exec nc %h %p"

或從命令列:

ssh user2@devbox -oProxyCommand="ssh -T user1@gateway 'exec nc devbox 22'"

答案4

我只是設定另一個 sshd 在不同的連接埠上運行。
編輯設定以允許 tcpforwarding。

cp /etc/ssh/sshd{,-second}_config 

編輯 sshd-second_config

Port 22220
cp /usr/lib/systemd/system/sshd.service  /etc/systemd/system/sshd-second.service

按以下方式變更 /etc/systemd/system/sshd-second.service:

Description=OpenSSH server second instance daemon
ExecStart=/usr/sbin/sshd -D -f /etc/ssh/sshd-second_config $OPTIONS

ExecStart 行可能會有所不同,具體取決於版本。

systemctl daemon-reload
systemctl enable sshd-second.service --now

更多資訊可以在這裡找到:
https://access.redhat.com/solutions/1166283

現在您應該可以轉發您想要的任何內容。

相關內容