I'm following the directions on windbg.info to try and find the source corresponding to a memory allocation/leak in my program. I set up a test case with leaky code to try and demonstrate this. I can get part of the way there, but not able to see actual source.
The C++ code in question is a debug build (optimization turned off, etc). Called multiple times.
class test
{
public:
int Allocate()
{
pai = new int[128];
pasz = new char[128];
}
private:
int * pai = nullptr;
char * pasz = nullptr;
};
I'm following the directions on windbg.info (shortened):
- To get source information you must additionally enable page heap in step 1 (gflags.exe /i MyApp.exe +ust +hpa) ...
- Do a !heap -flt s [Size]. [Size]=AllocSize determined previously. This command will list down all blocks with that particular size.
- Do a !heap -p -a [UserAddr] to get the stack trace from where you have allocated that much bytes. Use the [UserAddr] that you got in previous step
- Do a dt ntdll!_DPH_HEAP_BLOCK StackTrace [MyHeapBlockAddr], where [MyHeapBlockAddr] is the DPH_HEAP_BLOCK address retrieved in step 3.
- Do a dds [StackTrace]", where [StackTrace] is the value retrieved in previous step. Note that dds will dump the stack with source information included.
I do have all symbols loaded correctly:
00007ff7`b1400000 00007ff7`b142b000 ConsoleApplication1 C (private pdb symbols) c:\...
00007ff8`37ae0000 00007ff8`37c9e000 ucrtbased (private pdb symbols) c:\...
00007ff8`39d20000 00007ff8`39e16000 MSVCP140D (private pdb symbols) c:\...
00007ff8`40e30000 00007ff8`40e9e000 verifier (private pdb symbols) c:\...
00007ff8`40ec0000 00007ff8`40ee2000 VCRUNTIME140D (private pdb symbols) c:\...
00007ff8`6a410000 00007ff8`6a62d000 KERNELBASE (private pdb symbols) c:\...
00007ff8`6b4c0000 00007ff8`6b56c000 KERNEL32 (private pdb symbols) c:\...
00007ff8`6d9e0000 00007ff8`6dbb1000 ntdll (private pdb symbols) c:\...
I do see a 'good' stack that shows the call to test::Allocate:
0:004> !heap -flt s 2034
_DPH_HEAP_ROOT @ 272d60e1000
Freed and decommitted blocks
DPH_HEAP_BLOCK : VirtAddr VirtSize
Busy allocations
DPH_HEAP_BLOCK : UserAddr UserSize - VirtAddr VirtSize
00000272d60ecf70 : 00000272d6467fc0 0000000000002034 - 00000272d6467000 0000000000004000
0:004> !heap -p -a 00000272d6467fc0
address 00000272d6467fc0 found in
_DPH_HEAP_ROOT @ 272d60e1000
in busy allocation ( DPH_HEAP_BLOCK: UserAddr UserSize - VirtAddr VirtSize)
272d60ecf70: 272d6467fc0 2034 - 272d6467000 4000
...
00007ff7b14142a8 ConsoleApplication1!test::Allocate+0x0000000000000048
00007ff7b141495a ConsoleApplication1!main+0x000000000000008a
...
I thought I might be able to now get the source of this memory allocation:
0:004> dt ntdll!_DPH_HEAP_BLOCK StackTrace 00000272d60ecf70
+0x060 StackTrace : 0x00000272`d2f106d0 _RTL_TRACE_BLOCK
0:004> dds 0x00000272`d2f106d0
00000272`d2f106d0 00000000
00000272`d2f106d4 00000000
00000272`d2f106d8 00008804
...
No source even though I do have 'source file path' set. I have not found any examples of what a successful case looks like. Have I done something wrong in the environment set up, or the commands?
windbg version: 6.12.0002.633 AMD64. x64 test executable.
dds
is the command for dump DWORD and interpret as stack. This may work for 32 bit applications.
Your application is a 64 bit application. I can see this from addresses like 00007ff7'b1400000
which contain a backtick. So you should use dqs
(dump quad words and interpret as stack).
Even better is dps
(dump pointer size and interpret as stack), since it will use 32 or 64 bit depending on the architecture of your application.
User contributions licensed under CC BY-SA 3.0