首页
论坛
专栏
课程

[原创]MoonU安全学习笔记之顶层异常处理函数

MoonU 2018-11-5 14:37 1186

一、笔记说

        前两天在逆向一个小程序时看到一个顶层异常处理函数的用法很有意思,涉及的知识点也很多,对于逆向入门的人来说还是有很多启发的。我之前在学习异常与调试时也没有学习顶层异常处理函数的相关内容,所以想借助这个CM小程序加深对顶层异常处理函数的理解和使用。

        我们知道当一个异常发生时,操作系统将向发生异常的线程的栈中压入三个结构体:EXCEPTION_RECORD、CONTEXT、EXCEPTION_POINTERS, EXCEPTION_RECORD结构包含了关于抛出异常的信息,CONTEXT保存了寄存器上下文, EXCEPTION_POINTERS结构包含两个数据成员,他们分别为压入栈中的 EXCEPTION_RECORD结构指针和CONTEXT结构指针。

        其次,如果异常过滤程序返回EXCEPTION_CONTINUE_SEARCH时,系统会继续在调用树中的上层寻找异常处理程序,如果进程未注册VEH、SEH、VCH、UEF等异常处理程序,又会发生生么呢?在这种情况下,我们会遇到所谓的异常未处理函数SetUnhandledExceptionFilter,这个函数也给了我们最后处理异常的机会。   

二、平台环境

1. 系统:Window10

2. 分析工具:IDA(32位)

3. 程序:CrackMe.exe

三、实例笔记

   (一)本次逆向目标:如右图所示,此程序为MFC窗口程序,要我们分析反汇编代码找到密码字符串,点击check按钮,验证输入的字符是否正确。


(二)分析思路:

  2.2.1动态分析:

  在OD中打开CM.exe,运行起来随便输入字串,点击check,看看能找到什么。

很遗憾,一无所获,还触发了异常,不明所以。

如下图所示:

点击关闭程序,OD会停留在中断发生的位置,如下图所示:


那为什么会断在这?有经验的人会知道这是触发了访问异常,对于我们初学者来说不知道发生了什么那我们就用IDA来详细分析下它的反汇编代码,看看发生了什么?

2.2.2静态分析:

1).在IDA中打开程序后如下图所示,你会发现代码段内容很少,点击DialogFunc进入窗口回调函数。

  

2).添加vc32rtf签名。

3).修改变量名称、消息类型名称。

方法:选中变量值单击右键选择-》Use standard symbolic constant(快捷键M)打开符号列表


修改后如下图所示,可以看出在调用GetDlgItemTextA函数之后,触发了访问异常,双击401113这个地址,会发现这个地址在代码段。

4).所以得出一个结论:无论输入什么字符串都会触发异常,并调用异常处理函数:

异常处理函数调用顺序:

-》是否有内核调试器-》是否有用户调试器-》是否注册异常处理函数。

-》如果VEH、SEH、VCH、UEF都没有注册,则检查顶层异常处理函数;

5).跟踪代码发现在初始化对话框消息中注册了顶层异常处理函数,如下图所示:

6) .双击TopLevelExceptionFilter进入顶层异常处理定义函数,如下图所示。这部分数据是定义在.data段,并未识别为代码,需要我们手动将其转换为代码,并封装为函数(先按C、再按P)。

 

7) .解析顶层异常调用函数:

->>先熟悉以下异常结构体字段。

->>分析顶层异常函数代码实现,如下图示:

->>对于修改CONTEXT字段中,寄存器偏移量可采用以下办法得出:用寄存器字段地址 - 结构体地址。

->>在看懂了以上代码以后,你会发现,异常处理函数是修改CONTEXT结构体中的EDI、ESI、EIP字段,并恢复EXCEPTION_CONTINUE_EXECUTION,继续执行。

 

至此,我们找到了密码字串,也明白了利用异常处理函数修改线程上下文原理。

四、学习总结

这个小程序其实代码量非常小,但挖了很多坑,如果对基础知识掌握不好的话,还是不容易分析的。主要涉及的知识点有:1、了解异常处理机制;2、了解顶层异常处理函数;3、恢复数据段中的代码;4、异常结构体;5、准确分析汇编代码意义。异常处理机制对提高程序的稳定性和对抗反调试手段都很有帮助,更多异常相关知识请参阅《Windows核心编程》《加密解密》。以下附录SetUnhandledExceptionFilter函数注解。


附录:

SetUnhandledExceptionFilter()注解:

Enables an application to supersede the top-level exception handler of each thread of a process.允许应用程序继承进程中每一个线程的顶层异常处理程序。

After calling this function, if an exception occurs in a process that is not being debugged, and the exception makes it to the unhandled exception filter, that filter will call the exception filter function specified by thelpTopLevelExceptionFilter parameter.调用这个函数之后,如果一个异常发生在为被调试的进程中,那么这个异常会引起异常处理程序的调用,也就是说过滤器会调用thelpTopLevelExceptionFilter参数指定的异常处理程序。

Syntax

C++

LPTOP_LEVEL_EXCEPTION_FILTER WINAPI SetUnhandledExceptionFilter(

  _In_  LPTOP_LEVEL_EXCEPTION_FILTER lpTopLevelExceptionFilter

);

Parameters

lpTopLevelExceptionFilter [in]

A pointer to a top-level exception filter function that will be called whenever theUnhandledExceptionFilter function gets control, and the process is not being debugged.指向顶层异常过滤处理函数的指针, A value ofNULL for this parameter specifies default handling withinUnhandledExceptionFilter.

The filter function has syntax similar to that of UnhandledExceptionFilter: It takes a single parameter of typeLPEXCEPTION_POINTERS, has a WINAPI calling convention, and returns a value of typeLONG. The filter function should return one of the following values.

Value

Meaning

EXCEPTION_EXECUTE_HANDLER

0x1

Return from UnhandledExceptionFilter and execute the associated exception handler. This usually results in process termination.

EXCEPTION_CONTINUE_EXECUTION

0xffffffff

Return from UnhandledExceptionFilter and continue execution from the point of the exception. Note that the filter function is free to modify the continuation state by modifying the exception information supplied through itsLPEXCEPTION_POINTERS parameter.

EXCEPTION_CONTINUE_SEARCH

0x0

Proceed with normal execution of UnhandledExceptionFilter. That means obeying the SetErrorMode flags, or invoking the Application Error pop-up message box.

 

Return value

The SetUnhandledExceptionFilter function returns the address of the previous exception filter established with the function. ANULL return value means that there is no current top-level exception handler.

Remarks

Issuing SetUnhandledExceptionFilter replaces the existing top-level exception filter for all existing and all future threads in the calling process.

The exception handler specified by lpTopLevelExceptionFilter is executed in the context of the thread that caused the fault. This can affect the exception handler's ability to recover from certain exceptions, such as an invalid stack.

 



[防守篇]2018看雪.TSRC CTF 挑战赛(团队赛)11月1日征题开启!

最后于 2018-11-5 18:03 被MoonU编辑 ,原因: 图片显示异常
上传的附件:
最新回复 (1)
KevinsBobo 2 2018-11-5 19:00
2

0

感谢分享!
返回