我注册了SIGSEGV
的处理程序,使用fprintf
打印一些消息然后退出。该过程打印消息但未退出。它在exit()
之前被阻止。
我不能使用exit()
在处理程序中正常完成该过程吗?
void sigsegv__handler(){
fprintf(stderr, "SIGSEGV , TID: %d,PID: %d\n", TEST_ID, getpid());
exit(1);
}
答案 0 :(得分:5)
不应该从信号处理程序调用我不能使用
exit()
正常完成处理程序中的过程吗?
exit()
,因为它不能保证异步信号安全。请改用_exit()
,_Exit()
或abort()
。
那就是说,printf()
不应该从信号处理程序中调用,原因与适用于exit()
的原因相同。
有关async-signal-safe与否的完整功能列表,请查看此页面:
此外,当分段违规发生时,程序不稳定,甚至破坏,堆栈可能会被粉碎,因此无法保证从那一刻开始可以调用任何东西。
答案 1 :(得分:2)
在受控条件下,这可能是可能的,但总的来说,没有。 exit
函数尝试执行干净关闭,并要求进程处于正常状态。由于生成了SIGSEGV但未处理,因此代码可能不处于正常状态,因此无法保证干净关闭。在这些情况下使用_exit
。
您的fprintf
电话也不明智。使用write
。
答案 2 :(得分:0)
The list of functions POSIX requires是异步信号安全的:
下表定义了一组应该是的函数 异步信号安全。因此,应用程序可以调用它们,而不需要 限制,来自信号捕捉功能:
_Exit() _exit() abort() accept() access() aio_error() aio_return() aio_suspend() alarm() bind() cfgetispeed() cfgetospeed() cfsetispeed() cfsetospeed() chdir() chmod() chown() clock_gettime() close() connect() creat() dup() dup2() execl() execle() execv() execve() faccessat() fchdir() fchmod() fchmodat() fchown() fchownat() fcntl() fdatasync() fexecve() fork() fstat() fstatat() fsync() ftruncate() futimens() getegid() geteuid() getgid() getgroups() getpeername() getpgrp() getpid() getppid() getsockname() getsockopt() getuid() kill() link() linkat() listen() lseek() lstat() mkdir() mkdirat() mkfifo() mkfifoat() mknod() mknodat() open() openat() pause() pipe() poll() posix_trace_event() pselect() pthread_kill() pthread_self() pthread_sigmask() raise() read() readlink() readlinkat() recv() recvfrom() recvmsg() rename() renameat() rmdir() select() sem_post() send() sendmsg() sendto() setgid() setpgid() setsid() setsockopt() setuid() shutdown() sigaction() sigaddset() sigdelset() sigemptyset() sigfillset() sigismember() signal() sigpause() sigpending() sigprocmask() sigqueue() sigset() sigsuspend() sleep() sockatmark() socket() socketpair() stat() symlink() symlinkat() tcdrain() tcflow() tcflush() tcgetattr() tcgetpgrp() tcsendbreak() tcsetattr() tcsetpgrp() time() timer_getoverrun() timer_gettime() timer_settime() times() umask() uname() unlink() unlinkat() utime() utimensat() utimes() wait() waitpid() write()