Postprocess drmemory error stacks with new symbols

2019-09-16 06:25发布

问题:

After running a set of tests with drmemory overnight I am trying to resolve the error stacks by providing pdb symbols. The pdb's come from a large samba-mapped repository and using _NT_SYMBOL_PATH at runtime slowed things down too much.

Does anyone know of a tool that post-processes results.txt and pulls new symbols (via NT_SYMBOL_PATH or otherwise) as required to produce more detailed stacks ? If not, any hints for adapting asan_symbolize.py to do this ?

https://llvm.org/svn/llvm-project/compiler-rt/trunk/lib/asan/scripts/asan_symbolize.py

What I came up with so far using dbghelp.dll is below. Works but could be better.

https://github.com/patraulea/postpdb

回答1:

ok this Query does not pertain to use of windbg or doesn't have anything to do with _NT_SYMBOL_PATH

Dr.Memory is a memory diagnostic tool akin to valgrind and is based on Dynamorio instumentation framework usable on raw unmodified binaries

on windows you can invoke it like drmemory.exe calc.exe from a command prompt (cmd.exe)

as soon as the binary finishes execution a log file named results.txt is written to a default location

if you had setup _NT_SYMBOL_PATH drmemory honors it and resolves symbol information from prepulled symbol file (viz *.pdb) it does not seem to download files from ms symbol server it simply seems to ignore the SRV* cache and seems to use only the downstream symbol folder

so if the pdb file is missing or isnt downloaded yet

the results.txt will contain stack trace like

# 6 USER32.dll!gapfnScSendMessage +0x1ce    (0x75fdc4e7 <USER32.dll+0x1c4e7>)
# 7 USER32.dll!gapfnScSendMessage +0x2ce    (0x75fdc5e7 <USER32.dll+0x1c5e7>)

while if the symbol file was available it would show

# 6 USER32.dll!InternalCallWinProc
# 7 USER32.dll!UserCallWinProcCheckWow

so basically you need the symbol file for appplication in question

so as i commented you need to fetch the symbols for the exe in question

you can use symchk on a running process too and create a manifest file and you can use symchk on a machine that is connected to internet to download symbols and copy it to a local folder on a non_internet machine and point _NT_SYMBOL_PATH to this folder

>tlist | grep calc.exe
1772 calc.exe          Calculator

>symchk /om calcsyms.txt /ip 1772
SYMCHK: GdiPlus.dll          FAILED  - MicrosoftWindowsGdiPlus-   
1.1.7601.17514-gdiplus.pdb mismatched or not found

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

>head -n 4 calcsyms.txt
calc.pdb,971D2945E998438C847643A9DB39C88E2,1
calc.exe,4ce7979dc0000,1
ntdll.pdb,120028FA453F4CD5A6A404EC37396A582,1
ntdll.dll,4ce7b96e13c000,1

>tail -n 4 calcsyms.txt
CLBCatQ.pdb,00A720C79BAC402295B6EBDC147257182,1
clbcatq.dll,4a5bd9b183000,1
oleacc.pdb,67620D076A2E43C5A18ECD5AF77AADBE2,1
oleacc.dll,4a5bdac83c000,1

so assuming you have fetched the symbols it would be easier to rerun the tests with a locally cached copies of the symbol files

if you have fetched the symbols but you cannot rerun the tests and have to work solely with the output from results.txt you have some text processing work (sed . grep , awk . or custom parser)

the drmemory suite comes with a symbolquery.exe in the bin folder and it can be used to resolve the symbols from results.txt

in the example above you can notice the offset relative to modulebase like 0x1c4e7 in the line # 6 USER32.dll!gapfnScSendMessage +0x1ce (0x75fdc4e7 {USER32.dll+0x1c4e7})

so for each line in results.txt you have to parse out the offset and invoke symbolquery on the module like below

:\>symquery.exe -f -e c:\Windows\System32\user32.dll -a +0x1c4e7
InternalCallWinProc+0x23
??:0

:\>symquery.exe -f -e c:\Windows\System32\user32.dll -a +0x1c5e7
UserCallWinProcCheckWow+0xb3

a simple test processing example from a result.txt and a trimmed output

:\>grep "^#"  results.txt | sed s/".*<"//g
# 0 system call NtUserBuildPropList parameter #2
USER32.dll+0x649d9>)
snip
COMCTL32.dll+0x2f443>)

notice the comctl32.dll (there is a default comctl.dll in system32.dll and several others in winsxs you have to consult the other files like global.log to view the dll load path

symquery.exe -f -e c:\Windows\winsxs\x86_microsoft.windows.common-   
controls_6595b64144ccf1df_6.0.7601.17514_none_41e6975e2bd6f2b2\comctl32.dll -a +0x2f443
CallOriginalWndProc+0x1a
??:0

symquery.exe -f -e c:\Windows\system32\comctl32.dll -a +0x2f443
DrawInsert+0x120 <----- wrong symbol due to wrong module (late binding 
/forwarded xxx yyy reasons)