有两台机器,其中一台有脚本wait_for_signal.sh
,第二个有一个名为controller.py
。每个脚本的代码如下所示。
目的controller.py
是产生一个调用的子进程wait_for_signal.sh
脚本通过ssh
。当控制器需要退出时,它需要向正在运行的远程进程发送中断wait_for_signal.sh
.
等待信号.sh
#!/bin/bash
trap 'break' SIGINT
trap 'break' SIGHUP
echo "Start loop"
while true; do
sleep 1
done
echo "Script done"
控制器.py
import os
import signal
import subprocess
remote_machine = user@ip
remote_path = path/to/script/
remote_proc = subprocess.Popen(['ssh', '-T', remote_machine,
'./' + remote_path + 'wait_for_signal.sh'],
shell=False, stdout=subprocess.PIPE,
stderr=subprocess.PIPE)
# do other stuff
os.kill(remote_proc.pid, signal.SIGINT)
目前,信号发送到本地计算机上启动 ssh 连接的进程,而不是远程计算机。这会导致本地进程停止,但远程进程继续执行。
ssh 是如何工作的以及它停止时会向远程计算机发送什么类型的信号?如何向通过 ssh 连接启动的远程进程发送适当的信号?
你正在调用ssh
与-T
选项,这意味着它不会为远程会话分配 PTY(伪 TTY)。在这种情况下,无法通过 ssh 会话向远程进程发出信号。
SSH 协议有一个向远程进程发送信号的消息 https://www.rfc-editor.org/rfc/rfc4254#section-6.9。但是,您可能将 OpenSSH 用于客户端或服务器或两者,并且据我所知,OpenSSH 不实现信号消息。所以OpenSSH客户端无法发送消息,OpenSSH服务器也不会对其采取行动。
有一个用于发送“中断”消息的 SSH 扩展 https://www.rfc-editor.org/rfc/rfc4335 which is由 OpenSSH 支持。在交互式会话中,OpenSSH 客户端有一个转义序列 http://man.openbsd.org/ssh#ESCAPE_CHARACTERS您可以键入该命令以向服务器发送中断。 OpenSSH 服务器通过向远程会话的 PTY 发送中断来处理中断消息,unix PTY 通常会将中断视为 SIGINT。然而,中断从根本上来说是一个 TTY 概念,对于没有 PTY 的远程会话来说,这些都不起作用。
我可以想到两种方法来做你想做的事:
-
Invoke ssh
with the -tt
parameter instead of -T
. This will cause ssh to request a TTY for the remote session. Running the remote process through a TTY will make it act like it's running interactively. Killing the local ssh process should cause the remote process to receive a SIGHUP. Writing a Ctrl-C to the local ssh process's standard input should cause the remote process to receive a SIGINT.
-
打开另一个到远程主机的 ssh 会话并使用killall https://linux.die.net/man/1/killall或其他一些命令来向您想要向其发出信号的进程发出信号。
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)