一.使用异步安全函数在信号处理函数中。
错误代码:
-
#include <signal.h>
-
char *foo;
-
void int_handler() {
-
free(foo);
-
_Exit(0);
-
}
-
int main(void) {
-
foo = malloc(sizeof("Hello World."));
-
if (foo == NULL) {
-
/* handle error condition */
-
}
-
signal(SIGINT, int_handler);
-
strcpy(foo, "Hello World.");
-
puts(foo);
-
free(foo);
-
return 0;
-
}
因为free不是异步安全函数,main函数执行free后,接收到信号并执行int_handler信号处理函数执行free操作,会导致double free的错误。
信号处理程序应尽可能简洁,理想情况下只设置flag并返回。
正确代码:
-
#include <signal.h>
-
char *foo;
-
void int_handler() {
-
_Exit(0);
-
}
-
int main(void) {
-
foo = malloc(sizeof("Hello World."));
-
if (foo == NULL) {
-
/* handle error condition */
-
}
-
signal(SIGINT, int_handler);
-
strcpy(foo, "Hello World.");
-
puts(foo);
-
free(foo);
-
return 0;
-
}
二. sig_atomic_t
在处理信号(signal)的时候,有时对于一些变量的访问希望不会被中断,无论是硬件中断还是软件中断,这就要求访问或改变这些变量需要在计算机的一条指令内完成。通常情况下,int类型的变量通常是原子访问的,也可以认为 sig_atomic_t就是int类型的数据,因为对这些变量要求一条指令完成,所以sig_atomic_t不可能是结构体,只会是数字类型。
在linux里这样定义:
typedef int __sig_atomic_t;
为了安全起见,无条件的信号处理程序应该使用sig_atomic_t类型。
阅读(720) | 评论(0) | 转发(0) |