预期 LdrDoDebuggerBreak(),得到 NtWaitForWorkViaWorkerFactory()

Expected LdrDoDebuggerBreak(), got NtWaitForWorkViaWorkerFactory()

在调试研讨会期间,其中一位参与者无法遵循示例。

当 运行在他的 Windows 10 机器上在 WinDbg 10.0.15603.137 下运行可执行文件时,调试器第一次中断 NtWaitForWorkViaWorkerFactory() 而不是 [= 中的初始断点12=].

当尝试 运行 带有 g 的可执行文件时,它说 运行 没有调试对象。可能是什么问题?

这是它的样子:

应用程序的源代码很简单:

#include "stdafx.h"
#include <exception>

int _tmain(int /*argc*/, _TCHAR* /*argv*/[])
{
    throw std::exception();
}

注意:我几乎无法提供更多信息,因为我无法再访问客户的 PC,而且我的电脑也不会发生这种情况。

不可能确定问题出在哪里,但我们可以说出问题 可能 是什么。幸好你问的是这个。

我无法为此分配确切的概率,但很可能是隐式链接的 DLL 加载失败。这是在初始断点1.

之前发生的主要事情

为什么DLL加载失败?也许是某种资源问题,但是 - 特别是假设您在重启后尝试了 运行 一台 "fresh" 机器 - 更有可能是在有问题的机器上加载了一个额外的 DLL。也许是一个 AVRF DLL,也许是一个 AppInit DLL,也许是将 DLL 注入不知情和不情愿的进程的一百种其他方法之一2.

正如我在评论中所说,确定答案的方法是让 WinDBG 在进程创建时中断,而不是在初始断点处中断,然后从那里开始调试。

方法是用 -xe cpr 启动 NTSD/CDB,在 WinDBG 的 Event Filters window 中设置(可通过Debug 菜单),或在 WinDBG 中使用 sxe cpr.restart,假设您在 WinDBG 中启动进程(而不是附加到它),这是最好的方法在我看来最好,但这只是个人喜好问题。


1 我认为主要模块的 TLS 回调也在初始断点之前执行,但是有人弄乱项目配置或 CRT LIB 以添加有问题的 TLS 回调? (隐式链接 DLL 的 TLS 回调包含在 "DLL loading" 中。)

2 但是同样,更邪恶和更聪明的技巧不太常见,因此不太可能。