Author: ion
Date: Sun Jul 10 13:51:40 2011
New Revision: 52607
URL:
http://svn.reactos.org/svn/reactos?rev=52607&view=rev
Log:
[NTDLL]: Fix parsing and buffer overflow in LdrpLoadDll. Add more debug prints, and add
some missing code (commented out) for later.
Modified:
trunk/reactos/dll/ntdll/ldr/ldrutils.c
Modified: trunk/reactos/dll/ntdll/ldr/ldrutils.c
URL:
http://svn.reactos.org/svn/reactos/trunk/reactos/dll/ntdll/ldr/ldrutils.c?r…
==============================================================================
--- trunk/reactos/dll/ntdll/ldr/ldrutils.c [iso-8859-1] (original)
+++ trunk/reactos/dll/ntdll/ldr/ldrutils.c [iso-8859-1] Sun Jul 10 13:51:40 2011
@@ -16,6 +16,7 @@
/* GLOBALS *******************************************************************/
PLDR_DATA_TABLE_ENTRY LdrpLoadedDllHandleCache, LdrpGetModuleHandleCache;
+BOOLEAN g_ShimsEnabled;
/* FUNCTIONS *****************************************************************/
@@ -1849,6 +1850,7 @@
PPEB Peb = NtCurrentPeb();
NTSTATUS Status = STATUS_SUCCESS;
PWCHAR p1, p2;
+ WCHAR c;
WCHAR NameBuffer[266];
LPWSTR RawDllName;
UNICODE_STRING RawDllNameString;
@@ -1857,39 +1859,47 @@
/* Find the name without the extension */
p1 = DllName->Buffer;
-StartLoop:
p2 = NULL;
while (*p1)
{
- if (*p1++ == L'.')
+ c = *p1++;
+ if (c == L'.')
{
p2 = p1;
}
- else if (*p1 == L'\\')
- {
- goto StartLoop;
+ else if (c == L'\\')
+ {
+ p2 = NULL;
}
}
/* Save the Raw DLL Name */
RawDllName = NameBuffer;
- if (DllName->Length >= sizeof(NameBuffer))
- {
- /* The DLL's name is too long */
- return STATUS_NAME_TOO_LONG;
- }
+ if (DllName->Length >= sizeof(NameBuffer)) return STATUS_NAME_TOO_LONG;
RtlMoveMemory(RawDllName, DllName->Buffer, DllName->Length);
/* Check if no extension was found or if we got a slash */
- if (!p2 || *p2 == '\\')
+ if (!(p2) || (*p2 == '\\'))
{
/* Check that we have space to add one */
- if (DllName->Length + LdrApiDefaultExtension.Length >= sizeof(NameBuffer))
+ if ((DllName->Length + LdrApiDefaultExtension.Length + sizeof(UNICODE_NULL))
>=
+ sizeof(NameBuffer))
{
/* No space to add the extension */
+ DbgPrintEx(81, //DPFLTR_LDR_ID,
+ 0,
+ "LDR: %s - Dll name missing extension; with extension "
+ "added the name is too long\n"
+ " DllName: (@ %p) \"%wZ\"\n"
+ " DllName->Length: %u\n",
+ __FUNCTION__,
+ DllName,
+ DllName,
+ DllName->Length);
return STATUS_NAME_TOO_LONG;
}
+ /* FIXME: CLEAN THIS UP WITH Rtl String Functions */
/* Add it */
RtlMoveMemory((PVOID)((ULONG_PTR)RawDllName + DllName->Length),
LdrApiDefaultExtension.Buffer,
@@ -1941,16 +1951,18 @@
Redirected,
&LdrEntry);
if (!NT_SUCCESS(Status)) goto Quickie;
-
- /* Check if IMAGE_FILE_EXECUTABLE_IMAGE was provided */
- if (DllCharacteristics &&
- (*DllCharacteristics & IMAGE_FILE_EXECUTABLE_IMAGE))
- {
- LdrEntry->EntryPoint = NULL;
- LdrEntry->Flags &= ~LDRP_IMAGE_DLL;
- }
-
- /* FIXME Mark the DLL Ranges for Stack Traces later */
+
+ /* FIXME: Need to mark the DLL range for the stack DB */
+ //RtlpStkMarkDllRange(LdrEntry);
+
+ /* Check if IMAGE_FILE_EXECUTABLE_IMAGE was provided */
+ if ((DllCharacteristics) &&
+ (*DllCharacteristics & IMAGE_FILE_EXECUTABLE_IMAGE))
+ {
+ /* This is not a DLL, so remove such data */
+ LdrEntry->EntryPoint = NULL;
+ LdrEntry->Flags &= ~LDRP_IMAGE_DLL;
+ }
/* Make sure it's a DLL */
if (LdrEntry->Flags & LDRP_IMAGE_DLL)
@@ -1974,8 +1986,17 @@
InsertTailList(&Peb->Ldr->InInitializationOrderModuleList,
&LdrEntry->InInitializationOrderModuleList);
- /* Cancel the load and unload the DLL */
+ /* Cancel the load */
LdrpClearLoadInProgress();
+
+ /* Unload the DLL */
+ if (ShowSnaps)
+ {
+ DbgPrint("LDR: Unloading %wZ due to error %x walking "
+ "import descriptors",
+ DllName,
+ Status);
+ }
LdrUnloadDll(LdrEntry->DllBase);
/* Return the error */
@@ -1996,12 +2017,26 @@
if (CallInit && LdrpLdrDatabaseIsSetup)
{
/* FIXME: Notify Shim Engine */
-
+ if (g_ShimsEnabled)
+ {
+ /* Call it */
+ //ShimLoadCallback = RtlDecodeSystemPointer(g_pfnSE_DllLoaded);
+ //ShimLoadCallback(LdrEntry);
+ }
+
/* Run the init routine */
Status = LdrpRunInitializeRoutines(NULL);
if (!NT_SUCCESS(Status))
{
/* Failed, unload the DLL */
+ if (ShowSnaps)
+ {
+ DbgPrint("LDR: Unloading %wZ because either its init "
+ "routine or one of its static imports failed; "
+ "status = 0x%08lx\n",
+ DllName,
+ Status);
+ }
LdrUnloadDll(LdrEntry->DllBase);
}
}