所以我想调用两个后台ssh进程:
ssh -D localhost:8087 -fN aws-gateway-vpc1
ssh -D localhost:8088 -fN aws-gateway-vpc2
这些网关无法让我设置authorized_keys 文件,因此必须提示我输入交互式密码。这就是为什么我使用该-f
标志而不是 shell 的原因&
,它只会在我进行交互身份验证后将进程置于后台。
在这种情况下,我似乎无法使用$!
bash 变量来获取最近 [self] 后台进程的 pid。
如果中断的话,我还有哪些其他选项可以找到正确的 pid 以便稍后杀死?
答案1
通过 grep 查找 pid 可能容易出错。另一种选择是使用SSH 的ControlPath
选项ControlMaster
。这样您就可以让 ssh 命令侦听控制套接字并等待来自后续 ssh 调用的命令。
尝试这个
ssh -D localhost:8087 -S /tmp/.ssh-aws-gateway-vpc1 -M -fN aws-gateway-vpc1
# (...)
# later, when you want to terminate ssh connection
ssh -S /tmp/.ssh-aws-gateway-vpc1 -O exit aws-gateway-vpc1
该exit
命令允许您在不知道 PID 的情况下终止进程。如果您确实需要 PID,可以使用以下check
命令来显示它:
$ ssh -S /tmp/.ssh-aws-gateway-vpc1 -O check aws-gateway-vpc1
Master running (pid=1234)
答案2
正如您所说,它$!
不起作用,因为它尚未被当前 shell 置于后台。事实上,该ssh
进程甚至不是您启动它的 shell 的子进程。至少在我的 Arch 系统上,它作为 PID 进程的子进程1
运行init
。
因此,要获取 PID,您可以简单地使用ps
:
$ ssh -f localhost sleep 100
$ ps aux | grep '[s]sh.*-f'
terdon 20648 0.0 0.0 43308 680 ? Ss 12:15 0:00 ssh -f localhost sleep 100
这告诉我 PID 是20648
*。
或者,更简单地,使用pgrep -f
:
$ pgrep -f 'ssh.*-f'
20648
并且,杀死它(他们):
pkill -f 'ssh.*-f'
*看这如果您想知道命令[s]
中的,请提问grep
。
答案3
我没有 50 个代表点,所以我必须回答...这个示例并不完整,因为您必须向 ssh 添加多路复用控制。在 Debian 上,它默认未启用,因此您必须通过 ssh_config 文件启用它,或者使用“-o ControlMaster=yes”选项更容易启用它。尝试这个例子,它适用于每个 ssh。它将通过端口 3306 从 example.org 到端口 3307 上的本地主机。在示例中,我添加了一个端口选项,因为您还需要将其提供给 -O check 命令。
ssh -p1234 -TqfN -L 3307:localhost:3306 [email protected] -o ControlMaster=yes -o ControlPath=/dev/shm/control:%h:%p:%r -S /dev/shm/control:%h:%p:%r
然后你可以使用检查、退出等。像这样
ssh -p1234 -o ControlPath=/dev/shm/control:%h:%p:%r -O check [email protected]
主站运行(pid=xxxx)