尽管加载私有 pdb 文件,WinDBG 不显示源代码行

发布于 2024-11-08 23:22:55 字数 4399 浏览 3 评论 0原文

我正在尝试使用 WinDBG 调试本机 DLL 中的问题。我相信我已加载私有符号,但 WinDBG 未显示源代码行或参数信息。这是我所观察到的;任何帮助将不胜感激!

我有 PDB,我相信它对应于符号搜索路径中的 DLL。运行 lm 我看到:

01050000 01058000   3NMSMTHR C (private pdb symbols)  e:\ads_symbols\3NMSMTHR.pdb

由于这表明“私有 pdb 符号”,我希望这是私有 pdb。

我还运行 symchk 并看到以下输出:

C:\utils\inetmgr\patch01>"c:\Program Files\Debugging Tools for Windows (x86)\symchk.exe" /v 3nmsmthr.dll /s c:\utils\inetmgr\patch01
[SYMCHK] Searching for symbols to C:\utils\inetmgr\patch01\3nmsmthr.dll in path c:\utils\inetmgr\patch01
DBGHELP: Symbol Search Path: c:\utils\inetmgr\patch01
[SYMCHK] Using search path "c:\utils\inetmgr\patch01"
DBGHELP: No header for C:\utils\inetmgr\patch01\3NMSMTHR.DLL.  Searching for image on disk
DBGHELP: C:\utils\inetmgr\patch01\3NMSMTHR.DLL - OK
DBGHELP: 3NMSMTHR - private symbols & lines
     c:\utils\inetmgr\patch01\3NMSMTHR.pdb
[SYMCHK] MODULE64 Info ----------------------
[SYMCHK] Struct size: 1680 bytes
[SYMCHK] Base: 0x10000000
[SYMCHK] Image size: 32768 bytes
[SYMCHK] Date: 0x4cc1b0f8
[SYMCHK] Checksum: 0x00000000
[SYMCHK] NumSyms: 0
[SYMCHK] SymType: SymPDB
[SYMCHK] ModName: 3NMSMTHR
[SYMCHK] ImageName: C:\utils\inetmgr\patch01\3NMSMTHR.DLL
[SYMCHK] LoadedImage: C:\utils\inetmgr\patch01\3NMSMTHR.DLL
[SYMCHK] PDB: "c:\utils\inetmgr\patch01\3NMSMTHR.pdb"
[SYMCHK] CV: RSDS
[SYMCHK] CV DWORD: 0x53445352
[SYMCHK] CV Data:  I:\usr\bpi\adrutl\3NMSMTHR.pdb
[SYMCHK] PDB Sig:  0
[SYMCHK] PDB7 Sig: {A865C40A-5070-4752-AD1F-CD3087843807}
[SYMCHK] Age: 4
[SYMCHK] PDB Matched:  TRUE
[SYMCHK] DBG Matched:  TRUE
[SYMCHK] Line nubmers: TRUE
[SYMCHK] Global syms:  TRUE
[SYMCHK] Type Info:    TRUE
[SYMCHK] ------------------------------------
SymbolCheckVersion  0x00000002
Result              0x001f0001
DbgFilename
DbgTimeDateStamp    0x4cc1b0f8
DbgSizeOfImage      0x00008000
DbgChecksum         0x00000000
PdbFilename         c:\utils\inetmgr\patch01\3NMSMTHR.pdb
PdbSignature        {A865C40A-5070-4752-AD1F-CD3087843807}
PdbDbiAge           0x00000004
[SYMCHK] [ 0x00000000 - 0x001f0001 ] Checked "C:\utils\inetmgr\patch01\3NMSMTHR.DLL"

SYMCHK: FAILED files = 0
SYMCHK: PASSED + IGNORED files = 1

这会在我给定的正确路径中找到 PDB(请注意,我将这个确切的 PDB 文件复制到 e:\ads_symbols,这是 lm 输出中看到的路径)。此 symchk 输出状态 Line Numbers: true,因此我希望看到私有样式信息。但是,如果我运行 ~kv ,那么对于堆栈跟踪中的函数,我会看到:

