对比程序名称:
#include <windows.h>
#include <iostream>
#include <TlHelp32.h>
BOOL CheckProcessName()
{
HANDLE hSnap = CreateToolhelp32Snapshot(TH32CS_SNAPPROCESS, 0);
PROCESSENTRY32 pe32 = { 0 };
pe32.dwSize = sizeof(PROCESSENTRY32);
while (Process32Next(hSnap, &pe32))
{
/*if (wcscmp(pe32.szExeFile,L"x32dbg.exe") == 0)
{
return TRUE;
}*/
if (wcsstr(pe32.szExeFile, L"dbg") != 0)
{
return TRUE;
}
}
return FALSE;
}
bool _stdcall ThreadCall()
{
while (true)
{
if (CheckProcessName())
{
printf("debug\n");
system("pause");
exit(0);
}
}
}
int main()
{
HANDLE ret = CreateThread(NULL, NULL, (LPTHREAD_START_ROUTINE)ThreadCall, NULL, 0, NULL);
system("pause");
TerminateThread(ret,0);
return 0;
}
查找顶层窗口名称:
BOOL CheckWindowsTitle()
{
HWND hWnd = FindWindow(NULL, L"x32dbg");
if (hWnd != NULL)
{
printf("debug\n");
system("pause");
exit(0);
}
}
遍历顶层窗口模糊对比:
#include <windows.h>
#include <iostream>
#include <TlHelp32.h>
#include <vector>
#include <processthreadsapi.h>
BOOL TraversalTopWnd(std::vector<HWND>& vec)
{
vec.clear();
HWND hWnd = GetTopWindow(0); //获取当前所有顶级窗口的同级顶部窗口
while (hWnd)
{
if (GetParent(hWnd) == 0)//判断这个窗口是不是有父窗口
{
vec.push_back(hWnd);//没有父窗口,就代表自己最吊,压入
}
hWnd = GetWindow(hWnd, GW_HWNDNEXT);//遍历同级窗口的下一个顶级窗口
}
return TRUE;//循环压入这些真顶级窗口
}
BOOL CheckWindows()
{
std::vector<HWND> vec;
TraversalTopWnd(vec);
WCHAR szWindowName[MAX_PATH] = { 0 };
for (HWND tmp : vec)//遍历 vec 向量中的每一个 HWND 元素,并将每个元素赋值给 tmp
{
GetWindowText(tmp, szWindowName, MAX_PATH);
if (wcsstr(szWindowName, L"dbg") != NULL)
{
return TRUE;
}
}
return FALSE;
}
bool _stdcall ThreadCall()
{
while (true)
{
if (CheckWindows())
{
printf("debug\n");
system("pause");
exit(0);
}
}
}
int main()
{
HANDLE ret = CreateThread(NULL, NULL, (LPTHREAD_START_ROUTINE)ThreadCall, NULL, 0, NULL);
system("pause");
TerminateThread(ret,0);
return 0;
}
INT 3 异常:
BOOL CheckException()
{
__try
{
_asm int 3;
}
__except (EXCEPTION_EXECUTE_HANDLER)
{
return FALSE;
}
return TRUE;
}
就后面的几个异常而言:程序不挂调试器,是不会产生异常的,只是无效操作(你的代码产生的错误,不够发生异常,并不是不挂就永远不会异常)。挂了调试器就会抛出异常(内核抛)调试器和操作系统内核的协作,是挂调试器时看到异常行为的根本原因,调试器接受异常,由于调试器只能处理断点异常,所以调试器有会把异常还给程序的异常处理模块,所以执行了return TRUE;
如果不挂调试器,程序要执行__except块,必须在抛一个异常(throw)或者代码错误足够产生异常才会进入,不然永远不会进去__except块
互斥体异常:
BOOL CheckSetHandleInformation()
{
HANDLE hMutex = CreateMutex(NULL, FALSE, L"123");
if (hMutex != INVALID_HANDLE_VALUE)
{
//设置互斥体对象不能被关闭
SetHandleInformation(hMutex, HANDLE_FLAG_PROTECT_FROM_CLOSE, HANDLE_FLAG_PROTECT_FROM_CLOSE);
__try
{
CloseHandle(hMutex);
}
__except (EXCEPTION_EXECUTE_HANDLER)
{
return TRUE;
}
}
return FALSE;
}
NTClose异常:
BOOL CheckNtClose()
{
typedef NTSTATUS(WINAPI* FnNtClose)(
HANDLE Handle
);
FnNtClose func = (FnNtClose)GetProcAddress(GetModuleHandleA("ntdll.dll"), "NtClose");
__try
{
func((HANDLE)(0x99999999));
}
__except (EXCEPTION_EXECUTE_HANDLER)
{
return TRUE;
}
return FALSE;
}
复制句柄异常:
BOOL CheckDuplicateHandle()
{
__try
{
HANDLE hTarget, hTarget2;
//复制一个本地句柄
DuplicateHandle((HANDLE)-1, (HANDLE)-1, (HANDLE)-1, &hTarget, NULL, FALSE, DUPLICATE_SAME_ACCESS);
//设置这个句柄不能关闭
SetHandleInformation(hTarget, HANDLE_FLAG_PROTECT_FROM_CLOSE, HANDLE_FLAG_PROTECT_FROM_CLOSE);
//又复制一个句柄并关闭源句柄,产生异常
DuplicateHandle((HANDLE)-1, (HANDLE)hTarget, (HANDLE)-1, &hTarget2, NULL, FALSE, DUPLICATE_CLOSE_SOURCE);
return false;
}
__except (EXCEPTION_EXECUTE_HANDLER)
{
return TRUE;
}
}
判断父进程:
DWORD GetParentProcessID(DWORD dwProcessId)
{
HANDLE hSnap = CreateToolhelp32Snapshot(TH32CS_SNAPPROCESS, 0);
PROCESSENTRY32 pe32 = { 0 };
pe32.dwSize = sizeof(PROCESSENTRY32);
while (Process32Next(hSnap, &pe32))
{
if (dwProcessId == pe32.th32ProcessID)
{
return pe32.th32ParentProcessID;
}
}
}
DWORD GetProcessIdForProcessName(const WCHAR * szProcessName)
{
HANDLE hSnap = CreateToolhelp32Snapshot(TH32CS_SNAPPROCESS, 0);
PROCESSENTRY32 pe32 = { 0 };
pe32.dwSize = sizeof(PROCESSENTRY32);
while (Process32Next(hSnap, &pe32))
{
if (wcscmp(szProcessName, pe32.szExeFile) == 0)
{
return pe32.th32ProcessID;
}
}
}
BOOL CheckParentProcess()
{
DWORD dwProcessId = GetCurrentProcessId();
DWORD dwParentProcessId = GetParentProcessID(dwProcessId);
DWORD dwExplorerId = GetProcessIdForProcessName(L"explorer.exe");
if (dwParentProcessId != dwExplorerId)
{
return TRUE;
}
return FALSE;
}
硬件断点:
BOOL CheckDRRegister()
{
HANDLE hSnap = CreateToolhelp32Snapshot(TH32CS_SNAPTHREAD, 0);
THREADENTRY32 th32 = { 0 };
th32.dwSize = sizeof(THREADENTRY32);
while (Thread32Next(hSnap, &th32))
{
if (th32.th32OwnerProcessID == GetCurrentProcessId())
{
HANDLE hThread = OpenThread(THREAD_ALL_ACCESS, FALSE, th32.th32ThreadID);
CONTEXT ctx;
ctx.ContextFlags = CONTEXT_ALL;
GetThreadContext(hThread, &ctx);
if (ctx.Dr0 != 0 || ctx.Dr1 != 0 || ctx.Dr2 != 0 || ctx.Dr3 != 0)
{
return TRUE;
}
}
}
return FALSE;
}