[英]Hardwarebreakpoint WINAPI
我目前正在为一个小调试框架实现最后一个任务,即硬件断点。 到目前为止,我参考了这篇文章: http : //www.codeproject.com/KB/debug/hardwarebreakpoint.aspx和一本关于编写调试器的书。
到目前为止,我获得了以下两个用于设置硬件断点的函数:
void debuglib::breakpoints::hw_bp() {
HANDLE helper = 0;
CONTEXT co;
CURRENTCONTEXT(co);
helper = ::CreateThread(0,0,threadfunc,reinterpret_cast<void*>(co.Eip),0,0);
DWORD status = ::WaitForSingleObject(helper,INFINITE);
if (status != WAIT_OBJECT_0) {
::MessageBoxA(0, "Helper thread didn't exit cleanly", "HWBreakpoint", MB_OK);
}
::CloseHandle(helper);
}
static DWORD WINAPI debuglib::breakpoints::threadfunc(void* param) {
DWORD suspendcnt = ::SuspendThread(debuglib::process::thread());
if(suspendcnt) {
return 0;
}
CONTEXT co;
::ZeroMemory(&co,sizeof(co));
co.ContextFlags = CONTEXT_DEBUG_REGISTERS;
BOOL ok = ::GetThreadContext(debuglib::process::thread(),&co);
if(!ok) {
return 0;
}
DWORD freeDr = 0;
DWORD condition = debuglib::breakpoints::TRIGGER::CODE;
DWORD length = debuglib::breakpoints::SIZE::SIZE_1;
co.Dr0 = reinterpret_cast<DWORD>(param);
co.Dr7 = co.Dr7 | 1 << (freeDr*2);
co.Dr7 = co.Dr7 | condition << ((freeDr*4)+16);
co.Dr7 = co.Dr7 | length << ((freeDr*4)+18);
co.ContextFlags = CONTEXT_DEBUG_REGISTERS;
ok = ::SetThreadContext(debuglib::process::thread(), &co);
co.ContextFlags = CONTEXT_DEBUG_REGISTERS;
::GetThreadContext(debuglib::process::thread(),&co);
suspendcnt = ::ResumeThread(debuglib::process::thread());
if(suspendcnt == 0xFFFFFFFF) {
return 0;
}
return 1;
}
所以首先我要创建一个帮助线程,因为我正在调试当前线程。 在辅助线程的回调函数中,我暂停了主线程。 之后我读取主线程的当前 DR 值(目前这不相关,因为我总是使用 DR0,在此工作后,我将检查哪些寄存器是空闲的并且最多使用 4 个 BP)。 之后,我使用调用函数(EIP)的返回地址作为中断 DR0 并在 DR7 中设置所属标志的地址。
最后,我将恢复主线程并关闭辅助线程的句柄,因为它已完成。
使用此代码,我遇到了以下问题:
如果我在调试模式下执行程序,程序会在正确的地址处停止,但我不能再做任何事情,因为我猜设置了 INT1 标志并且 VS 调试器不能进一步单步执行?
如果我在没有调试的情况下执行程序,它会简单地崩溃。 我尝试在提到的项目 (http://www.codeproject.com/KB/debug/hardwarebreakpoint.aspx) 中使用 __try, __except 但这也不起作用。
我很感激并提供帮助或信息我做错了什么以及如何解决这个问题。
我认为尝试让程序自行调试不是一个好主意。 为什么不使用 Windows 内置的调试器开发 API?
开发中心 - 桌面 > 学习 > 参考 > 诊断 > 调试和错误处理 > 基本调试 > 调试参考 > 调试功能: http : //msdn.microsoft.com/en-us/library/windows/desktop/ms679303%28v=vs .85%29.aspx
在 x86 硬件上,通过在 eflags 中设置陷阱标志来启用单步执行。 CPU 在完成一条指令后将引发调试异常(中断 1)。 我认为正在发生的是 Visual Studio 调试器正在改变标志的那一点,干扰你正在尝试做的事情。
尝试在 Visual Studio 之外运行您的程序(无调试器)。 那么它是否按预期工作?
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.