当我通过 ssh 连接到一台机器时,我无法使用“Ctrl + C”组合,因为它会向会话发送终止信号。
例如,我从主机启动到客户端计算机的 SSH 会话,在客户端上运行“top”命令,当我想退出“top”时,我使用“Ctrl + C”组合键,SSH 会话关闭。此过程的输出如下:
[root@client ~]# top //I use Ctrl + C to exit from top
[root@main ~]# Killed by signal 2.
“ssh -vvv”输出:
Last login: Tue Feb 13 14:08:57 2018 from main.company.intra
[root@client ~]# debug3: send packet: type 1
debug1: channel 0: free: client-session, nchannels 1
debug3: channel 0: status: The following connections are open:
#0 client-session (t4 r0 i0/0 o0/0 fd 4/5 cc -1)
Killed by signal 2.
[root@main ~]#
当我尝试使用 MobaXterm 进行 ssh 时,没有任何问题。所以问题不在于服务器配置,而在于 PuTTy 配置。
我认为当我使用 MobaXterm 时,Ctrl+C 已发送到客户端服务器,而使用 PuTTy 时,中断信号已发送到主服务器(因此是 ssh 连接过程)。我认为如果我们修复此路由,问题就会解决。
答案1
我不能使用“Ctrl + C”组合,因为它会向会话发送终止信号。
Ctrl+C通常应该发送一个中断信号. 中断信号是信号 2。因此它正在执行预期的操作。
Killed by signal 2
该消息不是您通常会看到的消息,但它非常正确。该进程退出是因为它收到了信号 2,打断+SIGINT
产生的信号CtrlC
首先让我们看看哪个组合键对应中断信号
$ stty -a | grep intr
intr = ^C
现在让我们检查一下中断信号的数值
$ man 7 signal
...
Signal Value Action Comment
-----------------------------------------------------------------------
SIGHUP 1 Term Hangup detected on controlling terminal
or death of controlling process
SIGINT 2 Term Interrupt from keyboard
SIGQUIT 3 Core Quit from keyboard
SIGFPE 8 Core Floating point exception
SIGKILL 9 Term Kill signal
SIGSEGV 11 Core Invalid memory reference
请注意,KILL 信号是信号 9(而不是信号 2)。您可以使用该kill
命令发送这些信号中的任何一个,但其中只有一个是 KILL 信号,并且它不是信号 2。
所以问题仍然是,是什么产生了“被信号 2 杀死”这条消息。
如果我们看看https://stackoverflow.com/questions/3165511/how-to-make-terminal-not-print-killed-by-signal-2-on-catching-a-siginttrap SIGINT
我们看到,如果您有一个用于拦截信号并执行特殊处理的脚本,则可以生成此消息。
也许您有一个早于的top
别名或脚本?top
$PATH
/usr/bin
$ type top
top is /usr/bin/top
您建议中断从 *nix 计算机main
到 *nix 计算机的SSH 会话client
。让您停留在 *nix shell 提示符处。
从您提到 MobaXterm 作为 PuTTY 的替代品,我推断您使用的是 Windows 版 PuTTY,而不是 *nix 版 PuTTY。如果是这样,不清楚为什么您的 SSH 连接分为两部分(Win-PC -> “主” -> “客户端”)。
如果您使用 PuTTY 登录到主程序,然后使用ssh
登录到客户端,那么 PuTTY 的 ^C 由主程序处理而不是传递给客户端,这并不奇怪top
。
我们可以参考https://unix.stackexchange.com/questions/102061/ctrl-c-handling-in-ssh-session讨论了这个话题。
ssh remotehost
将在远程主机上运行交互式会话。在客户端,ssh 将尝试将 stdin 使用的 tty 设置为“原始”模式,而远程主机上的 sshd 将分配一个伪 tty 并将您的 shell 作为登录 shell 运行(例如 -bash)。设置原始模式意味着通常会发送信号的字符(例如 Ctrl-C 和 Ctrl-)将直接插入到输入流中。ssh 将按原样发送这些字符到远程主机,它们可能会发送 SIGINT 或 SIGQUIT,并且通常会终止任何命令并返回到远程主机上的 shell。只要远程 shell 处于活动状态,ssh 连接就会保持活动状态。
...
ssh remotehost command args ...
将在远程主机上运行非交互式会话。在客户端,ssh 不会将 tty 设置为原始模式(当然,除非读入密码或密码短语)。如果您键入 Ctrl-C,ssh 将收到 SIGINT 并立即终止,甚至不会发出与远程主机的连接已关闭消息。
因此,我怀疑您的 PuTTY 会话的配置与您的 MobaXterm 会话不同,并且发生了一些您(以及我们)不知道的事情。
PuTTY 不是在发送信号,而是在发送 ASCII 控制字符。这很容易证明。我们只需要求 shell 不对 ASCII 控制字符 0x03(ETX、Ctrl+C)进行任何特殊处理,然后查看 PuTTY 发送的内容:
$ stty intr ^A
$ cat -v
I will now press Ctrl + C ^C
I will now press Ctrl + A
$ $ echo $?
130
看http://tldp.org/LDP/abs/html/exitcodes.html130 = 128+2 = 信号 2。在这种情况下,我使用 ^A 将 0x01 发送到 shell,然后 shell 向进程发送信号 2。top
^C 仅发送 0x03,cat-V
显示为 ^C。
因此,我不会试图找出为什么 Putty 会“发送” SIGINTR 而 mobaXterm 不会。它们都不会这样做。它们只是发送一个 ASCII 控制字符。
那么看看你是如何调用PuTTY的,是通过单击桌面图标吗?该图标是否具有Target中带有额外参数的属性(Alt + Enter)?等等。