c语言 - SIGSEGV 处理程序无法退出



我注册了一个SIGSEGV处理程序,使用fprintf打印一些消息然后退出。该过程打印消息,但未退出。它在exit()之前阻止了.

我不能使用exit()在处理程序中正常完成该过程吗?

void sigsegv__handler(){
fprintf(stderr, "SIGSEGV , TID: %d,PID: %dn", TEST_ID, getpid());
exit(1);
}

我不能使用exit()在处理程序中正常完成该过程吗?

不应从信号处理程序调用exit()因为它不能保证异步信号安全。请改用_exit()_Exit()abort()

也就是说,不应从信号处理程序调用printf(),原因与适用于exit()的原因相同。

有关异步信号安全与否的完整功能列表,请浏览此页面:

  • Linux: http://man7.org/linux/man-pages/man7/signal.7.html
  • 波西克斯:http://pubs.opengroup.org/onlinepubs/9699919799/functions/V2_chap02.html#tag_15_04_03

而且,一旦发生分段违规,程序不稳定,甚至坏了,堆栈可能会被砸碎,所以不能保证从那一刻起可以调用任何东西。

在受控条件下,这可能是可能的,但一般来说,没有。exit函数尝试执行干净关闭,并要求进程处于正常状态。由于 SIGSEGV 已生成但未处理,因此代码可能不处于正常状态,因此不能保证干净关闭有效。在这些情况下使用_exit

您打电话给fprintf也是不明智的。使用write.

POSIX 需要异步信号安全的功能列表是:

下表定义了一组函数,这些函数应 异步信号安全。因此,应用程序可以调用它们,而无需 限制,来自信号捕获功能:

_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()

相关内容

  • 没有找到相关文章

最新更新