mirror of
https://github.com/reactos/reactos.git
synced 2025-08-03 19:55:41 +00:00
- Get rid of the KDB_MODULE_INFO and operate with LDR_DATA_TABLE_ENTRYs directly.
This saves us from some copy steps and unneeded search operations. - Fix loading HAL.DLL symbols. This module is not guaranteed to be the second one in PsLoadedModuleList due to the kernel loading bootvid.dll. - Don't duplicate code in KdbpSymFindModule and KdbpSymFindUserModule. Use a helper function instead and call it twice from KdbpSymFindModule. - Get rid of KdbpSymFindModuleByAddress, KdbpSymFindModuleByName and KdbpSymFindModuleByIndex. Instead use a single KdbpSymFindModule for all three variants. - Remove some unused functions and defines. svn path=/trunk/; revision=43118
This commit is contained in:
parent
7f582de62c
commit
4842b49169
6 changed files with 83 additions and 408 deletions
|
@ -68,43 +68,15 @@ KdPortPutByteEx(
|
||||||
|
|
||||||
#if defined(KDBG) || DBG
|
#if defined(KDBG) || DBG
|
||||||
|
|
||||||
VOID
|
|
||||||
KdbSymLoadUserModuleSymbols(
|
|
||||||
IN PLDR_DATA_TABLE_ENTRY LdrModule);
|
|
||||||
|
|
||||||
VOID
|
|
||||||
KdbSymFreeProcessSymbols(
|
|
||||||
IN PEPROCESS Process);
|
|
||||||
|
|
||||||
VOID
|
|
||||||
KdbSymLoadDriverSymbols(
|
|
||||||
IN PUNICODE_STRING Filename,
|
|
||||||
IN PLDR_DATA_TABLE_ENTRY Module
|
|
||||||
);
|
|
||||||
|
|
||||||
VOID
|
|
||||||
KdbSymUnloadDriverSymbols(
|
|
||||||
IN PLDR_DATA_TABLE_ENTRY ModuleObject);
|
|
||||||
|
|
||||||
VOID
|
|
||||||
KdbSymProcessBootSymbols(
|
|
||||||
IN PANSI_STRING AnsiFileName,
|
|
||||||
IN BOOLEAN FullName,
|
|
||||||
IN BOOLEAN LoadFromFile);
|
|
||||||
|
|
||||||
VOID
|
VOID
|
||||||
KdbSymProcessSymbols(
|
KdbSymProcessSymbols(
|
||||||
IN PANSI_STRING FileName,
|
IN PLDR_DATA_TABLE_ENTRY LdrEntry);
|
||||||
IN PKD_SYMBOLS_INFO SymbolInfo);
|
|
||||||
|
|
||||||
BOOLEAN
|
BOOLEAN
|
||||||
KdbSymPrintAddress(
|
KdbSymPrintAddress(
|
||||||
IN PVOID Address);
|
IN PVOID Address);
|
||||||
|
|
||||||
VOID
|
|
||||||
KdbDeleteProcessHook(
|
|
||||||
IN PEPROCESS Process);
|
|
||||||
|
|
||||||
NTSTATUS
|
NTSTATUS
|
||||||
KdbSymGetAddressInformation(
|
KdbSymGetAddressInformation(
|
||||||
IN PROSSYM_INFO RosSymInfo,
|
IN PROSSYM_INFO RosSymInfo,
|
||||||
|
@ -113,46 +85,16 @@ KdbSymGetAddressInformation(
|
||||||
OUT PCH FileName OPTIONAL,
|
OUT PCH FileName OPTIONAL,
|
||||||
OUT PCH FunctionName OPTIONAL
|
OUT PCH FunctionName OPTIONAL
|
||||||
);
|
);
|
||||||
|
|
||||||
typedef struct _KDB_MODULE_INFO
|
|
||||||
{
|
|
||||||
WCHAR Name[256];
|
|
||||||
ULONG_PTR Base;
|
|
||||||
ULONG Size;
|
|
||||||
PROSSYM_INFO RosSymInfo;
|
|
||||||
}
|
|
||||||
KDB_MODULE_INFO, *PKDB_MODULE_INFO;
|
|
||||||
|
|
||||||
/* MACROS FOR NON-KDBG BUILDS ************************************************/
|
|
||||||
|
|
||||||
# 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, 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, SYMBOLINFO) do { } while (0)
|
|
||||||
# define KDB_CREATE_THREAD_HOOK(CONTEXT) do { } while (0)
|
|
||||||
#endif
|
|
||||||
|
|
||||||
#if defined(KDBG) || DBG
|
|
||||||
# define KeRosPrintAddress(ADDRESS) KdbSymPrintAddress(ADDRESS)
|
|
||||||
#else
|
|
||||||
# define KeRosPrintAddress(ADDRESS) KiRosPrintAddress(ADDRESS)
|
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#ifdef KDBG
|
#ifdef KDBG
|
||||||
# define KdbInit() KdbpCliInit()
|
# define KdbInit() KdbpCliInit()
|
||||||
# define KdbModuleLoaded(FILENAME) KdbpCliModuleLoaded(FILENAME)
|
# define KdbModuleLoaded(FILENAME) KdbpCliModuleLoaded(FILENAME)
|
||||||
# define KDB_DELETEPROCESS_HOOK(PROCESS) KdbDeleteProcessHook(PROCESS)
|
|
||||||
#else
|
#else
|
||||||
# define KdbEnterDebuggerException(ER, PM, C, TF, F) kdHandleException
|
# define KdbEnterDebuggerException(ER, PM, C, TF, F) kdHandleException
|
||||||
# define KdbInit() do { } while (0)
|
# define KdbInit() do { } while (0)
|
||||||
# define KdbEnter() do { } while (0)
|
# define KdbEnter() do { } while (0)
|
||||||
# define KdbModuleLoaded(X) do { } while (0)
|
# define KdbModuleLoaded(X) do { } while (0)
|
||||||
# define KDB_DELETEPROCESS_HOOK(PROCESS) do { } while (0)
|
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
/* KD ROUTINES ***************************************************************/
|
/* KD ROUTINES ***************************************************************/
|
||||||
|
|
|
@ -135,9 +135,13 @@ KdpEnterDebuggerException(IN PKTRAP_FRAME TrapFrame,
|
||||||
}
|
}
|
||||||
else if (ExceptionCommand == BREAKPOINT_LOAD_SYMBOLS)
|
else if (ExceptionCommand == BREAKPOINT_LOAD_SYMBOLS)
|
||||||
{
|
{
|
||||||
|
#ifdef KDBG
|
||||||
|
PLDR_DATA_TABLE_ENTRY LdrEntry;
|
||||||
|
|
||||||
/* Load symbols. Currently implemented only for KDBG! */
|
/* Load symbols. Currently implemented only for KDBG! */
|
||||||
KDB_SYMBOLFILE_HOOK((PANSI_STRING)ExceptionRecord->ExceptionInformation[1],
|
if(KdbpSymFindModule(((PKD_SYMBOLS_INFO)ExceptionRecord->ExceptionInformation[2])->BaseOfDll, NULL, -1, &LdrEntry))
|
||||||
(PKD_SYMBOLS_INFO)ExceptionRecord->ExceptionInformation[2]);
|
KdbSymProcessSymbols(LdrEntry);
|
||||||
|
#endif
|
||||||
}
|
}
|
||||||
|
|
||||||
/* This we can handle: simply bump EIP */
|
/* This we can handle: simply bump EIP */
|
||||||
|
|
|
@ -1677,15 +1677,6 @@ continue_execution:
|
||||||
return ContinueType;
|
return ContinueType;
|
||||||
}
|
}
|
||||||
|
|
||||||
VOID
|
|
||||||
KdbDeleteProcessHook(
|
|
||||||
IN PEPROCESS Process)
|
|
||||||
{
|
|
||||||
KdbSymFreeProcessSymbols(Process);
|
|
||||||
|
|
||||||
/* FIXME: Delete breakpoints for process */
|
|
||||||
}
|
|
||||||
|
|
||||||
VOID
|
VOID
|
||||||
NTAPI
|
NTAPI
|
||||||
KdbpGetCommandLineSettings(
|
KdbpGetCommandLineSettings(
|
||||||
|
|
|
@ -142,16 +142,11 @@ KdbpRpnEvaluateParsedExpression(
|
||||||
/* from kdb_symbols.c */
|
/* from kdb_symbols.c */
|
||||||
|
|
||||||
BOOLEAN
|
BOOLEAN
|
||||||
KdbpSymFindModuleByAddress(IN PVOID Address,
|
KdbpSymFindModule(
|
||||||
OUT PKDB_MODULE_INFO pInfo);
|
IN PVOID Address OPTIONAL,
|
||||||
|
IN LPCWSTR Name OPTIONAL,
|
||||||
BOOLEAN
|
IN INT Index OPTIONAL,
|
||||||
KdbpSymFindModuleByName(IN LPCWSTR Name,
|
OUT PLDR_DATA_TABLE_ENTRY* pLdrEntry);
|
||||||
OUT PKDB_MODULE_INFO pInfo);
|
|
||||||
|
|
||||||
BOOLEAN
|
|
||||||
KdbpSymFindModuleByIndex(IN INT Index,
|
|
||||||
OUT PKDB_MODULE_INFO pInfo);
|
|
||||||
|
|
||||||
/* from kdb.c */
|
/* from kdb.c */
|
||||||
|
|
||||||
|
|
|
@ -1476,7 +1476,7 @@ KdbpCmdMod(
|
||||||
{
|
{
|
||||||
ULONGLONG Result = 0;
|
ULONGLONG Result = 0;
|
||||||
ULONG_PTR Address;
|
ULONG_PTR Address;
|
||||||
KDB_MODULE_INFO Info;
|
PLDR_DATA_TABLE_ENTRY LdrEntry;
|
||||||
BOOLEAN DisplayOnlyOneModule = FALSE;
|
BOOLEAN DisplayOnlyOneModule = FALSE;
|
||||||
INT i = 0;
|
INT i = 0;
|
||||||
|
|
||||||
|
@ -1498,7 +1498,7 @@ KdbpCmdMod(
|
||||||
|
|
||||||
Address = (ULONG_PTR)Result;
|
Address = (ULONG_PTR)Result;
|
||||||
|
|
||||||
if (!KdbpSymFindModuleByAddress((PVOID)Address, &Info))
|
if (!KdbpSymFindModule((PVOID)Address, NULL, -1, &LdrEntry))
|
||||||
{
|
{
|
||||||
KdbpPrint("No module containing address 0x%p found!\n", Address);
|
KdbpPrint("No module containing address 0x%p found!\n", Address);
|
||||||
return TRUE;
|
return TRUE;
|
||||||
|
@ -1508,7 +1508,7 @@ KdbpCmdMod(
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
if (!KdbpSymFindModuleByIndex(0, &Info))
|
if (!KdbpSymFindModule(NULL, NULL, 0, &LdrEntry))
|
||||||
{
|
{
|
||||||
ULONG_PTR ntoskrnlBase = ((ULONG_PTR)KdbpCmdMod) & 0xfff00000;
|
ULONG_PTR ntoskrnlBase = ((ULONG_PTR)KdbpCmdMod) & 0xfff00000;
|
||||||
KdbpPrint(" Base Size Name\n");
|
KdbpPrint(" Base Size Name\n");
|
||||||
|
@ -1522,13 +1522,10 @@ KdbpCmdMod(
|
||||||
KdbpPrint(" Base Size Name\n");
|
KdbpPrint(" Base Size Name\n");
|
||||||
for (;;)
|
for (;;)
|
||||||
{
|
{
|
||||||
KdbpPrint(" %08x %08x %ws\n", Info.Base, Info.Size, Info.Name);
|
KdbpPrint(" %08x %08x %wZ\n", LdrEntry->DllBase, LdrEntry->SizeOfImage, &LdrEntry->BaseDllName);
|
||||||
|
|
||||||
if ((!DisplayOnlyOneModule && !KdbpSymFindModuleByIndex(i++, &Info)) ||
|
if(DisplayOnlyOneModule || !KdbpSymFindModule(NULL, NULL, i++, &LdrEntry))
|
||||||
DisplayOnlyOneModule)
|
|
||||||
{
|
|
||||||
break;
|
break;
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
return TRUE;
|
return TRUE;
|
||||||
|
|
|
@ -5,6 +5,7 @@
|
||||||
* PURPOSE: Getting symbol information...
|
* PURPOSE: Getting symbol information...
|
||||||
*
|
*
|
||||||
* PROGRAMMERS: David Welch (welch@cwcom.net)
|
* PROGRAMMERS: David Welch (welch@cwcom.net)
|
||||||
|
* Colin Finck (colin@reactos.org)
|
||||||
*/
|
*/
|
||||||
|
|
||||||
/* INCLUDES *****************************************************************/
|
/* INCLUDES *****************************************************************/
|
||||||
|
@ -32,60 +33,24 @@ BOOLEAN KdbpSymbolsInitialized = FALSE;
|
||||||
|
|
||||||
/* FUNCTIONS ****************************************************************/
|
/* FUNCTIONS ****************************************************************/
|
||||||
|
|
||||||
/*! \brief Find a user-mode module...
|
|
||||||
*
|
|
||||||
* \param Address If \a Address is not NULL the module containing \a Address
|
|
||||||
* is searched.
|
|
||||||
* \param Name If \a Name is not NULL the module named \a Name will be
|
|
||||||
* searched.
|
|
||||||
* \param Index If \a Index is >= 0 the Index'th module will be returned.
|
|
||||||
* \param pInfo Pointer to a KDB_MODULE_INFO which is filled.
|
|
||||||
*
|
|
||||||
* \retval TRUE Module was found, \a pInfo was filled.
|
|
||||||
* \retval FALSE No module was found.
|
|
||||||
*
|
|
||||||
* \sa KdbpSymFindModule
|
|
||||||
*/
|
|
||||||
static BOOLEAN
|
static BOOLEAN
|
||||||
KdbpSymFindUserModule(
|
KdbpSymSearchModuleList(
|
||||||
IN PVOID Address OPTIONAL,
|
IN PLIST_ENTRY current_entry,
|
||||||
IN LPCWSTR Name OPTIONAL,
|
IN PLIST_ENTRY end_entry,
|
||||||
IN INT Index OPTIONAL,
|
IN PLONG Count,
|
||||||
OUT PKDB_MODULE_INFO pInfo)
|
IN PVOID Address,
|
||||||
|
IN LPCWSTR Name,
|
||||||
|
IN INT Index,
|
||||||
|
OUT PLDR_DATA_TABLE_ENTRY* pLdrEntry)
|
||||||
{
|
{
|
||||||
PLIST_ENTRY current_entry;
|
while (current_entry && current_entry != end_entry)
|
||||||
PLDR_DATA_TABLE_ENTRY current;
|
|
||||||
PEPROCESS CurrentProcess;
|
|
||||||
PPEB Peb = NULL;
|
|
||||||
INT Count = 0;
|
|
||||||
INT Length;
|
|
||||||
|
|
||||||
if (!KdbpSymbolsInitialized)
|
|
||||||
return FALSE;
|
|
||||||
|
|
||||||
CurrentProcess = PsGetCurrentProcess();
|
|
||||||
if (CurrentProcess)
|
|
||||||
Peb = CurrentProcess->Peb;
|
|
||||||
|
|
||||||
if (!Peb || !Peb->Ldr)
|
|
||||||
return FALSE;
|
|
||||||
|
|
||||||
current_entry = Peb->Ldr->InLoadOrderModuleList.Flink;
|
|
||||||
|
|
||||||
while (current_entry != &Peb->Ldr->InLoadOrderModuleList && current_entry)
|
|
||||||
{
|
{
|
||||||
current = CONTAINING_RECORD(current_entry, LDR_DATA_TABLE_ENTRY, InLoadOrderLinks);
|
*pLdrEntry = CONTAINING_RECORD(current_entry, LDR_DATA_TABLE_ENTRY, InLoadOrderLinks);
|
||||||
Length = min(current->BaseDllName.Length / sizeof(WCHAR), 255);
|
|
||||||
if ((Address && (Address >= (PVOID)current->DllBase &&
|
if ((Address && Address >= (PVOID)(*pLdrEntry)->DllBase && Address < (PVOID)((ULONG_PTR)(*pLdrEntry)->DllBase + (*pLdrEntry)->SizeOfImage)) ||
|
||||||
Address < (PVOID)((char *)current->DllBase + current->SizeOfImage))) ||
|
(Name && !_wcsnicmp((*pLdrEntry)->BaseDllName.Buffer, Name, (*pLdrEntry)->BaseDllName.Length / sizeof(WCHAR))) ||
|
||||||
(Name && _wcsnicmp(current->BaseDllName.Buffer, Name, Length) == 0) ||
|
(Index >= 0 && (*Count)++ == Index))
|
||||||
(Index >= 0 && Count++ == Index))
|
|
||||||
{
|
{
|
||||||
wcsncpy(pInfo->Name, current->BaseDllName.Buffer, Length);
|
|
||||||
pInfo->Name[Length] = L'\0';
|
|
||||||
pInfo->Base = (ULONG_PTR)current->DllBase;
|
|
||||||
pInfo->Size = current->SizeOfImage;
|
|
||||||
pInfo->RosSymInfo = current->PatchInformation;
|
|
||||||
return TRUE;
|
return TRUE;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -95,111 +60,53 @@ KdbpSymFindUserModule(
|
||||||
return FALSE;
|
return FALSE;
|
||||||
}
|
}
|
||||||
|
|
||||||
/*! \brief Find a kernel-mode module...
|
/*! \brief Find a module...
|
||||||
*
|
*
|
||||||
* Works like \a KdbpSymFindUserModule.
|
* \param Address If \a Address is not NULL the module containing \a Address
|
||||||
|
* is searched.
|
||||||
|
* \param Name If \a Name is not NULL the module named \a Name will be
|
||||||
|
* searched.
|
||||||
|
* \param Index If \a Index is >= 0 the Index'th module will be returned.
|
||||||
|
* \param pLdrEntry Pointer to a PLDR_DATA_TABLE_ENTRY which is filled.
|
||||||
*
|
*
|
||||||
* \sa KdbpSymFindUserModule
|
* \retval TRUE Module was found, \a pLdrEntry was filled.
|
||||||
|
* \retval FALSE No module was found.
|
||||||
*/
|
*/
|
||||||
static BOOLEAN
|
BOOLEAN
|
||||||
KdbpSymFindModule(
|
KdbpSymFindModule(
|
||||||
IN PVOID Address OPTIONAL,
|
IN PVOID Address OPTIONAL,
|
||||||
IN LPCWSTR Name OPTIONAL,
|
IN LPCWSTR Name OPTIONAL,
|
||||||
IN INT Index OPTIONAL,
|
IN INT Index OPTIONAL,
|
||||||
OUT PKDB_MODULE_INFO pInfo)
|
OUT PLDR_DATA_TABLE_ENTRY* pLdrEntry)
|
||||||
{
|
{
|
||||||
PLIST_ENTRY current_entry;
|
LONG Count = 0;
|
||||||
PLDR_DATA_TABLE_ENTRY current;
|
PEPROCESS CurrentProcess;
|
||||||
INT Count = 0;
|
|
||||||
INT Length;
|
|
||||||
|
|
||||||
if (!KdbpSymbolsInitialized)
|
/* First try to look up the module in the kernel module list. */
|
||||||
return FALSE;
|
if(KdbpSymSearchModuleList(PsLoadedModuleList.Flink,
|
||||||
|
&PsLoadedModuleList,
|
||||||
current_entry = PsLoadedModuleList.Flink;
|
&Count,
|
||||||
|
Address,
|
||||||
while (current_entry != &PsLoadedModuleList)
|
Name,
|
||||||
|
Index,
|
||||||
|
pLdrEntry))
|
||||||
{
|
{
|
||||||
current = CONTAINING_RECORD(current_entry, LDR_DATA_TABLE_ENTRY, InLoadOrderLinks);
|
return TRUE;
|
||||||
|
|
||||||
Length = min(current->BaseDllName.Length / sizeof(WCHAR), 255);
|
|
||||||
if ((Address && (Address >= (PVOID)current->DllBase &&
|
|
||||||
Address < (PVOID)((ULONG_PTR)current->DllBase + current->SizeOfImage))) ||
|
|
||||||
(Name && _wcsnicmp(current->BaseDllName.Buffer, Name, Length) == 0) ||
|
|
||||||
(Index >= 0 && Count++ == Index))
|
|
||||||
{
|
|
||||||
wcsncpy(pInfo->Name, current->BaseDllName.Buffer, Length);
|
|
||||||
pInfo->Name[Length] = L'\0';
|
|
||||||
pInfo->Base = (ULONG_PTR)current->DllBase;
|
|
||||||
pInfo->Size = current->SizeOfImage;
|
|
||||||
pInfo->RosSymInfo = current->PatchInformation;
|
|
||||||
return TRUE;
|
|
||||||
}
|
|
||||||
|
|
||||||
current_entry = current_entry->Flink;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
return KdbpSymFindUserModule(Address, Name, Index-Count, pInfo);
|
/* That didn't succeed. Try the module list of the current process now. */
|
||||||
}
|
CurrentProcess = PsGetCurrentProcess();
|
||||||
|
|
||||||
/*! \brief Find module by address...
|
if(!CurrentProcess || !CurrentProcess->Peb || !CurrentProcess->Peb->Ldr)
|
||||||
*
|
return FALSE;
|
||||||
* \param Address Any address inside the module to look for.
|
|
||||||
* \param pInfo Pointer to a KDB_MODULE_INFO struct which is filled on
|
|
||||||
* success.
|
|
||||||
*
|
|
||||||
* \retval TRUE Success - module found.
|
|
||||||
* \retval FALSE Failure - module not found.
|
|
||||||
*
|
|
||||||
* \sa KdbpSymFindModuleByName
|
|
||||||
* \sa KdbpSymFindModuleByIndex
|
|
||||||
*/
|
|
||||||
BOOLEAN
|
|
||||||
KdbpSymFindModuleByAddress(
|
|
||||||
IN PVOID Address,
|
|
||||||
OUT PKDB_MODULE_INFO pInfo)
|
|
||||||
{
|
|
||||||
return KdbpSymFindModule(Address, NULL, -1, pInfo);
|
|
||||||
}
|
|
||||||
|
|
||||||
/*! \brief Find module by name...
|
return KdbpSymSearchModuleList(CurrentProcess->Peb->Ldr->InLoadOrderModuleList.Flink,
|
||||||
*
|
&CurrentProcess->Peb->Ldr->InLoadOrderModuleList,
|
||||||
* \param Name Name of the module to look for.
|
&Count,
|
||||||
* \param pInfo Pointer to a KDB_MODULE_INFO struct which is filled on
|
Address,
|
||||||
* success.
|
Name,
|
||||||
*
|
Index,
|
||||||
* \retval TRUE Success - module found.
|
pLdrEntry);
|
||||||
* \retval FALSE Failure - module not found.
|
|
||||||
*
|
|
||||||
* \sa KdbpSymFindModuleByAddress
|
|
||||||
* \sa KdbpSymFindModuleByIndex
|
|
||||||
*/
|
|
||||||
BOOLEAN
|
|
||||||
KdbpSymFindModuleByName(
|
|
||||||
IN LPCWSTR Name,
|
|
||||||
OUT PKDB_MODULE_INFO pInfo)
|
|
||||||
{
|
|
||||||
return KdbpSymFindModule(NULL, Name, -1, pInfo);
|
|
||||||
}
|
|
||||||
|
|
||||||
/*! \brief Find module by index...
|
|
||||||
*
|
|
||||||
* \param Index Index of the module to return.
|
|
||||||
* \param pInfo Pointer to a KDB_MODULE_INFO struct which is filled on
|
|
||||||
* success.
|
|
||||||
*
|
|
||||||
* \retval TRUE Success - module found.
|
|
||||||
* \retval FALSE Failure - module not found.
|
|
||||||
*
|
|
||||||
* \sa KdbpSymFindModuleByName
|
|
||||||
* \sa KdbpSymFindModuleByAddress
|
|
||||||
*/
|
|
||||||
BOOLEAN
|
|
||||||
KdbpSymFindModuleByIndex(
|
|
||||||
IN INT Index,
|
|
||||||
OUT PKDB_MODULE_INFO pInfo)
|
|
||||||
{
|
|
||||||
return KdbpSymFindModule(NULL, NULL, Index, pInfo);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/*! \brief Print address...
|
/*! \brief Print address...
|
||||||
|
@ -217,30 +124,30 @@ BOOLEAN
|
||||||
KdbSymPrintAddress(
|
KdbSymPrintAddress(
|
||||||
IN PVOID Address)
|
IN PVOID Address)
|
||||||
{
|
{
|
||||||
KDB_MODULE_INFO Info;
|
PLDR_DATA_TABLE_ENTRY LdrEntry;
|
||||||
ULONG_PTR RelativeAddress;
|
ULONG_PTR RelativeAddress;
|
||||||
NTSTATUS Status;
|
NTSTATUS Status;
|
||||||
ULONG LineNumber;
|
ULONG LineNumber;
|
||||||
CHAR FileName[256];
|
CHAR FileName[256];
|
||||||
CHAR FunctionName[256];
|
CHAR FunctionName[256];
|
||||||
|
|
||||||
if (!KdbpSymbolsInitialized || !KdbpSymFindModuleByAddress(Address, &Info))
|
if (!KdbpSymbolsInitialized || !KdbpSymFindModule(Address, NULL, -1, &LdrEntry))
|
||||||
return FALSE;
|
return FALSE;
|
||||||
|
|
||||||
RelativeAddress = (ULONG_PTR) Address - Info.Base;
|
RelativeAddress = (ULONG_PTR)Address - (ULONG_PTR)LdrEntry->DllBase;
|
||||||
Status = KdbSymGetAddressInformation(Info.RosSymInfo,
|
Status = KdbSymGetAddressInformation(LdrEntry->PatchInformation,
|
||||||
RelativeAddress,
|
RelativeAddress,
|
||||||
&LineNumber,
|
&LineNumber,
|
||||||
FileName,
|
FileName,
|
||||||
FunctionName);
|
FunctionName);
|
||||||
if (NT_SUCCESS(Status))
|
if (NT_SUCCESS(Status))
|
||||||
{
|
{
|
||||||
DbgPrint("<%ws:%x (%s:%d (%s))>",
|
DbgPrint("<%wZ:%x (%s:%d (%s))>",
|
||||||
Info.Name, RelativeAddress, FileName, LineNumber, FunctionName);
|
&LdrEntry->BaseDllName, RelativeAddress, FileName, LineNumber, FunctionName);
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
DbgPrint("<%ws:%x>", Info.Name, RelativeAddress);
|
DbgPrint("<%wZ:%x>", &LdrEntry->BaseDllName, RelativeAddress);
|
||||||
}
|
}
|
||||||
|
|
||||||
return TRUE;
|
return TRUE;
|
||||||
|
@ -480,156 +387,10 @@ KdbpSymLoadModuleSymbols(
|
||||||
DPRINT("Installed symbols: %wZ %p\n", FileName, *RosSymInfo);
|
DPRINT("Installed symbols: %wZ %p\n", FileName, *RosSymInfo);
|
||||||
}
|
}
|
||||||
|
|
||||||
/*! \brief Unloads symbol info.
|
|
||||||
*
|
|
||||||
* \param RosSymInfo Pointer to the symbol info to unload.
|
|
||||||
*
|
|
||||||
* \sa KdbpSymLoadModuleSymbols
|
|
||||||
*/
|
|
||||||
static VOID
|
|
||||||
KdbpSymUnloadModuleSymbols(
|
|
||||||
IN PROSSYM_INFO RosSymInfo)
|
|
||||||
{
|
|
||||||
DPRINT("Unloading symbols\n");
|
|
||||||
|
|
||||||
if (RosSymInfo)
|
|
||||||
KdbpSymRemoveCachedFile(RosSymInfo);
|
|
||||||
}
|
|
||||||
|
|
||||||
/*! \brief Load symbol info for a user module.
|
|
||||||
*
|
|
||||||
* \param LdrModule Pointer to the module to load symbols for.
|
|
||||||
*/
|
|
||||||
VOID
|
|
||||||
KdbSymLoadUserModuleSymbols(
|
|
||||||
IN PLDR_DATA_TABLE_ENTRY LdrModule)
|
|
||||||
{
|
|
||||||
static WCHAR Prefix[] = L"\\??\\";
|
|
||||||
UNICODE_STRING KernelName;
|
|
||||||
DPRINT("LdrModule %p\n", LdrModule);
|
|
||||||
|
|
||||||
LdrModule->PatchInformation = NULL;
|
|
||||||
|
|
||||||
KernelName.MaximumLength = sizeof(Prefix) + LdrModule->FullDllName.Length;
|
|
||||||
KernelName.Length = KernelName.MaximumLength - sizeof(WCHAR);
|
|
||||||
KernelName.Buffer = ExAllocatePoolWithTag(NonPagedPool, KernelName.MaximumLength, TAG_KDBS);
|
|
||||||
|
|
||||||
if (!KernelName.Buffer)
|
|
||||||
return;
|
|
||||||
|
|
||||||
memcpy(KernelName.Buffer, Prefix, sizeof(Prefix) - sizeof(WCHAR));
|
|
||||||
memcpy(KernelName.Buffer + sizeof(Prefix) / sizeof(WCHAR) - 1, LdrModule->FullDllName.Buffer, LdrModule->FullDllName.Length);
|
|
||||||
KernelName.Buffer[KernelName.Length / sizeof(WCHAR)] = L'\0';
|
|
||||||
|
|
||||||
KdbpSymLoadModuleSymbols(&KernelName, (PROSSYM_INFO*)&LdrModule->PatchInformation);
|
|
||||||
|
|
||||||
ExFreePool(KernelName.Buffer);
|
|
||||||
}
|
|
||||||
|
|
||||||
/*! \brief Frees all symbols loaded for a process.
|
|
||||||
*
|
|
||||||
* \param Process Pointer to a process.
|
|
||||||
*/
|
|
||||||
VOID
|
|
||||||
KdbSymFreeProcessSymbols(
|
|
||||||
IN PEPROCESS Process)
|
|
||||||
{
|
|
||||||
PLIST_ENTRY CurrentEntry;
|
|
||||||
PLDR_DATA_TABLE_ENTRY Current;
|
|
||||||
PEPROCESS CurrentProcess;
|
|
||||||
PPEB Peb;
|
|
||||||
|
|
||||||
CurrentProcess = PsGetCurrentProcess();
|
|
||||||
if (CurrentProcess != Process)
|
|
||||||
KeAttachProcess(&Process->Pcb);
|
|
||||||
|
|
||||||
Peb = Process->Peb;
|
|
||||||
ASSERT(Peb);
|
|
||||||
ASSERT(Peb->Ldr);
|
|
||||||
|
|
||||||
CurrentEntry = Peb->Ldr->InLoadOrderModuleList.Flink;
|
|
||||||
while (CurrentEntry != &Peb->Ldr->InLoadOrderModuleList && CurrentEntry)
|
|
||||||
{
|
|
||||||
Current = CONTAINING_RECORD(CurrentEntry, LDR_DATA_TABLE_ENTRY, InLoadOrderLinks);
|
|
||||||
KdbpSymUnloadModuleSymbols(Current->PatchInformation);
|
|
||||||
|
|
||||||
CurrentEntry = CurrentEntry->Flink;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (CurrentProcess != Process)
|
|
||||||
KeDetachProcess();
|
|
||||||
}
|
|
||||||
|
|
||||||
/*! \brief Load symbol info for a driver.
|
|
||||||
*
|
|
||||||
* \param Filename Filename of the driver.
|
|
||||||
* \param Module Pointer to the driver LDR_DATA_TABLE_ENTRY.
|
|
||||||
*/
|
|
||||||
VOID
|
|
||||||
KdbSymLoadDriverSymbols(
|
|
||||||
IN PUNICODE_STRING Filename,
|
|
||||||
IN PLDR_DATA_TABLE_ENTRY Module)
|
|
||||||
{
|
|
||||||
/* Load symbols for the image if available */
|
|
||||||
DPRINT("Loading driver %wZ symbols (driver @ %08x)\n", Filename, Module->DllBase);
|
|
||||||
|
|
||||||
Module->PatchInformation = NULL;
|
|
||||||
|
|
||||||
KdbpSymLoadModuleSymbols(Filename, (PROSSYM_INFO*)&Module->PatchInformation);
|
|
||||||
}
|
|
||||||
|
|
||||||
/*! \brief Unloads symbol info for a driver.
|
|
||||||
*
|
|
||||||
* \param ModuleObject Pointer to the driver LDR_DATA_TABLE_ENTRY.
|
|
||||||
*/
|
|
||||||
VOID
|
|
||||||
KdbSymUnloadDriverSymbols(
|
|
||||||
IN PLDR_DATA_TABLE_ENTRY ModuleObject)
|
|
||||||
{
|
|
||||||
/* Unload symbols for module if available */
|
|
||||||
KdbpSymUnloadModuleSymbols(ModuleObject->PatchInformation);
|
|
||||||
ModuleObject->PatchInformation = NULL;
|
|
||||||
}
|
|
||||||
|
|
||||||
VOID
|
VOID
|
||||||
KdbSymProcessSymbols(
|
KdbSymProcessSymbols(
|
||||||
IN PANSI_STRING AnsiFileName,
|
IN PLDR_DATA_TABLE_ENTRY LdrEntry)
|
||||||
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)
|
if (!LoadSymbols)
|
||||||
{
|
{
|
||||||
LdrEntry->PatchInformation = NULL;
|
LdrEntry->PatchInformation = NULL;
|
||||||
|
@ -689,9 +450,7 @@ KdbInitialize(
|
||||||
PCHAR p1, p2;
|
PCHAR p1, p2;
|
||||||
SHORT Found = FALSE;
|
SHORT Found = FALSE;
|
||||||
CHAR YesNo;
|
CHAR YesNo;
|
||||||
LIST_ENTRY *ModuleEntry;
|
PLDR_DATA_TABLE_ENTRY LdrEntry;
|
||||||
PLDR_DATA_TABLE_ENTRY DataTableEntry;
|
|
||||||
KD_SYMBOLS_INFO SymbolsInfo;
|
|
||||||
|
|
||||||
DPRINT("KdbSymInit() BootPhase=%d\n", BootPhase);
|
DPRINT("KdbSymInit() BootPhase=%d\n", BootPhase);
|
||||||
|
|
||||||
|
@ -765,29 +524,16 @@ KdbInitialize(
|
||||||
}
|
}
|
||||||
else if (BootPhase == 1)
|
else if (BootPhase == 1)
|
||||||
{
|
{
|
||||||
/* Load symbols for NTOSKRNL.EXE */
|
/* Load symbols for NTOSKRNL.EXE.
|
||||||
ModuleEntry = &KeLoaderBlock->LoadOrderListHead;
|
It is always the first module in PsLoadedModuleList. KeLoaderBlock can't be used here as its content is just temporary. */
|
||||||
DataTableEntry = CONTAINING_RECORD(ModuleEntry,
|
LdrEntry = CONTAINING_RECORD(PsLoadedModuleList.Flink, LDR_DATA_TABLE_ENTRY, InLoadOrderLinks);
|
||||||
LDR_DATA_TABLE_ENTRY, InLoadOrderLinks);
|
KdbSymProcessSymbols(LdrEntry);
|
||||||
|
|
||||||
SymbolsInfo.BaseOfDll = DataTableEntry->DllBase;
|
/* Also load them for HAL.DLL.
|
||||||
SymbolsInfo.CheckSum = DataTableEntry->CheckSum;
|
This module has no fixed position, so search for it. */
|
||||||
SymbolsInfo.ProcessId = 0;
|
if(KdbpSymFindModule(NULL, L"HAL.DLL", -1, &LdrEntry))
|
||||||
SymbolsInfo.SizeOfImage = DataTableEntry->SizeOfImage;
|
KdbSymProcessSymbols(LdrEntry);
|
||||||
|
|
||||||
KdbSymProcessSymbols(NULL, &SymbolsInfo);
|
|
||||||
|
|
||||||
/* and HAL.DLL */
|
|
||||||
ModuleEntry = ModuleEntry->Flink;
|
|
||||||
DataTableEntry = CONTAINING_RECORD(ModuleEntry,
|
|
||||||
LDR_DATA_TABLE_ENTRY, InLoadOrderLinks);
|
|
||||||
|
|
||||||
SymbolsInfo.BaseOfDll = DataTableEntry->DllBase;
|
|
||||||
SymbolsInfo.CheckSum = DataTableEntry->CheckSum;
|
|
||||||
SymbolsInfo.ProcessId = 0;
|
|
||||||
SymbolsInfo.SizeOfImage = DataTableEntry->SizeOfImage;
|
|
||||||
|
|
||||||
KdbSymProcessSymbols(NULL, &SymbolsInfo);
|
|
||||||
KdbpSymbolsInitialized = TRUE;
|
KdbpSymbolsInitialized = TRUE;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue