本文主要是介绍反调试 - int 2dh , int 3h,希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!
原理
第 0x2d(45) 号中断处理函数是 KiDebugService,执行Int 2dh指令时,进程如果没有处于被调试状态,将会抛出异常,如果在被调试状态则能够正常执行。我们可以利用这一点检测调试器的存在。
如果有调试器,调试器就会接管这个 int 2dh 产生的异常从而不走我们设置的异常回调处理函数,当然如果调试器选择不接管这个异常我们是无法检测出调试器的,所以这是一种比较低级的反调试手段。
代码
int2d_x64.asm:
- 首先创建一个.cpp 文件,改下后缀为 .asm
- 找到这个asm 文件右键 - 属性,设置成如下:
命令行:ml64 /Fo $(IntDir)%(fileName).obj /c %(fileName).asm
输出:$(IntDir)%(fileName).obj
- 最后填入代码:
.code __int2d procint 2dhnopret
__int2d endpend
Test.cpp:
// Test_Console_1.cpp : 此文件包含 "main" 函数。程序执行将在此处开始并结束。
//#include <iostream>
#include <Windows.h>using namespace std;extern "C" void __int2d();BOOL isDebugger = TRUE;// 我们的异常接管函数
static LONG CALLBACK VectoredHandler(_In_ PEXCEPTION_POINTERS ExceptionInfo){isDebugger = FALSE;// 如果引发异常的是一个断点if (ExceptionInfo->ExceptionRecord->ExceptionCode == EXCEPTION_BREAKPOINT){// 忽略该异常,继续执行return EXCEPTION_CONTINUE_EXECUTION;}// 继续向上一层 seh 查找异常处理方法return EXCEPTION_CONTINUE_SEARCH;
}int main()
{// 注册 veh,1代表第一个被调用(非零都是第一个被调用)PVOID Handle = AddVectoredExceptionHandler(1, VectoredHandler);// 使用 int 2dh 触发异常__int2d();// 删除 vehRemoveVectoredExceptionHandler(Handle);// 判断调试器if (isDebugger == TRUE) {cout << "发现调试器" << endl;}else {cout << "没有调试器" << endl;}main_end:getchar();return 0;
}
效果图
vs 调试:
正常启动:
同理 int3 反调试代码:
// Test_Console_1.cpp : 此文件包含 "main" 函数。程序执行将在此处开始并结束。
//#include <iostream>
#include <Windows.h>using namespace std;BOOL isDebugger = TRUE;// 我们的异常回调处理函数
LONG CALLBACK VectoredHandler(_In_ PEXCEPTION_POINTERS ExceptionInfo) {isDebugger = FALSE;// 如果这个异常属于断点异常if (ExceptionInfo->ExceptionRecord->ExceptionCode == EXCEPTION_BREAKPOINT) {// 因为 int3 属于陷阱异常,中断完成后要回到产生异常的下一条指令(否则会一直产生 int3 陷入死循环)
#ifdef _WIN64ExceptionInfo->ContextRecord->Rip++;
#elseExceptionInfo->ContextRecord->Eip++;
#endif// 忽略异常继续执行return EXCEPTION_CONTINUE_EXECUTION;}// 继续向上一层 seh 查找异常处理方式return EXCEPTION_CONTINUE_SEARCH;
}int main()
{// 注册 vehPVOID Handle = AddVectoredExceptionHandler(1, VectoredHandler);// 手动触发异常__debugbreak();// 删除 vehRemoveVectoredExceptionHandler(Handle);// 判断调试器if (isDebugger == TRUE) {cout << "发现调试器!" << endl;}else {cout << "没有调试器" << endl;}getchar();return 0;
}
这篇关于反调试 - int 2dh , int 3h的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!