• 1274阅读
  • 3回复

调试器攻击技术 - Unhandled Exception Filter [复制链接]

上一主题 下一主题
离线天道酬勤
 

只看楼主 倒序阅读 使用道具 楼主  发表于: 2016-02-05
— 本帖被 天道酬勤 从 驱动保护 移动到本区(2016-05-19) —


5、 Unhandled Exception Filter



MSDN文档声明当一个异常到达Unhandled Exception Filter(kernel32!UnhandledExceptionFilter)并且程序没有被调试时,Unhandled Exception Filter将会调用在kernel32!SetUnhandledExceptionFilter()API作为参数指定的高层exception Filter。壳利用了这一点,通过设置exception Filter然后抛出异常,如果程序被调试那么这个异常将会被调试器接收,否则,控制被移交到exception Filter运行得以继续。
示例
下面的示例中通过SetUnhandledExceptionFilter()设置了一个高层的exception Filter,然后抛出一个违规访问异常。如果进程被调试,调试器将收到两次异常通知,否则exception Filter将修改CONTEXT.EIP并继续执行。
;set the exception filter
push                .exception_filter
call                  [SetUnhandledExceptionFilter]
mov                 [.original_filter],eax

;throw an exception
xor                  eax,eax
mov                 dword [eax],0

;restore exception filter
push                dword [.original_filter]
call                  [SetUnhandledExceptionFilter]

:::

.exception_filter:
;EAX = ExceptionInfo.ContextRecord
mov              eax,[esp+4]
mov              eax,[eax+4]

;set return EIP upon return
add                dword [eax+0xb8],6

;return EXCEPTION_CONTINUE_EXECUTION
mov              eax,0xffffffff
retn
有些壳并不调用SetUnhandledExceptionFilter()而是直接通过kernel32!_BasepCurrentTopLevelFilter手工设置exception Filter,以防逆向分析人员在那个API上下断。
对策有意思的是kernel32!UnhandledExceptionFilter()内部实现代码是使用ntdll!NtQueryInformationProcess(ProcessDebugPort)来确定进程是否被调试,从而决定是否调用已注册的exception Filter。因此,处理方法和DebugPort调试器检测技术相同。

离线gmhzxy

只看该作者 沙发  发表于: 2016-02-05
SEH 的 KiDisPatchException函数 是先让内核调试器接管,其次是应用层调试器,最后是程序自己处理的异常,所以说如果是有调试器的话,从正常代码到进入异常的时间不会少于10毫秒,超过10毫秒就可以认为是被调试了
离线im86165507

只看该作者 板凳  发表于: 2016-02-07
离线v2680267313

只看该作者 地板  发表于: 2016-04-30
用户被禁言,该主题自动屏蔽!
快速回复
限100 字节
如果您提交过一次失败了,可以用”恢复数据”来恢复帖子内容
 
上一个 下一个