2010/5/3 cheng chen <freakrobot(a)acm.org>:
请教大家2个问题,谢谢:
1.函数指针,断错误无法解决
#include<stdio.h>
#define FUNC(x) ((void(*)()) *(x))
void aa(){ printf("aa\n");}
void bb(){ printf("bb\n");}
void cc(){ printf("cc\n"); }
void dd(){ printf("dd\n");}
void* operate[] = {aa,bb,cc,dd};
int main()
{
printf("%x\n",operate);
(*(void(*) () ) 0x80496d8)();
(*(void(**) () ) 0x80496d8)();
改成这样就好了,原因就是少了个 '*'
//这个"断错误"了
//我这里的0x80496d8就是前面打印出来的operate的地址,应该就是指向aa函数的指针的地址么
//我用的格式跟《C陷阱与缺陷》P15 的方式一样的(*(void (*) 0))(); 将入口地址强制转化为函数么
((void(*) () ) *operate)();
//这个正确的
//FUNC(operate+1)();
//这个跟上面那个一致的,也"断错误"了
return 0;
}
于是我把它编程汇编指令,太长了粘个主函数
main:
pushl %ebp
movl %esp, %ebp
andl $-16, %esp
subl $16, %esp
movl $.LC4, %eax
movl $operate, 4(%esp)
movl %eax, (%esp)
call printf
movl $134518488, %eax
;这个$134518488我看过了就是0x80496d8,那不是跟下面的operate应该是一样的么
call *%eax
movl operate, %eax
;这个operate应该也是$134518488,不是吗?
call *%eax
movl $0, %eax
leave
ret
.size main, .-main
2.另外一个问题,断错误的停机指令是何时生成的?
还是上面程序,我用objdump反汇编找0x80496d8这个地址
80496d8: f4 hlt
80496d9: 83 04 08 08 addl $0x8,(%eax,%ecx,1)
怎么这里就有hlt指令了,是gcc编译的时候就生成hlt指令了吗?而不是运行出了错误才要停机的?
段错误是机器产生了错误中断后发生 SIGSEG 信号,然后程序收到后默认信号处理程序就是停止进程。