Author: fireball Date: Mon Nov 19 14:26:52 2007 New Revision: 30576
URL: http://svn.reactos.org/svn/reactos?rev=30576&view=rev Log: - Rewrite KdbSymProcessSymbols to use the KD_SYMBOLS_INFO structure kernel sends us. This removes the need for ugly names operations (maybe buggy!), and presents an elegant solution: just finding the needed module by its base address. - As a result, ALL modules get their symbols loaded now. - TODO: Remove KdbSymProcessBootSymbols(), it's used right now to load ntoskrnl and hal symbols during boot process.
Modified: trunk/reactos/ntoskrnl/include/internal/kd.h trunk/reactos/ntoskrnl/kd/kdmain.c trunk/reactos/ntoskrnl/kdbg/kdb_symbols.c
Modified: trunk/reactos/ntoskrnl/include/internal/kd.h URL: http://svn.reactos.org/svn/reactos/trunk/reactos/ntoskrnl/include/internal/k... ============================================================================== --- trunk/reactos/ntoskrnl/include/internal/kd.h (original) +++ trunk/reactos/ntoskrnl/include/internal/kd.h Mon Nov 19 14:26:52 2007 @@ -89,7 +89,7 @@ IN BOOLEAN LoadFromFile);
VOID -KdbSymProcessSymbols(IN PANSI_STRING FileName); +KdbSymProcessSymbols(IN PANSI_STRING FileName, IN PKD_SYMBOLS_INFO SymbolInfo);
BOOLEAN KdbSymPrintAddress(IN PVOID Address); @@ -119,12 +119,12 @@ # define KDB_LOADUSERMODULE_HOOK(LDRMOD) KdbSymLoadUserModuleSymbols(LDRMOD) # define KDB_LOADDRIVER_HOOK(FILENAME, MODULE) KdbSymLoadDriverSymbols(FILENAME, MODULE) # define KDB_UNLOADDRIVER_HOOK(MODULE) KdbSymUnloadDriverSymbols(MODULE) -# define KDB_SYMBOLFILE_HOOK(FILENAME) KdbSymProcessSymbols(FILENAME) +# define KDB_SYMBOLFILE_HOOK(FILENAME, SYMBOLINFO) KdbSymProcessSymbols((FILENAME), (SYMBOLINFO)) #else # define KDB_LOADUSERMODULE_HOOK(LDRMOD) do { } while (0) # define KDB_LOADDRIVER_HOOK(FILENAME, MODULE) do { } while (0) # define KDB_UNLOADDRIVER_HOOK(MODULE) do { } while (0) -# define KDB_SYMBOLFILE_HOOK(FILENAME) do { } while (0) +# define KDB_SYMBOLFILE_HOOK(FILENAME, SYMBOLINFO) do { } while (0) # define KDB_CREATE_THREAD_HOOK(CONTEXT) do { } while (0) #endif
Modified: trunk/reactos/ntoskrnl/kd/kdmain.c URL: http://svn.reactos.org/svn/reactos/trunk/reactos/ntoskrnl/kd/kdmain.c?rev=30... ============================================================================== --- trunk/reactos/ntoskrnl/kd/kdmain.c (original) +++ trunk/reactos/ntoskrnl/kd/kdmain.c Mon Nov 19 14:26:52 2007 @@ -131,7 +131,8 @@ else if (ExceptionCommand == BREAKPOINT_LOAD_SYMBOLS) { /* Load symbols. Currently implemented only for KDBG! */ - KDB_SYMBOLFILE_HOOK((PANSI_STRING)ExceptionRecord->ExceptionInformation[1]); + KDB_SYMBOLFILE_HOOK((PANSI_STRING)ExceptionRecord->ExceptionInformation[1], + (PKD_SYMBOLS_INFO)ExceptionRecord->ExceptionInformation[2]); }
/* This we can handle: simply bump EIP */
Modified: trunk/reactos/ntoskrnl/kdbg/kdb_symbols.c URL: http://svn.reactos.org/svn/reactos/trunk/reactos/ntoskrnl/kdbg/kdb_symbols.c... ============================================================================== --- trunk/reactos/ntoskrnl/kdbg/kdb_symbols.c (original) +++ trunk/reactos/ntoskrnl/kdbg/kdb_symbols.c Mon Nov 19 14:26:52 2007 @@ -578,50 +578,77 @@ }
VOID -KdbSymProcessSymbols(IN PANSI_STRING AnsiFileName) -{ - ANSI_STRING SystemPrefix, RealPathPrefix, ProperName; - CHAR Buffer[MAX_PATH], RealPathBuffer[MAX_PATH]; - - /* Init our strings for compare operations */ - RtlInitAnsiString(&SystemPrefix, "\SystemRoot"); - - /* Convert system root to ansi */ - sprintf(RealPathBuffer, "%S", (PWCHAR)&SharedUserData->NtSystemRoot[2]); - RtlInitAnsiString(&RealPathPrefix, RealPathBuffer); - RealPathPrefix.MaximumLength = MAX_PATH; - - /* There are 3 cases: - 1) \SystemRoot\System32\ -> no change - 2) \ReactOS\System32 -> \SystemRoot\System32 - 3) module.dll -> ??\C:\ReactOS\system32\module.dll - */ - if (RtlPrefixString(&SystemPrefix, AnsiFileName, FALSE)) - { - /* Case: \SystemRoot\System32\ , just directly load it */ - KdbSymProcessBootSymbols(AnsiFileName, TRUE, FALSE); - } - else if (RtlPrefixString(&RealPathPrefix, AnsiFileName, FALSE)) - { - /* It's prefixed with a real path, instead of a \SystemRoot. - So build a new, proper name. */ - RtlZeroMemory(Buffer, MAX_PATH); - strcpy(Buffer, "\SystemRoot"); - strncat(Buffer, - AnsiFileName->Buffer + RealPathPrefix.Length, - AnsiFileName->Length - RealPathPrefix.Length); - - /* Convert it to ANSI_STRING */ - RtlInitAnsiString(&ProperName, Buffer); - - /* Process symbols */ - KdbSymProcessBootSymbols(&ProperName, TRUE, TRUE); +KdbSymProcessSymbols(IN PANSI_STRING AnsiFileName, IN PKD_SYMBOLS_INFO SymbolInfo) +{ + BOOLEAN Found = FALSE; + PLIST_ENTRY ListHead, NextEntry; + PLDR_DATA_TABLE_ENTRY LdrEntry = NULL; + + //DPRINT("KdbSymProcessSymbols(%Z)\n", AnsiFileName); + + /* We use PsLoadedModuleList here, otherwise (in case of + using KeLoaderBlock) all our data will be just lost */ + ListHead = &PsLoadedModuleList; + + /* Found module we are interested in */ + NextEntry = ListHead->Flink; + while (ListHead != NextEntry) + { + /* Get the entry */ + LdrEntry = CONTAINING_RECORD(NextEntry, + LDR_DATA_TABLE_ENTRY, + InLoadOrderLinks); + + if (SymbolInfo->BaseOfDll == LdrEntry->DllBase) + { + Found = TRUE; + break; + } + + /* Go to the next one */ + NextEntry = NextEntry->Flink; + } + + /* Exit if we didn't find the module requested */ + if (!Found) + return; + + DPRINT("Found LdrEntry=%p\n", LdrEntry); + if (!LoadSymbols) + { + LdrEntry->PatchInformation = NULL; + return; + } + + /* Remove symbol info if it already exists */ + if (LdrEntry->PatchInformation != NULL) + { + KdbpSymRemoveCachedFile(LdrEntry->PatchInformation); + } + + /* Load new symbol information */ + if (! RosSymCreateFromMem(LdrEntry->DllBase, + LdrEntry->SizeOfImage, + (PROSSYM_INFO*)&LdrEntry->PatchInformation)) + { + /* Error loading symbol info, try to load it from file */ + KdbpSymLoadModuleSymbols(&LdrEntry->FullDllName, + (PROSSYM_INFO*)&LdrEntry->PatchInformation); + + /* It already added symbols to cache */ } else { - /* Just a bare filename, nothing else. Why? Who knows... */ - KdbSymProcessBootSymbols(AnsiFileName, FALSE, TRUE); - } + /* Add file to cache */ + KdbpSymAddCachedFile(&LdrEntry->FullDllName, LdrEntry->PatchInformation); + } + + DPRINT("Installed symbols: %wZ@%08x-%08x %p\n", + &LdrEntry->BaseDllName, + LdrEntry->DllBase, + LdrEntry->SizeOfImage + (ULONG)LdrEntry->DllBase, + LdrEntry->PatchInformation); + }