00bef2ac 01052a8a 00000000 00000000 00020aa4 3NMSMTHR!BPMThrProcTerm+0x2c0
00bef2cc 100073eb 00bef4d8 00000000 00000000 3NMSMTHR!BPMThrThreadInitName+0x2a

这看起来不像是在读取私有信息——我没有像我一样获得源列表对于在 MSFT 符号服务器上具有私有符号的 MS CRT 函数。另外,如果我执行 x /t /d 3NMSMTHR!ThreadInitName 然后我会得到

01052a60 <NoType> 3NMSMTHR!BPMThrThreadInitName = <no type information>

最后如果我尝试使用 .frame3 (转到那个帧),然后执行 dv 显示当地人,我收到:

0:001> .frame
03 00bef2cc 100073eb 3NMSMTHR!BPMThrThreadInitName+0x2a
0:001> dv
Unable to enumerate locals, HRESULT 0x80004005
Private symbols (symbols.pri) are required for locals.
Type ".hh dbgerr005" for details.

这对我来说没有意义。任何帮助将不胜感激。我的总体目标是获取参数和源信息。或者确认我拥有的 PDB 文件实际上不是私有符号。我没有构建这个 DLL 或 PDB,也不知道传递给它的链接器选项的任何细节。

谢谢!

编辑:

我没有提到我收到校验和错误:

*** WARNING: Unable to verify checksum for C:\utils\inetmgr\3NMSMTHR.dll

抱歉!我试图按照下面的建议运行 .lines 命令,我看到:

*** WARNING: Unable to verify checksum for C:\utils\inetmgr\3NMSMTHR.dll
DBGHELP: 3NMSMTHR - private symbols & lines 
    e:\ads_symbols\3NMSMTHR.pdb
Line number information will not be loaded

所以我想这就是我的问题。这引出了我的下一个问题:有没有办法修复校验和(列为 0,请参见上面的 symchk 输出)?考虑到 symchk 输出,该 PDB 是正确的。我可以让它绕过校验和检查吗?

EDIT2:

对于遇到此问题的其他人:我能够通过以下方式修复校验和警告:

editbin /release 3NMSMTHR.DLL

这在 PE 标头中设置了校验和。然后我必须运行

.symopt+0x40

In WinDbg 才能强制它加载 PDB,即使 DLL 上的时间戳不同。我确信我也可以使用一些实用程序来更新修改后的时间戳。

这修复了有关校验和的警告...但仍然没有参数信息(在右侧框架上运行 dv),没有源行信息等。

所以现在我迷路了。这些 PDB 是否可能不包含该信息?我如何确认这一点?我将如何构建它们来遏制它?我们使用 NMAKE 来构建它们。

EDIT3:

我将 DLL 和 PDB 重建为 DEBUG,然后获得了我期望的所有堆栈跟踪信息。所以现在我的问题是:(1)是否可以在版本中构建并获取静态函数、参数信息等(私有符号信息)? (2) 我从 dll+pdbs 版本中获得的堆栈跟踪不正确——第一个函数入口点是正确的,但下一个堆栈帧显示了一个未调用的函数。我的假设是发布的 DLL 内联了一些函数,并且 PDB 不知何故只是“猜测”该框架中的函数?很奇怪。

I am trying to debug a problem in a native DLL using WinDBG. I believe that I have the private symbols loaded, but WinDBG is not displaying the source lines or parameter information. Here is what I am observing; any help would be greatly appreciated!

I have the PDB which I believe corresponds to the DLL in the symbol search path. Running lm I see:

01050000 01058000   3NMSMTHR C (private pdb symbols)  e:\ads_symbols\3NMSMTHR.pdb

As this states "private pdb symbols" I expect that this is the private pdb.

I also ran symchk and see the following output:

