WinDbg 无法加载扩展

WinDbg can't load extension

我在 WinDbg 预览中加载扩展时遇到一些问题。可以找到扩展代码 here.

目前,当我 运行 .extpath 我得到默认路径并且扩展名保存在 C:\Users\user\AppData\Local\Dbg\EngineExtensions32 但是每当我执行 .chain 时,dll 是扩展名永远不会加载并尝试手动加载扩展会导致错误 The engine has been disconnected unexpectedly.

如何正确加载此扩展程序?

作为许多应用程序的旁注,当我使用 WinDbg 附加到它们并尝试加载 sos.dll 时,我只得到以下输出,而我在网上找不到任何东西,例如 this or 能够纠正这个问题:
.cordll -u -ve -l CLRDLL: No CLR image loaded (i.e. mscorwks.dll) CLR DLL status: No load attempts

如何让 CLR SOS dll 在每次 WinDbg 启动时自动加载?

您正在就 2 个问题寻求帮助,因此这里有两个答案。在这个网站上,我们更喜欢一次一个问题。

如何正确加载此扩展程序?

link you provided中有一个注释:

Though I believe I resolved the issue, it may be necessary that you copy the extension to the very same folder where WinDBG is located.

我可以重现你的问题,当我将所有编译工件复制到 WinDbg 目录时,它确实得到了解决。

我已经 opened an issue on the Github repository 了。

如何让 CLR SOS dll 在每次 WinDbg 启动时自动加载?

加载 SOS 并非易事,原因如下:

  • WinDbg 启动时无法加载 SOS。它还需要一个调试会话,因此它要么需要附加到 运行ning 程序,要么需要打开故障转储,要么需要启动一个新进程。这意味着,您需要 -z 加载故障转储,-p 附加 py PID,-pn 通过进程名称附加或给出可执行文件的名称。
  • 无法在初始断点处加载 SOS,因为 .NET 尚不可用,尚不清楚加载哪个版本的 SOS。
  • 您需要 运行 WinDbg 的正确位数才能加载 SOS,否则它将因位数不匹配而失败(类似于 .NET 中的 BadImageFormatException)。
  • 根据 .NET 版本,我们需要在 clrcoreclrmscorwks 所在的位置加载 SOS。更糟糕的是,在某些情况下,甚至没有正确命名 .NET DLL(例如 mscorwks_64800000
  • 使用引号时,我们可能需要正确转义这些引号

有了这些知识,您现在可以构建一个小脚本并使用 -c 参数将其传递给 WinDbg。但是让我们首先确定需要做什么。

首先,我们可以简单地尝试所有.NET 版本。如果加载 .NET,其中两个将失败,其中一个可能会成功。三个命令是

.loadby sos clr
.loadby sos coreclr
.loadby sos mscorwks

现在,我们需要在加载 .NET 时执行此操作。对于崩溃转储或已经有 .NET 的进程来说很好 [=7​​3=]ning。这不适用于从头开始的进程。

所以,对于简单的情况,我们有一个像

这样的命令行
windbg.exe -c ".loadby sos clr;.loadby sos coreclr;.loadby sos mscorwks" -z crash.dmp
windbg.exe -c ".loadby sos clr;.loadby sos coreclr;.loadby sos mscorwks" -p PID
windbg.exe -c ".loadby sos clr;.loadby sos coreclr;.loadby sos mscorwks" -pn name

启动新进程的事情变得更加复杂。通常你可以这样做

sxe -c".loadby sos clr;g" ld clr

在加载 CLR DLL 时尽早加载 SOS。不幸的是,您一次只能有一个 ld 断点,并且您只能指定一个模块。但是,我们可以通过设置三个未解析的断点来解决这个问题:

bu clr!EEStartup ".loadby sos clr;g"
bu mscorwks!EEStartup ".loadby sos mscorwks;g"
bu coreclr!EEStartup ".loadby sos coreclr;g"

请注意,我们 运行 陷入丑陋的引号转义问题。这些无法使用双引号 ("")、脱字符引号 (^") 或我们从命令行知道的其他内容来解决。这就是我们需要编写脚本的原因。然后命令行是

windbg -c "$$<loadsos.dbg;g" notepad.exe

其中 $$< 是 运行 具有给定名称的脚本的命令。然后该文件包含所需的命令

.loadby sos clr
.loadby sos coreclr
.loadby sos mscorwks
bu clr!EEStartup ".loadby sos clr;g"
bu mscorwks!EEStartup ".loadby sos mscorwks;g"
bu coreclr!EEStartup ".loadby sos coreclr;g"