Исключение COM на "пользовательский компонент" - как определить DLL?
У нас есть большое унаследованное приложение VB, состоящее из нескольких библиотек DLL (несколько десятков или около того), установленных в одном приложении сервера COM+. Время от времени происходит что-то, что вызывает dllhost.exe киль (и автоматический перезапуск), оставляя это сообщение в журнале событий приложений Windows...
Система вызвала пользовательский компонент, и этот компонент вышел из строя и сгенерировал исключение. Это указывает на проблему с пользовательским компонентом. Сообщите разработчику этого компонента о сбое и предоставьте ему информацию ниже.
Идентификатор серверного приложения: {8CC02F18-2733-4A17-9E5C-1A70CB6B6977}
Идентификатор экземпляра приложения сервера: {1940A147-8A5E-45FA-86FE-DAF92A822597}
Имя приложения сервера: MyTestApp
Серьезный характер этой ошибки привел к прекращению процесса.
Исключение: C0000005
Адрес: 0x758DA3DAИсточник: Complus
Код события: 4786
Уровень: Ошибка
Наряду с этим это еще один журнал, в частности, на dllhost.exe...
Неверное имя приложения: dllhost.exe, версия: 6.0.6000.16386, отметка времени: 0x4549b14e
Неверное имя модуля: msvcrt.dll, версия: 7.0.6002.18005, отметка времени: 0x49e0379e.
Код исключения: 0xc0000005
Смещение ошибки: 0x0000a3da
Идентификатор ошибочного процесса: 0x83c
Время запуска ошибочного приложения: 0x01cb50c507ee0166
Неверный путь к приложению: %11
Неверный путь к модулю: %12
Идентификатор отчета: %13
Я знаю, что это указывает на ошибку во время выполнения C (msvcrt), но в идеале мне нужно проследить это обратно в DLL, которая вызывается в msvcrt (возможно, с неверными данными / параметрами). Итак, без установки отладчика, есть ли способ определить DLL, которая вызывает это? Я пытаюсь увидеть, есть ли где-нибудь дамп памяти, который я могу использовать для анализа в автономном режиме - и, таким образом, привязать адрес к чему-то конкретному. Но без этого я не уверен, что это возможно. Может ли подсистема COM получить минимальный дамп при сбое размещенного приложения? (да, это возможно [возможно] - на вкладке "Дамп" есть флажок).
Это на Windows Server 2008 R1 32-битный (но также будет интересен и для Server 2003).
Это не влияет на доступность приложения - COM+ просто перезапускает dllhost, и приложение продолжается, но это неудобство, которое было бы полезно исправить.
Ладно, у меня аварийная свалка, у меня виндбг, но это не помогает. Не уверен, что я толстый (возможно) или что-то еще:-) Вывод !analyze -v
ниже, но он ничего не показывает в наших DLL, хотя похоже, что он не смог разрешить FAULTING_IP? Я не уверен, куда обратиться дальше.
Мне интересно, являются ли какие-либо из моих pdb унылыми и стоит создавать новые - подключенные к серверу символов Microsoft, поэтому они не должны быть, но не уверены, для какого модуля он (очевидно) сообщает о неправильных символах для (BUGCHECK_STR и PRIMARY_PROBLEM_CLASS) (или эти символы находятся на сервере, на котором изначально выполнялся код?). Было бы лучше разместить PDB на самом сервере?
Если нет, то есть другие идеи? Раньше я кратко использовал windbg, но я не являюсь его постоянным пользователем, так что, может быть, есть еще заклинания, которые мне нужно набрать, чтобы копать глубже? Руководство приветствуется:-)
*******************************************************************************
* *
* Exception Analysis *
* *
*******************************************************************************
FAULTING_IP:
+5c112faf02e0d82c
00000000 ?? ???
EXCEPTION_RECORD: ffffffff -- (.exr 0xffffffffffffffff)
ExceptionAddress: 00000000
ExceptionCode: 80000003 (Break instruction exception)
ExceptionFlags: 00000000
NumberParameters: 0
FAULTING_THREAD: 00000f1c
DEFAULT_BUCKET_ID: WRONG_SYMBOLS
PROCESS_NAME: dllhost.exe
ERROR_CODE: (NTSTATUS) 0x80000003 - {EXCEPTION} Breakpoint A breakpoint has been reached.
EXCEPTION_CODE: (HRESULT) 0x80000003 (2147483651) - One or more arguments are invalid
MOD_LIST: <ANALYSIS/>
NTGLOBALFLAG: 0
APPLICATION_VERIFIER_FLAGS: 0
MANAGED_STACK: !dumpstack -EE
OS Thread Id: 0xf1c (0)
Current frame:
ChildEBP RetAddr Caller,Callee
LAST_CONTROL_TRANSFER: from 77b15620 to 77b15e74
PRIMARY_PROBLEM_CLASS: WRONG_SYMBOLS
BUGCHECK_STR: APPLICATION_FAULT_WRONG_SYMBOLS
STACK_TEXT:
0022fa68 77b15620 77429884 00000064 00000000 ntdll!KiFastSystemCallRet
0022fa6c 77429884 00000064 00000000 00000000 ntdll!NtWaitForSingleObject+0xc
0022fadc 774297f2 00000064 ffffffff 00000000 kernel32!WaitForSingleObjectEx+0xbe
0022faf0 778e2c44 00000064 ffffffff 00e42374 kernel32!WaitForSingleObject+0x12
0022fb0c 778e2e32 00060848 0022fb5b 00000000 ole32!CSurrogateProcessActivator::WaitForSurrogateTimeout+0x55
0022fb24 00e413a4 0022fb40 00000000 00061d98 ole32!CoRegisterSurrogateEx+0x1e9
0022fcb0 00e41570 00e40000 00000000 00061d98 dllhost!WinMain+0xf2
0022fd40 7742d0e9 7ffde000 0022fd8c 77af19bb dllhost!_initterm_e+0x1a1
0022fd4c 77af19bb 7ffde000 dc2ccd29 00000000 kernel32!BaseThreadInitThunk+0xe
0022fd8c 77af198e 00e416e6 7ffde000 ffffffff ntdll!__RtlUserThreadStart+0x23
0022fda4 00000000 00e416e6 7ffde000 00000000 ntdll!_RtlUserThreadStart+0x1b
STACK_COMMAND: .cxr 00000000 ; kb ; dt ntdll!LdrpLastDllInitializer BaseDllName ; dt ntdll!LdrpFailureData ; ~0s; .ecxr ; kb
FOLLOWUP_IP:
dllhost!WinMain+f2
00e413a4 ff15a410e400 call dword ptr [dllhost!_imp__CoUninitialize (00e410a4)]
SYMBOL_STACK_INDEX: 6
SYMBOL_NAME: dllhost!WinMain+f2
FOLLOWUP_NAME: MachineOwner
MODULE_NAME: dllhost
IMAGE_NAME: dllhost.exe
DEBUG_FLR_IMAGE_TIMESTAMP: 4549b14e
FAILURE_BUCKET_ID: WRONG_SYMBOLS_80000003_dllhost.exe!WinMain
BUCKET_ID: APPLICATION_FAULT_WRONG_SYMBOLS_dllhost!WinMain+f2
2 ответа
У вас есть символы для VB DLL? Символы важны для получения стека вызовов. Я надеюсь, у вас есть правильные символы. Ты можешь использовать ld *
а потом lme
который должен получить список символов, которые не совпадают в пределах windbg. Также установите путь к символам для символов MS, а также для своего пользовательского кода, используя _NT_SYMBOL_PATH
Один из самых простых вариантов - загрузить дамп в DebugDiag, который должен дать вам причину сбоя вместе со стеком вызовов. DebugDiag имеет расширения отладчика для Complus.
И вот команда родного стека вызовов для всех потоков
~*ek
и этот один переключиться на текущее исключение
.ecxr
Отладка Mon / WinDbg - лучший способ устранить эту проблему. у вас должна быть возможность использовать список модулей в winDbg или команду lm для просмотра списка загруженных модулей. Затем трассировка стека должна сказать вам, какие библиотеки задействованы. Это должно быть возможно даже без символов для процесса / DLL.