C:\utils\inetmgr\patch01>"c:\Program Files\Debugging Tools for Windows (x86)\symchk.exe" /v 3nmsmthr.dll /s c:\utils\inetmgr\patch01
[SYMCHK] Searching for symbols to C:\utils\inetmgr\patch01\3nmsmthr.dll in path c:\utils\inetmgr\patch01
DBGHELP: Symbol Search Path: c:\utils\inetmgr\patch01
[SYMCHK] Using search path "c:\utils\inetmgr\patch01"
DBGHELP: No header for C:\utils\inetmgr\patch01\3NMSMTHR.DLL.  Searching for image on disk
DBGHELP: C:\utils\inetmgr\patch01\3NMSMTHR.DLL - OK
DBGHELP: 3NMSMTHR - private symbols & lines
     c:\utils\inetmgr\patch01\3NMSMTHR.pdb
[SYMCHK] MODULE64 Info ----------------------
[SYMCHK] Struct size: 1680 bytes
[SYMCHK] Base: 0x10000000
[SYMCHK] Image size: 32768 bytes
[SYMCHK] Date: 0x4cc1b0f8
[SYMCHK] Checksum: 0x00000000
[SYMCHK] NumSyms: 0
[SYMCHK] SymType: SymPDB
[SYMCHK] ModName: 3NMSMTHR
[SYMCHK] ImageName: C:\utils\inetmgr\patch01\3NMSMTHR.DLL
[SYMCHK] LoadedImage: C:\utils\inetmgr\patch01\3NMSMTHR.DLL
[SYMCHK] PDB: "c:\utils\inetmgr\patch01\3NMSMTHR.pdb"
[SYMCHK] CV: RSDS
[SYMCHK] CV DWORD: 0x53445352
[SYMCHK] CV Data:  I:\usr\bpi\adrutl\3NMSMTHR.pdb
[SYMCHK] PDB Sig:  0
[SYMCHK] PDB7 Sig: {A865C40A-5070-4752-AD1F-CD3087843807}
[SYMCHK] Age: 4
[SYMCHK] PDB Matched:  TRUE
[SYMCHK] DBG Matched:  TRUE
[SYMCHK] Line nubmers: TRUE
[SYMCHK] Global syms:  TRUE
[SYMCHK] Type Info:    TRUE
[SYMCHK] ------------------------------------
SymbolCheckVersion  0x00000002
Result              0x001f0001
DbgFilename
DbgTimeDateStamp    0x4cc1b0f8
DbgSizeOfImage      0x00008000
DbgChecksum         0x00000000
PdbFilename         c:\utils\inetmgr\patch01\3NMSMTHR.pdb
PdbSignature        {A865C40A-5070-4752-AD1F-CD3087843807}
PdbDbiAge           0x00000004
[SYMCHK] [ 0x00000000 - 0x001f0001 ] Checked "C:\utils\inetmgr\patch01\3NMSMTHR.DLL"

SYMCHK: FAILED files = 0
SYMCHK: PASSED + IGNORED files = 1

This finds the PDB in the right path I've given it (note that I copied this exact PDB file to e:\ads_symbols which is the path seen in the lm output). This symchk output states Line Numbers: true and thus I expect to see private style information. However, if I run ~kv then for my functions in the stack trace I see:

00bef2ac 01052a8a 00000000 00000000 00020aa4 3NMSMTHR!BPMThrProcTerm+0x2c0
00bef2cc 100073eb 00bef4d8 00000000 00000000 3NMSMTHR!BPMThrThreadInitName+0x2a

And this doesn't seem like its reading the private information-- I don't get the source listing like I do for the MS CRT functions which have private symbols on the MSFT symbol server. Also if I do x /t /d 3NMSMTHR!ThreadInitName then I get

01052a60 <NoType> 3NMSMTHR!BPMThrThreadInitName = <no type information>

And lastly if I try to use .frame3 (to go to that frame) and then execute dv to display the locals, I receive the:

0:001> .frame
03 00bef2cc 100073eb 3NMSMTHR!BPMThrThreadInitName+0x2a
0:001> dv
Unable to enumerate locals, HRESULT 0x80004005
Private symbols (symbols.pri) are required for locals.
Type ".hh dbgerr005" for details.

