为什么Linux在按下Ctrl C时总是输出“^ C”?
发布时间:2020-12-13 18:47:32 所属栏目:Linux 来源:网络整理
导读:我一直在研究 Linux中的信号.我已经完成了一个捕获SIGINT的测试程序. #include unistd.h#include signal.h#include iostreamvoid signal_handler(int signal_no);int main() { signal(SIGINT,signal_handler); for (int i = 0; i 10; ++i) { std::cout "I'm
我一直在研究
Linux中的信号.我已经完成了一个捕获SIGINT的测试程序.
#include <unistd.h> #include <signal.h> #include <iostream> void signal_handler(int signal_no); int main() { signal(SIGINT,signal_handler); for (int i = 0; i < 10; ++i) { std::cout << "I'm sleeping..." << std::endl; unsigned int one_ms = 1000; usleep(200* one_ms); } return 0; } void signal_handler(int signal_no) { if (signal_no == SIGINT) std::cout << "Oops,you pressed Ctrl+C!n"; return; } 输出看起来像这样: I'm sleeping... I'm sleeping... ^COops,you pressed Ctrl+C! I'm sleeping... I'm sleeping... ^COops,you pressed Ctrl+C! I'm sleeping... ^COops,you pressed Ctrl+C! I'm sleeping... I'm sleeping... I'm sleeping... 据我所知,当按下Ctrl C时,前台进程组中的进程都会收到一个SIGINT(如果没有进程选择忽略它). 那么shell(bash)和上面程序的实例都收到了信号吗?每个“哎呀”之前的“^ C”来自哪里? 操作系统是CentOS,shell是bash. 解决方法
终端(驱动程序)拦截^ C并将其转换为发送到附加进程(即shell)的信号,stty intr ^ B将指示终端驱动程序拦截^ B.它也是将^ C回送到终端的终端驱动程序.
shell只是一个位于该行另一端的进程,并通过终端驱动程序(例如/ dev / ttyX)从终端接收它的stdin,并且它的stdout(和stderr)也附加到同一个tty . 注意(如果启用了回显),终端将击键发送到进程(组)并返回到终端. stty命令只是用于“控制”tty的进程的tty驱动程序的ioctl()的包装. 更新:为了证明shell没有参与,我创建了以下小程序.它应该由它的父shell通过exec ./a.out执行(看起来交互式shell会分叉一个子shell,无论如何)程序将生成SIGINTR的键设置为^ B,关闭echo,然后等待来自stdin的输入. #include <stdio.h> #include <string.h> #include <termios.h> #include <unistd.h> #include <signal.h> #include <errno.h> int thesignum = 0; void handler(int signum); void handler(int signum) { thesignum = signum;} #define THE_KEY 2 /* ^B */ int main(void) { int rc; struct termios mytermios; rc = tcgetattr(0,&mytermios); printf("tcgetattr=%dn",rc ); mytermios.c_cc[VINTR] = THE_KEY; /* set intr to ^B */ mytermios.c_lflag &= ~ECHO ; /* Dont echo */ rc = tcsetattr(0,TCSANOW,&mytermios); printf("tcsetattr(intr,%d) =%dn",THE_KEY,rc ); printf("Setting handler()n" ); signal(SIGINT,handler); printf("entering pause()n... type something followed by ^%cn",'@'+THE_KEY ); rc = pause(); printf("Rc=%d: %d(%s),signum=%dn",rc,errno,strerror(errno),thesignum ); // mytermios.c_cc[VINTR] = 3; /* reset intr to ^C */ mytermios.c_lflag |= ECHO ; /* Do echo */ rc = tcsetattr(0,rc ); return 0; } intr.sh: #!/bin/sh echo $$ exec ./a.out echo I am back. (编辑:李大同) 【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容! |