Имя функции из трассировки стека Windows - PullRequest
1 голос
/ 11 января 2010

Как восстановить имя функции трассировки стека вместо <UNKNOWN>?

    Event Type: Error
    Event Source:   abcd
    Event Category: None
    Event ID:   16
    Date:       1/3/2010
    Time:       10:24:10 PM
    User:       N/A
    Computer:   CMS01
    Description:
    Server.exe caused a  in module  at 2CA001B:77E4BEF7

    Build 6.0.0.334

    WorkingSetSize: 1291071488 bytes

    EAX=02CAF420  EBX=00402C88  ECX=00000000  EDX=7C82860C  ESI=02CAF4A8
    EDI=02CAFB68  EBP=02CAF470  ESP=02CAF41C  EIP=77E4BEF7  FLG=00000206
    CS=2CA001B   DS=2CA0023  SS=7C820023  ES=2CA0023   FS=7C82003B  GS=2CA0000

    2CA001B:77E4BEF7 (0xE06D7363 0x00000001 0x00000003 0x02CAF49C) 
    2CA001B:006DFAC7 (0x02CAF4B8 0x00807F50 0x00760D50 0x007D951C) 
    2CA001B:006DFC87 (0x00003561 0x7F6A0F38 0x008E7290 0x00021A6F) 
    2CA001B:0067E4C3 (0x00003561 0x00000000 0x02CAFBB8 0x02CAFB74) 
    2CA001B:00674CB2 (0x00003561 0x006EBAC7 0x02CAFB68 0x02CAFA64) 
    2CA001B:00402CA4 (0x00003560 0x00000000 0x00000000 0x02CAFBB8) 
    2CA001B:00402B29 (0x00003560 0x00000001 0x02CAFBB8 0x00000000) 
    2CA001B:00683096 (0x00003560 0x563DDDB6 0x00000000 0x02CAFC18) 
    2CA001B:00688E32 (0x02CAFC58 0x7C7BE590 0x00000000 0x00000000) 
    2CA001B:00689F0C (0x02CAFC58 0x7C7BE590 0x00000000 0x00650930) 
    2CA001B:0042E8EA (0x7F677648 0x7F677648 0x00CAFD6C 0x02CAFD6C) 
    2CA001B:004100CA (0x563DDB3E 0x00000000 0x00000000 0x008E7290) 
    2CA001B:0063AC39 (0x7F677648 0x02CAFD94 0x02CAFD88 0x77B5B540) 
    2CA001B:0064CB51 (0x7F660288 0x563DD9FE 0x00000000 0x00000000) 
    2CA001B:0063A648 (0x00000000 0x02CAFFEC 0x77E6482F 0x008E7290) 
    2CA001B:0063A74D (0x008E7290 0x00000000 0x00000000 0x008E7290) 
    2CA001B:77E6482F (0x0063A740 0x008E7290 0x00000000 0x00000000) 

Ответы [ 5 ]

1 голос
/ 11 января 2010

Получите точно такую ​​же сборку программы, objdump, и посмотрите, какая функция находится по адресу. Если имена символов были удалены из исполняемого файла, это может быть немного сложно.

Если программный код каким-либо образом динамический, вам, возможно, придется запустить его в отладчике, чтобы найти адреса функций.

Если программа намеренно запутана и противна, и она каким-то образом рандомизирует адреса своих функций во время выполнения (иногда это делают уклончивые вещи, такие как вирусы или код защиты от копирования), тогда все ставки отключены.

В общем: Самый простой способ выяснить причину сбоя - выполнить шаги, необходимые для его воспроизведения в экземпляре приложения, запущенного в отладчике. Все остальные подходы намного сложнее. Вот почему разработчики часто не тратят время на устранение ошибок, для которых нет известных способов воспроизведения.

0 голосов
/ 12 января 2010

Самая распространенная причина в том, что у вас нет модуля по указанному адресу. Это может случиться, например, когда вы разыменовываете неинициализированный указатель на функцию или вызываете виртуальную функцию, используя недопустимый указатель this.

Вероятно, это не тот случай: «77E4BEF7» с очень высокой вероятностью является Windows DLL, а 006DFAC7 - адресом в одном из ваших модулей. Для этого вам не нужны файлы PDB: Windows всегда должна знать имя модуля (.EXE или .DLL) - фактически, для этого нужно сначала имя этого модуля, чтобы даже найти правильный файл PDB.

Теперь остается вопрос, почему у вас нет информации о модуле. Это я не могу сказать из информации выше. Вам нужна информация о реальной системе. Например, если есть DEP? Включен ли DEP для вашего процесса?

0 голосов
/ 11 января 2010

Я использую StackWalker - просто скомпилируйте его в исходный код вашей программы, и в случае его сбоя вы можете сгенерировать трассировку стека в это время, включая имена функций.

0 голосов
/ 11 января 2010

Вам необходимо иметь файл с информацией об отладке (.pdb) рядом с exe при возникновении сбоя.
Тогда, надеюсь, ваш код аварийного дампа может загрузить его и использовать информацию в нем.

0 голосов
/ 11 января 2010

Попробуйте запустить тот же встроенный из вашей IDE, приостановить его и перейти к адресам в сборке. Затем вы можете переключиться на исходный код и увидеть там функции.

По крайней мере, так работает в Delphi. И я знаю об этой возможности и в Visual Studio.

Если у вас нет встроенной IDE, вы должны использовать отладчик, такой как OllyDbg. Запустите исполняемый файл, вызвавший ошибки, и приостановите приложение в OllyDbg. Перейти к адресам из стека трассировки. Откройте аналогичный проект приложения в вашей среде IDE, запустите его и приостановите. Найдите тот же двоичный шаблон, который вы видите в OllyDbg, а затем переключитесь на исходный код.

Последняя известная мне возможность - анализ файла карты, если вы создали его во время сборки.

...