Friday, February 6, 2009

Alias evaluation in WinDBG script

I copied and pasted the following commands from Dmitry Vostokov's Memory Dump Analysis Volume 2 into a script file.

aS /c FirstModule .printf "%mu", @@c++((*(ntdll!_LDR_DATA_TABLE_ENTRY**)&@$peb->Ldr->InLoadOrderModuleList.Flink)->BaseDllName.Buffer);
.dump /ma /u c:\${FirstModule}.dmp;


To see whether the script actually works, I launched a notepad, attached windbg to it, and ran the script. However, the script generated the output as following for every run,

c:\${FirstModule}_1008_2009-02-06_11-56-11-549_17f0.dmp - mini user dump
Dump successfully written


Somehow, the alias was not evaluated. However, as I entered those commands directly into the windbg command window, the alias was evaluated as expected. After trial and error, I changed the script as following,

.block
{
aS /c FirstModule .printf "%mu", @@c++((*(ntdll!_LDR_DATA_TABLE_ENTRY**)&@$peb->Ldr->InLoadOrderModuleList.Flink)->BaseDllName.Buffer);
.dump /ma /u c:\${FirstModule}.dmp;
}


As I ran the script for the first time, the alias still was not evaluated.

c:\${FirstModule}_1008_2009-02-06_12-12-47-359_17f0.dmp - mini user dump
Dump successfully written


However, as I ran the script the second time and more, the alias was evaluated correctly.

c:\notepad.exe_1008_2009-02-06_12-14-58-959_17f0.dmp - mini user dump
Dump successfully written


Then I looked up the .block from the windbg help. The comments section explains the reason.

When each block is entered, all aliases within the block are evaluated. If you alter the value of an alias at some point within a command block, commands subsequent to that point will not use the new alias value unless they are within a subordinate block.

Then I changed the script as following and everything works like a charm since then.

aS /c FirstModule .printf "%mu", @@c++((*(ntdll!_LDR_DATA_TABLE_ENTRY**)&@$peb->Ldr->InLoadOrderModuleList.Flink)->BaseDllName.Buffer);
.block
{
.dump /ma /u c:\${FirstModule}.dmp;
}


1 comments:

  1. Here is another script, which could be used to search a specified string from the stack traces of all threads in a process.

    aS ThreadStack "~*e r? $t1=((ntdll!_NT_TIB *)@$teb)->StackLimit; r? $t2=((ntdll!_NT_TIB *)@$teb)->StackBase; dps @$t1 @$t2";
    .block {.shell -i - -ci "${ThreadStack}" FIND /C "${$arg1}"}

    Please note the line ".block {.shell -i - -ci "${ThreadStack}" FIND /C "${$arg1}"}" must be on a single line, otherwise, the error message "FIND: Parameter format not correct" would return.

    Sometimes, it is kind of tricky to set an alias right. At that time, al (List Alias) command could be used to check whether the alias is set correct.
    ReplyDelete