我在一個大型應用程序上工作,經常使用WinDbg來診斷基於客戶的DMP文件的問題。我已經爲WinDbg寫了一些小擴展,這些擴展已經證明對於從DMP文件中提取信息位非常有用。在我的擴展代碼中,我發現自己以相同的方式反覆引用C++類對象,一次又一次地,手動。例如:如何基於WinDbg擴展中的轉儲文件內存創建對象?
Address = GetExpression("somemodule!somesymbol");
ReadMemory(Address, &addressOfPtr, sizeof(addressOfPtr), &cb);
// get the actual address
ReadMemory(addressOfObj, &addressOfObj, sizeof(addressOfObj), &cb);
ULONG offset;
ULONG addressOfField;
GetFieldOffset("somemodule!somesymbolclass", "somefield", &offset);
ReadMemory(addressOfObj+offset, &addressOfField, sizeof(addressOfField), &cb);
行之有效,但我已經寫了更多的擴展,具有更強大的功能(和訪問我們的應用DMP文件的更多複雜的對象),我渴望一個更好的解決方案。我當然可以訪問我們自己的應用程序的源代碼,所以我認爲應該有一種方法可以將對象從DMP文件中複製出來,並使用該內存在調試器擴展中創建一個實際對象,以便我可以調用函數通過鏈接來自我們的應用程序的DLL)。這可以幫助我省去手工從DMP中取出東西的麻煩。
這甚至可能嗎?我嘗試了一些顯而易見的事情,例如在擴展中創建一個新對象,然後直接從DMP文件中用一個大的ReadMemory覆蓋它。這似乎將數據放在正確的字段中,但是當我試圖調用一個函數時卻嚇壞了。我想我失去了一些東西......也許C++拉了一些我不知道的vtable時髦性?我的代碼看起來與此類似:
SomeClass* thisClass = SomeClass::New();
ReadMemory(addressOfObj, &(*thisClass), sizeof(*thisClass), &cb);
後續:它看起來像從EngExtCpp可能ExtRemoteTyped是我想要的嗎?有沒有人成功使用過這個?我需要谷歌了一些示例代碼,但沒有多少運氣。
跟帖2:我追求這一調查的兩種不同的路線。
1)我期待到ExtRemoteTyped,但現在看來這個類是真的只是爲ReadMemory/GetFieldOffset調用一個幫手。是的,這將有助於加快ALOT的速度,但對於從DMP文件重新創建對象並沒有什麼幫助。儘管文檔很渺茫,所以我可能會誤解某些東西。 2)我也在考慮嘗試使用ReadMemory來使用DMP文件中的數據覆蓋在擴展中創建的對象。但是,我並沒有像上面那樣使用sizeof(* thisClass),而是認爲我只會挑選出數據元素,並保持vtable不變。
偉大的問題PJ! – 2010-04-04 21:52:01