This doesn't make sense to me. Any help would be much appreciated. My overall goal is to get the parameter and source information. OR to confirm that the PDB file I have is in fact NOT the private symbols. I didn't build this DLL or PDB nor do I know any specifics about the linker options passed to it.

Thanks!

EDIT:

I failed to mention that I am getting the checksum error:

*** WARNING: Unable to verify checksum for C:\utils\inetmgr\3NMSMTHR.dll

Sorry! I was trying to run the .lines command as suggested below and I see:

*** WARNING: Unable to verify checksum for C:\utils\inetmgr\3NMSMTHR.dll
DBGHELP: 3NMSMTHR - private symbols & lines 
    e:\ads_symbols\3NMSMTHR.pdb
Line number information will not be loaded

So I guess that's my problem. Which leads to my next question: is there a way to fix the checksum (which is listed as 0, see above symchk output)? This PDB is the correct one given the symchk output. Can I have it bypass the checksum check?

EDIT2:

For anyone else that comes across this: I was able to fix the checksum warning by:

editbin /release 3NMSMTHR.DLL

This set the checksum in the PE header. Then I had to run the

.symopt+0x40

In WinDbg in order to force it to load the PDB even though the timestamp on the DLL was different. I'm sure that alternatively I could've used some utility to update the modified timestamp as well.

That fixed the warning about the checksum...but STILL no parameter info (running dv on the right frame), no source line info, etc.

So now I'm lost. Is it possible that these PDBs don't contain that info? How could I confirm that? How would I build them to contain it? We use NMAKE to build these.

EDIT3:

I rebuilt the DLL and PDB as DEBUG and then got all of the stack trace information that I expected. So now my question is: (1) is it possible to build in release and get the static functions, parameter info, etc. (private symbol info)? and (2) the stack trace I was getting with the release dlls+pdbs was incorrect-- the first function entrypoint was correct, but then the next stack frame showed a func that wasn't called. My assumption is that the release DLL inlined some functions and somehow the PDB was just "guessing" at the function in that frame? Very strange.

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(4

生生漫 2024-11-15 23:22:55

您尝试过 .lines 命令吗?

Did you try the .lines command?

落日海湾 2024-11-15 23:22:55

如果您希望即使在发布模式下也能够理解转储或堆栈跟踪,您应该确保以下几点:

  1. 使用 /Zi 或 /ZI 进行编译(调试信息格式是两个程序数据库选项之一)。
  2. 您不使用 /Oy 进行编译(忽略帧指针)。
  3. 您与/DEBUG(生成调试信息)链接。
  4. 您保留(但不分发)生成的 .pdb 文件。

主要是避免遗漏帧指针;省略它们可以在函数调用中节省一点时间/空间,但使堆栈遍历变得非常困难。请注意,由于其他优化设置(特别是内联),您可能仍然会从发布版本中获得奇怪的堆栈跟踪,但它们仍然应该具有大多数有趣的功能。

If you want to be able to make sense of dumps or stack traces even in Release mode, you should ensure the following:

  1. You compile with /Zi or /ZI (Debug Information Format is one of the two Program Database options).
  2. You do not compile with /Oy (Omit Frame Pointers).
  3. You link with /DEBUG (Generate Debug Info).
  4. You keep (but don't distribute) the resulting .pdb file.

The main thing is to avoid omitting frame pointers; omitting them saves a little bit of time/space in a function call but makes it very hard to stack walk. Note that you may still get odd stack traces from release builds due to other optimisation settings (particularly inlining) but they should still have the majority of interesting functions.

不美如何 2024-11-15 23:22:55

如果函数是用汇编语言编写的,您将不会有类型信息。另外,静态库也可能链接到 DLL,并且静态库没有完整的调试信息。

You will not have type information if the function is written in assembly language. Also it is possible that a static library was linked to the DLL and the static library did not have full debug information.

窗影残 2024-11-15 23:22:55

我知道这已经过时了,但对于遇到此问题的任何人来说,对我有用的是运行“.lines -e”。这可能就是纳文所建议的。

I know this is old, but for anyone coming across this issue, what worked for me was to run ".lines -e". This is probably what Naveen was suggesting.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文