为什么Ctrl-C不会杀死终端本身?

我们打开它时终端正在运行。

luvpreet@DHARI-Inspiron-3542:/$ 

我刚打开它。 所以,当我按下Ctrl + C时 ,为什么不自杀并关闭终端?

Ctrl + C是中断信号。 当您在终端中键入此内容时,bash会将SIGINT发送到前台的作业。 如果没有工作(刚刚开通终端的情况),没有任何反应。 终端仿真器程序不是在shell中运行的作业,因此,它不会获得信号而不会关闭。

如果要使用控制键关闭终端,请使用Ctrl + D (EOF),这会导致bash退出(并关闭终端)。

另请参阅: 关于信号的Bash初学者指南以及更深入的信号处理方式
注意:自评论发布以来,此答案已经过编辑

与其他击键*一样, ^ C击键并不神奇 – 它会向任何具有焦点的程序发送键码。 (在X中, C的键码为54, Ctrl的修饰符为0x4。)接收键流的程序负责执行适当的操作 – 请记住,在许多GUI应用程序中,击键复制到剪贴板。

当GUI终端仿真器(例如,Konsole)或虚拟终端接收到它解释为^ C的击键时,它可以执行三件事之一。 如果终端处于原始模式 ,则运行程序已要求终端不对自身执行任何特殊键处理并将其直接传递给程序。 一些支持行编辑等高级function的程序在完全原始击键和处理过的文本行之间的某些配置中接收键盘输入; 例如, bash一次接收一个键击。 ^ C由终端解释,但退格键按原样发送到shell。

然而,大多数程序使用熟模式 (因为它不是原始模式),终端在实际将它们发送到程序之前解释一些基本的击键(这就是为什么你可以在cat使用退格键)。 在此模式下,终端自身将^ C键击转换为SIGINT信号并将其发送到子进程。 由于终端产生了信号,因此不会混淆并终止。

  • SysRq真的很神奇。

^ C通常映射(参见stty -a )到SIGINT信号(参见man 7 signal )。

未捕获的SIGINT中断正在运行的进程,但是……

SIGINT是进程可以为(“捕获信号”)指定行为的信号之一。

你所谓的“终端”捕获SIGINT ,然后重新开始工作。

当我是初学者时,我错过了当我使用命令行的时候我实际上使用了两个单独的程序,一个终端和一个shell(例如bash)

shell是你可能已经知道的,一个程序,它接受输入命令或脚本,执行它们并打印它们的输出。

另一侧的终端就像是用户和程序之间的中间人(该程序通常是像bash或fish一样的shell)。 终端所做的是例如从键盘读取输入,可能以某种方式处理该输入,并将其重定向到另一个程序(bash)。

此外,这也适用于其他方式,当其他程序输出某些内容时,某些内容被重定向到终端,然后终端的工作就是将某些内容输出到屏幕上。 在获取输入并将其打印到屏幕之间,终端可以以各种方式解释它所获得的输入。

例如,如果程序输出以下序列:

 \e[0;31m some extra foobar text 

终端将输出带有红色字母的“一些额外的foobar文本”屏幕。 这是因为终端选择以特殊方式处理该奇怪的代码,该代码提示它以红色打印以下输出。

类似地,当用户按下Ctrl - C ,关于此的唯一特殊之处在于终端选择以特殊方式对待它,该键序列没有任何其他特殊之处。 具体来说,这暗示它将中断信号(SIGINT)发送到终端内运行的进程,即shell。 如果此时存在任何由shell生成并且当前正在前台运行的程序,它也会收到信号。 现在shell有一个特殊的处理程序用于此信号,没有任何反应。 但大多数程序都有默认的处理程序,在SIGINT的情况下只是退出。

每个信号都有一个与之关联的默认操作。 信号的默认操作是脚本或程序在收到信号时执行的操作。

Ctrl + C发送“中断”信号( SIGINT ),该信号默认为将进程终止到前台运行的作业。

Ctrl + D告诉终端它应该在标准输入上注册EOF ,bash将其解释为退出的愿望。

进程可以选择忽略INT信号,Bash在交互模式下运行时会这样做。

从手册 :

当bash是交互式的时,在没有任何陷阱的情况下,它会忽略SIGTERM(因此kill 0不会杀死交互式shell),并且捕获并处理SIGINT(以便等待内置中断)。 在所有情况下,bash都会忽略SIGQUIT。 如果作业控制生效,bash将忽略SIGTTIN,SIGTTOU和SIGTSTP。


用陷阱来理解它:

trap是内置在shell中的函数,它响应硬件信号和其他事件。 它定义并激活在shell接收信号或其他特殊条件时运行的处理程序。

 trap [-lp] [arg] [sigspec …] 

-l打印信号名称列表及其对应的数字。
-p显示与每个SIGNAL_SPEC关联的陷阱命令。

当shell收到信号sigspec时,将读取并执行arg。 每个sigspec都是信号名称或信号编号。 信号名称不区分大小写,SIG前缀是可选的。

如果sigspec0EXIT ,则在shell退出时执行arg。 要理解它,关闭终端并在.bashrc文件中编辑以下行后打开它。

 trap 'notify-send "Ctrl D pressed"' 0 

Ctrl D类似于exit命令退出终端。

如果您希望Bash在收到INT信号时退出,即使在交互模式下,您也可以将以下内容添加到~/.bashrc

 trap 'exit' INT 

要么

 trap 'exit' 2