我正在玩一个简单的程序(下面的源代码)。我的电脑配置:
Linux mymachine 3.13.0-49-generic#83-Ubuntu SMP Fri Apr 10 20:11:33 UTC 2015 x86_64 x86_64 x86_64 GNU / Linux
gcc版本4.8.4(Ubuntu 4.8.4-2ubuntu1~14.04.3)
#include <stdio.h>
#include <stdlib.h>
#include <signal.h>
#include <unistd.h>
void catcher(int a){
setresuid(geteuid(),geteuid(),geteuid());
printf("WIN!\n");
system("/bin/sh");
exit(0);
}
int main(int argc, char **argv){
puts("source code is available in level02.c\n");
if (argc != 3 || !atoi(argv[2]))
//printf("!atoi(argv[2]) = %d\n", !atoi(argv[2]));
return 1;
signal(SIGFPE, catcher);
printf("end\n");
return abs(atoi(argv[1])) / atoi(argv[2]);
}
我打算通过以这种方式调用可执行文件来触发此程序中的SIGFPE:
$./a.out -2147483648 -1
source code is available in level02.c
end
WIN!
如您所见,SIGFPE已成功触发。但是,如果我在参数中取消注释单个printf行,检查“if”条件:
#include <stdio.h>
#include <stdlib.h>
#include <signal.h>
#include <unistd.h>
void catcher(int a){
setresuid(geteuid(),geteuid(),geteuid());
printf("WIN!\n");
system("/bin/sh");
exit(0);
}
int main(int argc, char **argv){
puts("source code is available in level02.c\n");
if (argc != 3 || !atoi(argv[2]))
printf("!atoi(argv[2]) = %d\n", !atoi(argv[2]));
return 1;
signal(SIGFPE, catcher);
printf("end\n");
return abs(atoi(argv[1])) / atoi(argv[2]);
}
然后我重新编译程序并尝试使用相同的方式触发SIGFPE。我只能得到这个:
source code is available in level02.c
发生了什么事?
答案 0 :(得分:1)
因为现在你的源代码与实际解析它的方式相比是错误的。
if (argc != 3 || !atoi(argv[2]))
printf("!atoi(argv[2]) = %d\n", !atoi(argv[2]));
return 1;
考虑将两个语句放在一个块中,以避免这种情况。