WEB开发网
开发学院网络安全黑客技术 Structured Exception Handling 阅读

Structured Exception Handling

 2007-01-14 20:14:46 来源:WEB开发网   
核心提示: 简单总结一下,当发生异常时会调用一个回调函数,Structured Exception Handling(3),这个回调函数需要四个参数,其中三个都是结构体指针,从而得到一个指向_except_handler回调函数的指针,现在操作系统已经有足够的信息来调用_except_handler函

简单总结一下,当发生异常时会调用一个回调函数。这个回调函数需要四个参数,其中三个都是结构体指针。在这些结构体中,有些域重要,有些并不重要。关键的问题是_except_handler回调函数收到了大量的信息,比如异常的类型和发生的位置。异常回调函数需要使用这些信息来决定所采取的行动。

我很想现在就给出一个样例程序来说明_except_handler,只是仍有一些东西需要解释,即当异常发生时操作系统是如何知道在那里调用回调函数呢?答案在另一个叫EXCEPTION_REGISTRATION的结构体中。本文通篇都能见到这个结构体,因此对这部分还是不要囫囵吞枣为好。唯一能找到 EXCEPTION_REGISTRATION正式定义的地方就是VisualC++运行时库源代码中的EXSUP.INC文件:

_EXCEPTION_REGISTRATIONstruc
  prev  dd   ?
  handlerdd   ?
_EXCEPTION_REGISTRATIONends

可以看到,在WINNT.H的NT_TIB结构体定义中,这个结构体被称为_EXCEPTION_REGISTRATION_RECORD。然而_EXCEPTION_REGISTRATION_RECORD的定义是没有的,因此我所能用的只能是EXSUP.INC中的汇编语言的struc定义。对于我前面提到的SEH的未公开,这就是一例。

不管怎样,我们回到目前的问题上来。当异常发生时,OS是如何知道调用位置的呢?EXCEPTION_REGISTRATION结构体有两个域,第一个先不用管。第二个域,handler,为一个指向_except_handler回调函数的指针。有点儿接近答案了,但是还有个问题就是,OS从哪里能找到这个EXCEPTION_REGISTRATION结构体呢?

为了回答这个问题,需要记住结构化异常处理是以线程为基础的。也就是说,每一个线程都有自己的异常处理回调函数。在1996年5月的专栏中,我讲了一个关键的Win32数据结构,线程信息块(TEB或TIB)。这个结构体中有一个域对于WindowsNT,Windows95,Win32s和OS/2都是相同的。TIB中的第一个DWORD是一个指向线程的EXCEPTION_REGISTRATION结构体的指针。在Intel的Win32平台上,FS寄存器永远指向当前的TIB,因此,在FS:[0]就可以找到指向EXCEPTION_REGISTRATION结构体的指针。答案出来了!当异常发生时,系统察看出错线程的TIB并取回一个指向EXCEPTION_REGISTRATION结构体的指针,从而得到一个指向_except_handler回调函数的指针。现在操作系统已经有足够的信息来调用_except_handler函数了,见Figure2。

上一页  1 2 3 4 5 6 7 8  下一页

Tags:Structured Exception Handling

编辑录入:爽爽 [复制链接] [打 印]
赞助商链接