Author: tkreuzer Date: Wed Nov 12 09:24:40 2008 New Revision: 37308
URL: http://svn.reactos.org/svn/reactos?rev=37308&view=rev Log: Implement RtlLookupFunctionTable, RtlLookupFunctionEntry and a usermode/kernelmode version of RtlpLookupModuleBase helper function.
Added: branches/ros-amd64-bringup/reactos/lib/rtl/amd64/unwind.c (with props) Modified: branches/ros-amd64-bringup/reactos/dll/ntdll/rtl/libsupp.c branches/ros-amd64-bringup/reactos/lib/rtl/amd64/stubs.c branches/ros-amd64-bringup/reactos/lib/rtl/rtl.rbuild branches/ros-amd64-bringup/reactos/ntoskrnl/amd64stubs.c branches/ros-amd64-bringup/reactos/ntoskrnl/include/internal/ke.h branches/ros-amd64-bringup/reactos/ntoskrnl/rtl/libsupp.c
Modified: branches/ros-amd64-bringup/reactos/dll/ntdll/rtl/libsupp.c URL: http://svn.reactos.org/svn/reactos/branches/ros-amd64-bringup/reactos/dll/nt... ============================================================================== --- branches/ros-amd64-bringup/reactos/dll/ntdll/rtl/libsupp.c [iso-8859-1] (original) +++ branches/ros-amd64-bringup/reactos/dll/ntdll/rtl/libsupp.c [iso-8859-1] Wed Nov 12 09:24:40 2008 @@ -14,6 +14,8 @@ #include <debug.h>
SIZE_T RtlpAllocDeallocQueryBufferSize = PAGE_SIZE; +#define IMAGE_DOS_MAGIC 0x5a4d +#define IMAGE_PE_MAGIC 0x00004550
/* FUNCTIONS ***************************************************************/
@@ -356,6 +358,62 @@ }
return NULL; +} + +PVOID +NTAPI +RtlpLookupModuleBase( + PVOID Address) +{ + NTSTATUS Status; + MEMORY_BASIC_INFORMATION MemoryInformation; + ULONG_PTR Base, Limit; + PIMAGE_DOS_HEADER DosHeader; + PIMAGE_NT_HEADERS NtHeader; + + Status = NtQueryVirtualMemory(NtCurrentProcess(), + Address, + MemoryBasicInformation, + &MemoryInformation, + sizeof(MEMORY_BASIC_INFORMATION), + NULL); + if (!NT_SUCCESS(Status)) + { + return NULL; + } + + /* FIXME: remove these checks? */ + Base = (ULONG_PTR)MemoryInformation.BaseAddress; + Limit = Base + MemoryInformation.RegionSize; + if ( ((ULONG_PTR)Address < Base) || + ((ULONG_PTR)Address >= Limit) ) + { + /* WTF? */ + return NULL; + } + + /* Check if we got the right kind of memory */ + if ( (MemoryInformation.State != MEM_COMMIT) || + (MemoryInformation.Type != MEM_IMAGE) ) + { + return NULL; + } + + /* Check DOS magic */ + DosHeader = MemoryInformation.AllocationBase; + if (DosHeader->e_magic != IMAGE_DOS_MAGIC) + { + return NULL; + } + + /* Check NT header */ + NtHeader = (PVOID)((ULONG_PTR)DosHeader + DosHeader->e_lfanew); + if (NtHeader->Signature != IMAGE_PE_MAGIC) + { + return NULL; + } + + return MemoryInformation.AllocationBase; }
Modified: branches/ros-amd64-bringup/reactos/lib/rtl/amd64/stubs.c URL: http://svn.reactos.org/svn/reactos/branches/ros-amd64-bringup/reactos/lib/rt... ============================================================================== --- branches/ros-amd64-bringup/reactos/lib/rtl/amd64/stubs.c [iso-8859-1] (original) +++ branches/ros-amd64-bringup/reactos/lib/rtl/amd64/stubs.c [iso-8859-1] Wed Nov 12 09:24:40 2008 @@ -13,19 +13,6 @@ #include <debug.h>
/* PUBLIC FUNCTIONS **********************************************************/ - -/* - * @unimplemented - */ -PVOID -NTAPI -RtlLookupFunctionEntry(IN ULONGLONG ControlPC, - OUT PULONGLONG ImageBase, - OUT PULONGLONG TargetGp) -{ - UNIMPLEMENTED; - return NULL; -}
/* * @unimplemented
Added: branches/ros-amd64-bringup/reactos/lib/rtl/amd64/unwind.c URL: http://svn.reactos.org/svn/reactos/branches/ros-amd64-bringup/reactos/lib/rt... ============================================================================== --- branches/ros-amd64-bringup/reactos/lib/rtl/amd64/unwind.c (added) +++ branches/ros-amd64-bringup/reactos/lib/rtl/amd64/unwind.c [iso-8859-1] Wed Nov 12 09:24:40 2008 @@ -1,0 +1,153 @@ +/* COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS system libraries + * PURPOSE: Exception related functions + * PROGRAMMER: Timo Kreuzer + */ + +/* INCLUDES *****************************************************************/ + +#include <rtl.h> + +#define NDEBUG +#include <debug.h> + +#define UNWIND_HISTORY_TABLE_NONE 0 +#define UNWIND_HISTORY_TABLE_GLOBAL 1 +#define UNWIND_HISTORY_TABLE_LOCAL 2 + +PVOID +NTAPI +RtlpLookupModuleBase( + PVOID Address); + +/* FUNCTIONS *****************************************************************/ + +PRUNTIME_FUNCTION +NTAPI +RtlLookupFunctionTable( + IN DWORD64 ControlPc, + OUT PDWORD64 ImageBase, + OUT PULONG Length) +{ + PIMAGE_DOS_HEADER DosHeader; + PIMAGE_NT_HEADERS NtHeader; + PIMAGE_DATA_DIRECTORY Directory; + + /* Find ModuleBase */ + DosHeader = RtlpLookupModuleBase((PVOID)ControlPc); + if (!DosHeader) + { + return NULL; + } + + /* Locate NT header and check number of directories */ + NtHeader = (PVOID)((ULONG64)DosHeader + DosHeader->e_lfanew); + if (NtHeader->OptionalHeader.NumberOfRvaAndSizes + < IMAGE_DIRECTORY_ENTRY_EXCEPTION) + { + return NULL; + } + + /* Locate the exception directory */ + Directory = &NtHeader->OptionalHeader.DataDirectory[IMAGE_DIRECTORY_ENTRY_EXCEPTION]; + *Length = Directory->Size / sizeof(RUNTIME_FUNCTION); + *ImageBase = (ULONG64)DosHeader; + if (!Directory->VirtualAddress) + { + return NULL; + } + + return (PVOID)((ULONG64)DosHeader + Directory->VirtualAddress); +} + + +// http://msdn.microsoft.com/en-us/library/ms680597(VS.85).aspx +PRUNTIME_FUNCTION +NTAPI +RtlLookupFunctionEntry( + IN DWORD64 ControlPc, + OUT PDWORD64 ImageBase, + OUT PUNWIND_HISTORY_TABLE HistoryTable) +{ + PRUNTIME_FUNCTION FunctionTable, FunctionEntry; + ULONG TableLength; + ULONG IndexLo, IndexHi, IndexMid; + + /* Find the corresponding table */ + FunctionTable = RtlLookupFunctionTable(ControlPc, + ImageBase, + &TableLength); + + /* Fail, if no table is found */ + if (!FunctionTable) + { + return (PVOID)1; + } + + /* Use relative virtual address */ + ControlPc -= *ImageBase; + + /* Do a binary search */ + IndexLo = 0; + IndexHi = TableLength; + + while (IndexHi > IndexLo) + { + IndexMid = (IndexLo + IndexHi) / 2; + FunctionEntry = &FunctionTable[IndexMid]; + + if ( (ControlPc >= FunctionEntry->BeginAddress) && + (ControlPc < FunctionEntry->EndAddress) ) + { + /* ControlPc is within limits, return entry */ + return FunctionEntry; + } + + if (ControlPc < FunctionEntry->BeginAddress) + { + /* Continue search in lower half */ + IndexHi = IndexMid; + } + else + { + /* Continue search in upper half */ + IndexLo = IndexMid + 1; + } + } + + /* Nothing found, return NULL */ + return NULL; +} + + +PEXCEPTION_ROUTINE +NTAPI +RtlVirtualUnwind( + IN ULONG HandlerType, + IN ULONG64 ImageBase, + IN ULONG64 ControlPc, + IN PRUNTIME_FUNCTION FunctionEntry, + IN OUT PCONTEXT ContextRecord, + OUT PVOID *HandlerData, + OUT PULONG64 EstablisherFrame, + IN OUT PKNONVOLATILE_CONTEXT_POINTERS ContextPointers) +{ + UNIMPLEMENTED; + return 0; +} + +VOID +NTAPI +RtlUnwindEx( + IN ULONG64 TargetFrame, + IN ULONG64 TargetIp, + IN PEXCEPTION_RECORD ExceptionRecord, + IN PVOID ReturnValue, + OUT PCONTEXT OriginalContext, + IN PUNWIND_HISTORY_TABLE HistoryTable) +{ + UNIMPLEMENTED; + return; +} + +
Propchange: branches/ros-amd64-bringup/reactos/lib/rtl/amd64/unwind.c ------------------------------------------------------------------------------ svn:eol-style = native
Propchange: branches/ros-amd64-bringup/reactos/lib/rtl/amd64/unwind.c ------------------------------------------------------------------------------ svn:mergeinfo =
Modified: branches/ros-amd64-bringup/reactos/lib/rtl/rtl.rbuild URL: http://svn.reactos.org/svn/reactos/branches/ros-amd64-bringup/reactos/lib/rt... ============================================================================== --- branches/ros-amd64-bringup/reactos/lib/rtl/rtl.rbuild [iso-8859-1] (original) +++ branches/ros-amd64-bringup/reactos/lib/rtl/rtl.rbuild [iso-8859-1] Wed Nov 12 09:24:40 2008 @@ -39,6 +39,7 @@ <if property="ARCH" value="amd64"> <directory name="amd64"> <file>debug_asm.S</file> + <file>unwind.c</file> <file>stubs.c</file> </directory> <file>mem.c</file>
Modified: branches/ros-amd64-bringup/reactos/ntoskrnl/amd64stubs.c URL: http://svn.reactos.org/svn/reactos/branches/ros-amd64-bringup/reactos/ntoskr... ============================================================================== --- branches/ros-amd64-bringup/reactos/ntoskrnl/amd64stubs.c [iso-8859-1] (original) +++ branches/ros-amd64-bringup/reactos/ntoskrnl/amd64stubs.c [iso-8859-1] Wed Nov 12 09:24:40 2008 @@ -68,14 +68,10 @@ STUB(KdpGdbStubInit) STUB(KdbpSafeReadMemory) STUB(RtlFillMemoryUlong) -STUB(RtlCaptureContext) -STUB(RtlpGetExceptionAddress) -STUB(RtlDispatchException) STUB(DbgkDebugObjectType) STUB(KdbEnterDebuggerException) STUB(KdbpCliModuleLoaded) STUB(RtlUnwind) -STUB(RtlInitializeContext) STUB(DbgCommandString) STUB(ExAcquireRundownProtection) STUB(ExAcquireRundownProtectionCacheAware) @@ -180,7 +176,6 @@ STUB(RtlCopyMemory) STUB(RtlCopyMemoryNonTemporal) STUB(RtlFillMemory) -STUB(RtlLookupFunctionEntry) STUB(RtlMoveMemory) STUB(RtlOemStringToUnicodeSize) STUB(RtlPcToFileHeader) @@ -196,8 +191,6 @@ STUB(RtlTraceDatabaseValidate) STUB(RtlUnicodeStringToAnsiSize) STUB(RtlUnicodeStringToOemSize) -STUB(RtlUnwindEx) -STUB(RtlVirtualUnwind) STUB(RtlZeroMemory) STUB(SeReportSecurityEvent) STUB(SeSetAuditParameter)
Modified: branches/ros-amd64-bringup/reactos/ntoskrnl/include/internal/ke.h URL: http://svn.reactos.org/svn/reactos/branches/ros-amd64-bringup/reactos/ntoskr... ============================================================================== --- branches/ros-amd64-bringup/reactos/ntoskrnl/include/internal/ke.h [iso-8859-1] (original) +++ branches/ros-amd64-bringup/reactos/ntoskrnl/include/internal/ke.h [iso-8859-1] Wed Nov 12 09:24:40 2008 @@ -1047,6 +1047,18 @@ VOID );
+PVOID +NTAPI +KiPcToFileHeader(IN PVOID Eip, + OUT PLDR_DATA_TABLE_ENTRY *LdrEntry, + IN BOOLEAN DriversOnly, + OUT PBOOLEAN InKernel); + +PVOID +NTAPI +KiRosPcToUserFileHeader(IN PVOID Eip, + OUT PLDR_DATA_TABLE_ENTRY *LdrEntry); + #include "ke_x.h"
#endif /* __NTOSKRNL_INCLUDE_INTERNAL_KE_H */
Modified: branches/ros-amd64-bringup/reactos/ntoskrnl/rtl/libsupp.c URL: http://svn.reactos.org/svn/reactos/branches/ros-amd64-bringup/reactos/ntoskr... ============================================================================== --- branches/ros-amd64-bringup/reactos/ntoskrnl/rtl/libsupp.c [iso-8859-1] (original) +++ branches/ros-amd64-bringup/reactos/ntoskrnl/rtl/libsupp.c [iso-8859-1] Wed Nov 12 09:24:40 2008 @@ -27,6 +27,30 @@ SIZE_T RtlpAllocDeallocQueryBufferSize = 128;
/* FUNCTIONS *****************************************************************/ + +PVOID +NTAPI +RtlpLookupModuleBase( + PVOID Address) +{ + PLDR_DATA_TABLE_ENTRY LdrEntry; + BOOLEAN InSystem; + PVOID p; + + /* Get the base for this file */ + if ((ULONG_PTR)Address > (ULONG_PTR)MmHighestUserAddress) + { + /* We are in kernel */ + p = KiPcToFileHeader(Address, &LdrEntry, FALSE, &InSystem); + } + else + { + /* We are in user land */ + p = KiRosPcToUserFileHeader(Address, &LdrEntry); + } + + return p; +}
VOID NTAPI