[ros-diffs] [ion] 25874: - Improve LdrGetModuleObject (in FreeLDR) to handle partial names too, so NTOSKRNL will still match NTOSKRNL.EXE. This is needed for forwarder support. - Implement LdrPEFixupForward in FreeLDR and update LdrPEGetExportByName to use it, so that FreeLDR can now parse import tables with forwarders. - Add call to MmInitSystem for Phase 0 in ExpInitializeExecutive. - Completely redesign the way boot drivers are handled. They're now re-mapped during Phase 0 MmInit (part of the re-mapping is a hack until FreeLDR 2.5 is ready) and the IoMgr only does I/O stuff, not PE loading anymore (this is only half-true, we still process imports until FreeLDR 2.5 is done). - Also re-design the way the module list head is initialized and used. LdrInit1 is now gone, Phase 0 MmInit now handles initializing it and copying boot loader data to it. - Some code is still missing and functions still need to be improved. - When FreeLDR 2.5 is ready some of the hacks will go away, they're #ifed for now to make it easy to switch.

ion at svn.reactos.org ion at svn.reactos.org
Thu Feb 22 19:02:54 CET 2007


Author: ion
Date: Thu Feb 22 21:02:53 2007
New Revision: 25874

URL: http://svn.reactos.org/svn/reactos?rev=25874&view=rev
Log:
- Improve LdrGetModuleObject (in FreeLDR) to handle partial names too, so NTOSKRNL will still match NTOSKRNL.EXE. This is needed for forwarder support.
- Implement LdrPEFixupForward in FreeLDR and update LdrPEGetExportByName to use it, so that FreeLDR can now parse import tables with forwarders.
- Add call to MmInitSystem for Phase 0 in ExpInitializeExecutive.
- Completely redesign the way boot drivers are handled. They're now re-mapped during Phase 0 MmInit (part of the re-mapping is a hack until FreeLDR 2.5 is ready) and the IoMgr only does I/O stuff, not PE loading anymore (this is only half-true, we still process imports until FreeLDR 2.5 is done).
- Also re-design the way the module list head is initialized and used. LdrInit1 is now gone, Phase 0 MmInit now handles initializing it and copying boot loader data to it.
- Some code is still missing and functions still need to be improved.
- When FreeLDR 2.5 is ready some of the hacks will go away, they're #ifed for now to make it easy to switch.

Modified:
    trunk/reactos/boot/freeldr/freeldr/arch/i386/loader.c
    trunk/reactos/ntoskrnl/ex/init.c
    trunk/reactos/ntoskrnl/include/internal/ex.h
    trunk/reactos/ntoskrnl/include/internal/mm.h
    trunk/reactos/ntoskrnl/io/iomgr/driver.c
    trunk/reactos/ntoskrnl/ke/i386/kiinit.c
    trunk/reactos/ntoskrnl/ldr/loader.c
    trunk/reactos/ntoskrnl/mm/mminit.c
    trunk/reactos/ntoskrnl/mm/sysldr.c

Modified: trunk/reactos/boot/freeldr/freeldr/arch/i386/loader.c
URL: http://svn.reactos.org/svn/reactos/trunk/reactos/boot/freeldr/freeldr/arch/i386/loader.c?rev=25874&r1=25873&r2=25874&view=diff
==============================================================================
--- trunk/reactos/boot/freeldr/freeldr/arch/i386/loader.c (original)
+++ trunk/reactos/boot/freeldr/freeldr/arch/i386/loader.c Thu Feb 22 21:02:53 2007
@@ -127,6 +127,12 @@
                IN INT nPos,
                IN BOOLEAN IsKernel);
 
+PVOID
+NTAPI
+LdrPEGetExportByName(PVOID BaseAddress,
+                     PUCHAR SymbolName,
+                     USHORT Hint);
+
 /* FUNCTIONS *****************************************************************/
 
 /*++
@@ -300,6 +306,46 @@
     PageDir->Pde[0].PageFrameNumber = 1;
 }
 
+PLOADER_MODULE
+NTAPI
+LdrGetModuleObject(PCHAR ModuleName)
+{
+    ULONG i;
+
+    for (i = 0; i < LoaderBlock.ModsCount; i++)
+    {
+        if (strstr(_strupr((PCHAR)reactos_modules[i].String), _strupr(ModuleName)))
+        {
+            return &reactos_modules[i];
+        }
+    }
+
+    return NULL;
+}
+
+PVOID
+NTAPI
+LdrPEFixupForward(IN PCHAR ForwardName)
+{
+    CHAR NameBuffer[128];
+    PCHAR p;
+    PLOADER_MODULE ModuleObject;
+
+    strcpy(NameBuffer, ForwardName);
+    p = strchr(NameBuffer, '.');
+    if (p == NULL) return NULL;
+    *p = 0;
+
+    ModuleObject = LdrGetModuleObject(NameBuffer);
+    if (!ModuleObject)
+    {
+        DbgPrint("LdrPEFixupForward: failed to find module %s\n", NameBuffer);
+        return NULL;
+    }
+
+    return LdrPEGetExportByName((PVOID)ModuleObject->ModStart, (PUCHAR)(p + 1), 0xffff);
+}
+
 PVOID
 NTAPI
 LdrPEGetExportByName(PVOID BaseAddress,
@@ -360,10 +406,10 @@
             if ((ULONG_PTR)Function >= (ULONG_PTR)ExportDir &&
                 (ULONG_PTR)Function < (ULONG_PTR)ExportDir + ExportDirSize)
             {
-                Function = NULL;
+                Function = LdrPEFixupForward((PCHAR)Function);
                 if (Function == NULL)
                 {
-                    DbgPrint("LdrPEGetExportByName(): failed to find %s\n",SymbolName);
+                    DbgPrint("LdrPEGetExportByName(): failed to find %s\n", Function);
                 }
                 return Function;
             }
@@ -390,10 +436,10 @@
             if ((ULONG_PTR)Function >= (ULONG_PTR)ExportDir &&
                 (ULONG_PTR)Function < (ULONG_PTR)ExportDir + ExportDirSize)
             {
-                Function = NULL;
+                Function = LdrPEFixupForward((PCHAR)Function);
                 if (Function == NULL)
                 {
-                    DbgPrint("LdrPEGetExportByName(): failed to find %s\n",SymbolName);
+                    DbgPrint("1: failed to find %s\n", Function);
                 }
                 return Function;
             }
@@ -413,7 +459,7 @@
     }
 
     ExName = RVA(BaseAddress, ExNames[mid]);
-    DbgPrint("LdrPEGetExportByName(): failed to find %s\n",SymbolName);
+    DbgPrint("2: failed to find %s\n",SymbolName);
     return (PVOID)NULL;
 }
 
@@ -472,23 +518,6 @@
         FunctionNameList++;
     }
     return STATUS_SUCCESS;
-}
-
-PLOADER_MODULE
-NTAPI
-LdrGetModuleObject(PCHAR ModuleName)
-{
-    ULONG i;
-
-    for (i = 0; i < LoaderBlock.ModsCount; i++)
-    {
-        if (!_stricmp((PCHAR)reactos_modules[i].String, ModuleName))
-        {
-            return &reactos_modules[i];
-        }
-    }
-
-    return NULL;
 }
 
 NTSTATUS

Modified: trunk/reactos/ntoskrnl/ex/init.c
URL: http://svn.reactos.org/svn/reactos/trunk/reactos/ntoskrnl/ex/init.c?rev=25874&r1=25873&r2=25874&view=diff
==============================================================================
--- trunk/reactos/ntoskrnl/ex/init.c (original)
+++ trunk/reactos/ntoskrnl/ex/init.c Thu Feb 22 21:02:53 2007
@@ -896,6 +896,9 @@
     /* Initialize the executive at phase 0 */
     if (!ExInitSystem()) KEBUGCHECK(PHASE0_INITIALIZATION_FAILED);
 
+    /* Initialize the memory manager at phase 0 */
+    if (!MmInitSystem(0, LoaderBlock)) KeBugCheck(MEMORY1_INITIALIZATION_FAILED);
+
     /* Load boot symbols */
     ExpLoadBootSymbols(LoaderBlock);
 

Modified: trunk/reactos/ntoskrnl/include/internal/ex.h
URL: http://svn.reactos.org/svn/reactos/trunk/reactos/ntoskrnl/include/internal/ex.h?rev=25874&r1=25873&r2=25874&view=diff
==============================================================================
--- trunk/reactos/ntoskrnl/include/internal/ex.h (original)
+++ trunk/reactos/ntoskrnl/include/internal/ex.h Thu Feb 22 21:02:53 2007
@@ -20,6 +20,7 @@
 ULONG ExpAnsiCodePageDataOffset, ExpOemCodePageDataOffset;
 ULONG ExpUnicodeCaseTableDataOffset;
 PVOID ExpNlsSectionPointer;
+extern ULONG ExpInitializationPhase;
 
 typedef struct _EXHANDLE
 {

Modified: trunk/reactos/ntoskrnl/include/internal/mm.h
URL: http://svn.reactos.org/svn/reactos/trunk/reactos/ntoskrnl/include/internal/mm.h?rev=25874&r1=25873&r2=25874&view=diff
==============================================================================
--- trunk/reactos/ntoskrnl/include/internal/mm.h (original)
+++ trunk/reactos/ntoskrnl/include/internal/mm.h Thu Feb 22 21:02:53 2007
@@ -1429,4 +1429,17 @@
     OUT PULONG ResultLength
 );
 
+VOID
+NTAPI
+MiReloadBootLoadedDrivers(
+    IN PLOADER_PARAMETER_BLOCK LoaderBlock
+);
+
+BOOLEAN
+NTAPI
+MiInitializeLoadedModuleList(
+    IN PLOADER_PARAMETER_BLOCK LoaderBlock
+);
+
+
 #endif

Modified: trunk/reactos/ntoskrnl/io/iomgr/driver.c
URL: http://svn.reactos.org/svn/reactos/trunk/reactos/ntoskrnl/io/iomgr/driver.c?rev=25874&r1=25873&r2=25874&view=diff
==============================================================================
--- trunk/reactos/ntoskrnl/io/iomgr/driver.c (original)
+++ trunk/reactos/ntoskrnl/io/iomgr/driver.c Thu Feb 22 21:02:53 2007
@@ -34,10 +34,10 @@
 /* DECLARATIONS ***************************************************************/
 
 NTSTATUS
-LdrProcessModule(
-    PVOID ModuleLoadBase,
-    PUNICODE_STRING ModuleName,
-    PLDR_DATA_TABLE_ENTRY *ModuleObject
+NTAPI
+LdrTemporaryDriverHack(
+    PLDR_DATA_TABLE_ENTRY ModuleObject,
+    PUNICODE_STRING ModuleName
 );
 
 /* PRIVATE FUNCTIONS **********************************************************/
@@ -452,66 +452,6 @@
          /* FIXME: Check if it is the right status code */
          Status = STATUS_PLUGPLAY_NO_DEVICE;
       }
-
-      /*
-       * Special case for boot modules that were loaded by boot loader.
-       */
-
-      else if (KeLoaderBlock)
-      {
-         WCHAR SearchNameBuffer[256];
-         UNICODE_STRING SearchName;
-         PLIST_ENTRY ListHead, NextEntry;
-         PLDR_DATA_TABLE_ENTRY LdrEntry;
-
-         Status = STATUS_UNSUCCESSFUL;
-
-         /*
-          * FIXME:
-          * Improve this searching algorithm by using the image name
-          * stored in registry entry ImageName and use the whole path
-          * (requires change in FreeLoader).
-          */
-         swprintf(SearchNameBuffer, L"%wZ.sys", ServiceName);
-         RtlInitUnicodeString(&SearchName, SearchNameBuffer);
-
-         /* Loop the boot modules */
-         ListHead = &KeLoaderBlock->LoadOrderListHead;
-         NextEntry = ListHead->Flink->Flink;
-         while (ListHead != NextEntry)
-         {
-            /* Get the entry */
-            LdrEntry = CONTAINING_RECORD(NextEntry,
-                                         LDR_DATA_TABLE_ENTRY,
-                                         InLoadOrderLinks);
-
-            /* Compare names */
-            if (RtlEqualUnicodeString(&LdrEntry->BaseDllName, &SearchName, TRUE))
-            {
-                /* Tell, that the module is already loaded */
-                LdrEntry->Flags |= LDRP_ENTRY_INSERTED;
-
-                Status = LdrProcessModule(LdrEntry->DllBase,
-                                          &ServiceImagePath,
-                                          ModuleObject);
-
-                KDB_SYMBOLFILE_HOOK(&SearchName);
-                break;
-            }
-
-            /* Go to the next driver */
-            NextEntry = NextEntry->Flink;
-         }
-
-         if (!NT_SUCCESS(Status))
-            /* Try to load it. It may just have been installed by PnP manager */
-            Status = LdrLoadModule(&ServiceImagePath, ModuleObject);
-      }
-
-      /*
-       * Case for rest of the drivers
-       */
-
       else
       {
          DPRINT("Loading module\n");
@@ -805,28 +745,116 @@
    return STATUS_SUCCESS;
 }
 
+NTSTATUS
+NTAPI
+MiResolveImageReferences(IN PVOID ImageBase,
+                         IN PUNICODE_STRING ImageFileDirectory,
+                         IN PUNICODE_STRING NamePrefix OPTIONAL,
+                         OUT PCHAR *MissingApi,
+                         OUT PWCHAR *MissingDriver,
+                         OUT PLOAD_IMPORTS *LoadImports);
+
+extern KSPIN_LOCK PsLoadedModuleSpinLock;
+
+//
+// Used for images already loaded (boot drivers)
+//
+NTSTATUS
+NTAPI
+LdrProcessDriverModule(PLDR_DATA_TABLE_ENTRY LdrEntry,
+                       PUNICODE_STRING FileName,
+                       PLDR_DATA_TABLE_ENTRY *ModuleObject)
+{
+    NTSTATUS Status;
+    PLDR_DATA_TABLE_ENTRY NewEntry;
+    UNICODE_STRING BaseName, BaseDirectory;
+    PLOAD_IMPORTS LoadedImports = (PVOID)-2;
+    PCHAR MissingApiName, Buffer;
+    PWCHAR MissingDriverName;
+    PVOID DriverBase = LdrEntry->DllBase;
+
+    /* Allocate a buffer we'll use for names */
+    Buffer = ExAllocatePoolWithTag(NonPagedPool, MAX_PATH, TAG_LDR_WSTR);
+    if (!Buffer)
+    {
+        /* Fail */
+        return STATUS_INSUFFICIENT_RESOURCES;
+    }
+
+    /* Check for a separator */
+    if (FileName->Buffer[0] == OBJ_NAME_PATH_SEPARATOR)
+    {
+        PWCHAR p;
+        ULONG BaseLength;
+
+        /* Loop the path until we get to the base name */
+        p = &FileName->Buffer[FileName->Length / sizeof(WCHAR)];
+        while (*(p - 1) != OBJ_NAME_PATH_SEPARATOR) p--;
+
+        /* Get the length */
+        BaseLength = (ULONG)(&FileName->Buffer[FileName->Length / sizeof(WCHAR)] - p);
+        BaseLength *= sizeof(WCHAR);
+
+        /* Setup the string */
+        BaseName.Length = (USHORT)BaseLength;
+        BaseName.Buffer = p;
+    }
+    else
+    {
+        /* Otherwise, we already have a base name */
+        BaseName.Length = FileName->Length;
+        BaseName.Buffer = FileName->Buffer;
+    }
+
+    /* Setup the maximum length */
+    BaseName.MaximumLength = BaseName.Length;
+
+    /* Now compute the base directory */
+    BaseDirectory = *FileName;
+    BaseDirectory.Length -= BaseName.Length;
+    BaseDirectory.MaximumLength = BaseDirectory.Length;
+
+    NewEntry = LdrEntry;
+
+    /* Resolve imports */
+    MissingApiName = Buffer;
+    Status = MiResolveImageReferences(DriverBase,
+                                      &BaseDirectory,
+                                      NULL,
+                                      &MissingApiName,
+                                      &MissingDriverName,
+                                      &LoadedImports);
+    if (!NT_SUCCESS(Status))
+    {
+        /* Fail */
+        ExFreePool(LdrEntry->FullDllName.Buffer);
+        ExFreePool(LdrEntry);
+        return Status;
+    }
+
+    /* Return */
+    *ModuleObject = LdrEntry;
+    return STATUS_SUCCESS;
+}
+
 /*
  * IopInitializeBuiltinDriver
  *
  * Initialize a driver that is already loaded in memory.
  */
 
-NTSTATUS FASTCALL INIT_FUNCTION
-IopInitializeBuiltinDriver(
-   PDEVICE_NODE ModuleDeviceNode,
-   PVOID ModuleLoadBase,
-   PUNICODE_STRING ModuleName,
-   ULONG ModuleLength)
-{
-   PLDR_DATA_TABLE_ENTRY ModuleObject;
-   PDEVICE_NODE DeviceNode;
-   PDRIVER_OBJECT DriverObject;
-   NTSTATUS Status;
-   PWCHAR FileNameWithoutPath;
-   LPWSTR FileExtension;
-
-   DPRINT("Initializing driver '%wZ' at %08lx, length 0x%08lx\n",
-      ModuleName, ModuleLoadBase, ModuleLength);
+NTSTATUS
+NTAPI
+IopInitializeBuiltinDriver(IN PLDR_DATA_TABLE_ENTRY LdrEntry)
+{
+    PDEVICE_NODE DeviceNode;
+    PDRIVER_OBJECT DriverObject;
+    NTSTATUS Status;
+    PWCHAR FileNameWithoutPath;
+    LPWSTR FileExtension;
+    PUNICODE_STRING ModuleName = &LdrEntry->BaseDllName;
+    PLDR_DATA_TABLE_ENTRY ModuleObject;
+
 
    /*
     * Display 'Loading XXX...' message
@@ -836,9 +864,6 @@
    /*
     * Determine the right device object
     */
-
-   if (ModuleDeviceNode == NULL)
-   {
       /* Use IopRootDeviceNode for now */
       Status = IopCreateDeviceNode(IopRootDeviceNode, NULL, &DeviceNode);
       if (!NT_SUCCESS(Status))
@@ -846,15 +871,11 @@
          CPRINT("Driver '%wZ' load failed, status (%x)\n", ModuleName, Status);
          return(Status);
       }
-   } else
-   {
-      DeviceNode = ModuleDeviceNode;
-   }
+
 
    /*
     * Generate filename without path (not needed by freeldr)
     */
-
    FileNameWithoutPath = wcsrchr(ModuleName->Buffer, L'\\');
    if (FileNameWithoutPath == NULL)
    {
@@ -866,17 +887,15 @@
    }
 
    /*
-    * Load the module
+    * Load the module. Remove for FreeLDR 2.5.
     */
    RtlCreateUnicodeString(&DeviceNode->ServiceName, FileNameWithoutPath);
-   Status = LdrProcessModule(ModuleLoadBase, &DeviceNode->ServiceName,
-      &ModuleObject);
+   Status = LdrProcessDriverModule(LdrEntry, &DeviceNode->ServiceName, &ModuleObject);
    if (!NT_SUCCESS(Status))
    {
-      if (ModuleDeviceNode == NULL)
-         IopFreeDeviceNode(DeviceNode);
-      CPRINT("Driver '%wZ' load failed, status (%x)\n", ModuleName, Status);
-      return Status;
+           IopFreeDeviceNode(DeviceNode);
+       CPRINT("Driver '%wZ' load failed, status (%x)\n", ModuleName, Status);
+       return Status;
    }
 
    /* Load symbols */
@@ -885,7 +904,6 @@
    /*
     * Strip the file extension from ServiceName
     */
-
    FileExtension = wcsrchr(DeviceNode->ServiceName.Buffer, '.');
    if (FileExtension != NULL)
    {
@@ -896,13 +914,11 @@
    /*
     * Initialize the driver
     */
-
    Status = IopInitializeDriverModule(DeviceNode, ModuleObject,
       &DeviceNode->ServiceName, FALSE, &DriverObject);
 
    if (!NT_SUCCESS(Status))
    {
-      if (ModuleDeviceNode == NULL)
          IopFreeDeviceNode(DeviceNode);
       CPRINT("Driver '%wZ' load failed, status (%x)\n", ModuleName, Status);
       return Status;
@@ -1005,31 +1021,9 @@
             if (!(LdrEntry->Flags & LDRP_ENTRY_INSERTED))
             {
                 /* Initialize it */
-                IopInitializeBuiltinDriver(NULL,
-                                           LdrEntry->DllBase,
-                                           &LdrEntry->BaseDllName,
-                                           LdrEntry->SizeOfImage);
+                IopInitializeBuiltinDriver(LdrEntry);
             }
         }
-
-        /* Go to the next driver */
-        NextEntry = NextEntry->Flink;
-    }
-
-    /* Loop modules again */
-    NextEntry = ListHead->Flink;
-    while (ListHead != NextEntry)
-    {
-        /* Get the entry */
-        LdrEntry = CONTAINING_RECORD(NextEntry,
-                                     LDR_DATA_TABLE_ENTRY,
-                                     InLoadOrderLinks);
-
-        /* Free memory */
-        DPRINT("Driver at: %p ending at: %p for module: %wZ\n",
-                LdrEntry->DllBase,
-                (ULONG_PTR)LdrEntry->DllBase+ LdrEntry->SizeOfImage,
-                &LdrEntry->FullDllName);
 
         /* Go to the next driver */
         NextEntry = NextEntry->Flink;

Modified: trunk/reactos/ntoskrnl/ke/i386/kiinit.c
URL: http://svn.reactos.org/svn/reactos/trunk/reactos/ntoskrnl/ke/i386/kiinit.c?rev=25874&r1=25873&r2=25874&view=diff
==============================================================================
--- trunk/reactos/ntoskrnl/ke/i386/kiinit.c (original)
+++ trunk/reactos/ntoskrnl/ke/i386/kiinit.c Thu Feb 22 21:02:53 2007
@@ -533,9 +533,6 @@
             0,
             4096);
 
-    /* Sets up the Text Sections of the Kernel and HAL for debugging */
-    LdrInit1();
-
     /* Set the NX Support policy */
     SharedUserData->NXSupportPolicy = (UCHAR)NXSupportPolicy;
 

Modified: trunk/reactos/ntoskrnl/ldr/loader.c
URL: http://svn.reactos.org/svn/reactos/trunk/reactos/ntoskrnl/ldr/loader.c?rev=25874&r1=25873&r2=25874&view=diff
==============================================================================
--- trunk/reactos/ntoskrnl/ldr/loader.c (original)
+++ trunk/reactos/ntoskrnl/ldr/loader.c Thu Feb 22 21:02:53 2007
@@ -17,13 +17,6 @@
 #include <ntoskrnl.h>
 #define NDEBUG
 #include <debug.h>
-
-/* GLOBALS *******************************************************************/
-
-LIST_ENTRY PsLoadedModuleList;
-KSPIN_LOCK ModuleListLock;
-LDR_DATA_TABLE_ENTRY NtoskrnlModuleObject;
-LDR_DATA_TABLE_ENTRY HalModuleObject;
 
 /* FUNCTIONS *****************************************************************/
 
@@ -105,52 +98,7 @@
     return(0);
 }
 
-VOID
-INIT_FUNCTION
-NTAPI
-LdrInit1(VOID)
-{
-    PLDR_DATA_TABLE_ENTRY HalModuleObject, NtoskrnlModuleObject, LdrEntry;
-
-    /* Initialize the module list and spinlock */
-    InitializeListHead(&PsLoadedModuleList);
-    KeInitializeSpinLock(&ModuleListLock);
-
-    /* Get the NTOSKRNL Entry from the loader */
-    LdrEntry = CONTAINING_RECORD(KeLoaderBlock->LoadOrderListHead.Flink, LDR_DATA_TABLE_ENTRY, InLoadOrderLinks);
-
-    /* Initialize ModuleObject for NTOSKRNL */
-    NtoskrnlModuleObject = ExAllocatePoolWithTag(PagedPool,
-                                                 sizeof(LDR_DATA_TABLE_ENTRY),
-                                                 TAG('M', 'm', 'L', 'd'));
-    NtoskrnlModuleObject->DllBase = LdrEntry->DllBase;
-    RtlInitUnicodeString(&NtoskrnlModuleObject->FullDllName, KERNEL_MODULE_NAME);
-    NtoskrnlModuleObject->BaseDllName = NtoskrnlModuleObject->FullDllName;
-    NtoskrnlModuleObject->EntryPoint = LdrEntry->EntryPoint;
-    NtoskrnlModuleObject->SizeOfImage = LdrEntry->SizeOfImage;
-
-    /* Insert it into the list */
-    InsertTailList(&PsLoadedModuleList, &NtoskrnlModuleObject->InLoadOrderLinks);
-
-    /* Get the HAL Entry from the loader */
-    LdrEntry = CONTAINING_RECORD(KeLoaderBlock->LoadOrderListHead.Flink->Flink, LDR_DATA_TABLE_ENTRY, InLoadOrderLinks);
-
-    /* Initialize ModuleObject for HAL */
-    HalModuleObject = ExAllocatePoolWithTag(PagedPool,
-                                                 sizeof(LDR_DATA_TABLE_ENTRY),
-                                                 TAG('M', 'm', 'L', 'd'));
-    HalModuleObject->DllBase = LdrEntry->DllBase;
-    RtlInitUnicodeString(&HalModuleObject->FullDllName, HAL_MODULE_NAME);
-    HalModuleObject->BaseDllName = HalModuleObject->FullDllName;
-    HalModuleObject->EntryPoint = LdrEntry->EntryPoint;
-    HalModuleObject->SizeOfImage = LdrEntry->SizeOfImage;
-
-    /* Insert it into the list */
-    InsertTailList(&PsLoadedModuleList, &HalModuleObject->InLoadOrderLinks);
-
-    /* Hook for KDB on initialization of the loader. */
-    KDB_LOADERINIT_HOOK(NtoskrnlModuleObject, HalModuleObject);
-}
+extern KSPIN_LOCK PsLoadedModuleSpinLock;
 
 //
 // Used for checking if a module is already in the module list.
@@ -166,7 +114,7 @@
 
     DPRINT("LdrGetModuleObject(%wZ) called\n", ModuleName);
 
-    KeAcquireSpinLock(&ModuleListLock,&Irql);
+    KeAcquireSpinLock(&PsLoadedModuleSpinLock,&Irql);
 
     Entry = PsLoadedModuleList.Flink;
     while (Entry != &PsLoadedModuleList)
@@ -180,14 +128,14 @@
         if (!LdrpCompareModuleNames(&Module->BaseDllName, ModuleName))
         {
             DPRINT("Module %wZ\n", &Module->BaseDllName);
-            KeReleaseSpinLock(&ModuleListLock, Irql);
+            KeReleaseSpinLock(&PsLoadedModuleSpinLock, Irql);
             return(Module);
         }
 
         Entry = Entry->Flink;
     }
 
-    KeReleaseSpinLock(&ModuleListLock, Irql);
+    KeReleaseSpinLock(&PsLoadedModuleSpinLock, Irql);
 
     DPRINT("Could not find module '%wZ'\n", ModuleName);
 
@@ -204,9 +152,9 @@
     KIRQL Irql;
 
     /* Remove the module from the module list */
-    KeAcquireSpinLock(&ModuleListLock,&Irql);
+    KeAcquireSpinLock(&PsLoadedModuleSpinLock,&Irql);
     RemoveEntryList(&ModuleObject->InLoadOrderLinks);
-    KeReleaseSpinLock(&ModuleListLock, Irql);
+    KeReleaseSpinLock(&PsLoadedModuleSpinLock, Irql);
 
     /* Hook for KDB on unloading a driver. */
     KDB_UNLOADDRIVER_HOOK(ModuleObject);
@@ -221,29 +169,104 @@
 }
 
 //
-// Used for images already loaded (boot drivers)
+// Used by NtLoadDriver/IoMgr
 //
 NTSTATUS
-LdrProcessModule(PVOID ModuleLoadBase,
-                 PUNICODE_STRING FileName,
-                 PLDR_DATA_TABLE_ENTRY *ModuleObject)
+NTAPI
+LdrLoadModule(
+              PUNICODE_STRING FileName,
+              PLDR_DATA_TABLE_ENTRY *ModuleObject )
 {
+    PVOID ModuleLoadBase;
+    NTSTATUS Status;
+    HANDLE FileHandle;
+    OBJECT_ATTRIBUTES ObjectAttributes;
+    PLDR_DATA_TABLE_ENTRY Module;
+    FILE_STANDARD_INFORMATION FileStdInfo;
+    IO_STATUS_BLOCK IoStatusBlock;
     unsigned int DriverSize, Idx;
     ULONG CurrentSize;
     PVOID DriverBase;
     PIMAGE_DOS_HEADER PEDosHeader;
     PIMAGE_NT_HEADERS PENtHeaders;
     PIMAGE_SECTION_HEADER PESectionHeaders;
-    NTSTATUS Status;
     KIRQL Irql;
     PIMAGE_NT_HEADERS NtHeader;
     UNICODE_STRING BaseName, BaseDirectory, PrefixName;
     PLDR_DATA_TABLE_ENTRY LdrEntry;
     ULONG EntrySize;
     PLOAD_IMPORTS LoadedImports = (PVOID)-2;
-    PWSTR NameBuffer;
     PCHAR MissingApiName, Buffer;
     PWCHAR MissingDriverName;
+
+    *ModuleObject = NULL;
+
+    DPRINT("Loading Module %wZ...\n", FileName);
+
+    /*  Open the Module  */
+    InitializeObjectAttributes(&ObjectAttributes,
+        FileName,
+        OBJ_CASE_INSENSITIVE,
+        NULL,
+        NULL);
+
+    Status = ZwOpenFile(&FileHandle,
+        GENERIC_READ,
+        &ObjectAttributes,
+        &IoStatusBlock,
+        FILE_SHARE_READ,
+        FILE_SYNCHRONOUS_IO_NONALERT);
+
+    if (!NT_SUCCESS(Status))
+    {
+        DPRINT("Could not open module file: %wZ (Status 0x%08lx)\n", FileName, Status);
+        return(Status);
+    }
+
+
+    /*  Get the size of the file  */
+    Status = ZwQueryInformationFile(FileHandle,
+        &IoStatusBlock,
+        &FileStdInfo,
+        sizeof(FileStdInfo),
+        FileStandardInformation);
+    if (!NT_SUCCESS(Status))
+    {
+        DPRINT("Could not get file size\n");
+        NtClose(FileHandle);
+        return(Status);
+    }
+
+
+    /*  Allocate nonpageable memory for driver  */
+    ModuleLoadBase = ExAllocatePoolWithTag(NonPagedPool,
+        FileStdInfo.EndOfFile.u.LowPart,
+        TAG_DRIVER_MEM);
+    if (ModuleLoadBase == NULL)
+    {
+        DPRINT("Could not allocate memory for module");
+        NtClose(FileHandle);
+        return(STATUS_INSUFFICIENT_RESOURCES);
+    }
+
+
+    /*  Load driver into memory chunk  */
+    Status = ZwReadFile(FileHandle,
+        0, 0, 0,
+        &IoStatusBlock,
+        ModuleLoadBase,
+        FileStdInfo.EndOfFile.u.LowPart,
+        0, 0);
+    if (!NT_SUCCESS(Status))
+    {
+        DPRINT("Could not read module file into memory");
+        ExFreePool(ModuleLoadBase);
+        NtClose(FileHandle);
+        return(Status);
+    }
+
+
+    ZwClose(FileHandle);
 
     DPRINT("Processing PE Module at module base:%08lx\n", ModuleLoadBase);
 
@@ -414,9 +437,6 @@
         LdrEntry->Flags |= 0x80000000;
     }
 
-    /* We'll put the name after the entry */
-    NameBuffer = (PVOID)(LdrEntry + 1);
-
     /* Setup the rest of the entry */
     LdrEntry->DllBase = DriverBase;
     LdrEntry->EntryPoint = (PVOID)((ULONG_PTR)DriverBase +
@@ -426,7 +446,7 @@
     LdrEntry->SectionPointer = LdrEntry;
 
     /* Now write the DLL name */
-    LdrEntry->BaseDllName.Buffer = NameBuffer;
+    LdrEntry->BaseDllName.Buffer = (PVOID)(LdrEntry + 1);
     LdrEntry->BaseDllName.Length = BaseName.Length;
     LdrEntry->BaseDllName.MaximumLength = BaseName.Length;
 
@@ -461,9 +481,9 @@
     }
 
     /* Insert the entry */
-    KeAcquireSpinLock(&ModuleListLock, &Irql);
+    KeAcquireSpinLock(&PsLoadedModuleSpinLock, &Irql);
     InsertTailList(&PsLoadedModuleList, &LdrEntry->InLoadOrderLinks);
-    KeReleaseSpinLock(&ModuleListLock, Irql);
+    KeReleaseSpinLock(&PsLoadedModuleSpinLock, Irql);
 
     /* Resolve imports */
     MissingApiName = Buffer;
@@ -482,105 +502,7 @@
     }
 
     /* Return */
-    *ModuleObject = LdrEntry;
-    return STATUS_SUCCESS;
-}
-
-//
-// Used by NtLoadDriver/IoMgr
-//
-NTSTATUS
-NTAPI
-LdrLoadModule(
-              PUNICODE_STRING Filename,
-              PLDR_DATA_TABLE_ENTRY *ModuleObject )
-{
-    PVOID ModuleLoadBase;
-    NTSTATUS Status;
-    HANDLE FileHandle;
-    OBJECT_ATTRIBUTES ObjectAttributes;
-    PLDR_DATA_TABLE_ENTRY Module;
-    FILE_STANDARD_INFORMATION FileStdInfo;
-    IO_STATUS_BLOCK IoStatusBlock;
-
-    *ModuleObject = NULL;
-
-    DPRINT("Loading Module %wZ...\n", Filename);
-
-    /*  Open the Module  */
-    InitializeObjectAttributes(&ObjectAttributes,
-        Filename,
-        OBJ_CASE_INSENSITIVE,
-        NULL,
-        NULL);
-
-    Status = ZwOpenFile(&FileHandle,
-        GENERIC_READ,
-        &ObjectAttributes,
-        &IoStatusBlock,
-        FILE_SHARE_READ,
-        FILE_SYNCHRONOUS_IO_NONALERT);
-
-    if (!NT_SUCCESS(Status))
-    {
-        DPRINT("Could not open module file: %wZ (Status 0x%08lx)\n", Filename, Status);
-        return(Status);
-    }
-
-
-    /*  Get the size of the file  */
-    Status = ZwQueryInformationFile(FileHandle,
-        &IoStatusBlock,
-        &FileStdInfo,
-        sizeof(FileStdInfo),
-        FileStandardInformation);
-    if (!NT_SUCCESS(Status))
-    {
-        DPRINT("Could not get file size\n");
-        NtClose(FileHandle);
-        return(Status);
-    }
-
-
-    /*  Allocate nonpageable memory for driver  */
-    ModuleLoadBase = ExAllocatePoolWithTag(NonPagedPool,
-        FileStdInfo.EndOfFile.u.LowPart,
-        TAG_DRIVER_MEM);
-    if (ModuleLoadBase == NULL)
-    {
-        DPRINT("Could not allocate memory for module");
-        NtClose(FileHandle);
-        return(STATUS_INSUFFICIENT_RESOURCES);
-    }
-
-
-    /*  Load driver into memory chunk  */
-    Status = ZwReadFile(FileHandle,
-        0, 0, 0,
-        &IoStatusBlock,
-        ModuleLoadBase,
-        FileStdInfo.EndOfFile.u.LowPart,
-        0, 0);
-    if (!NT_SUCCESS(Status))
-    {
-        DPRINT("Could not read module file into memory");
-        ExFreePool(ModuleLoadBase);
-        NtClose(FileHandle);
-        return(Status);
-    }
-
-
-    ZwClose(FileHandle);
-
-    Status = LdrProcessModule(ModuleLoadBase,
-        Filename,
-        &Module);
-    if (!NT_SUCCESS(Status))
-    {
-        DPRINT("Could not process module\n");
-        ExFreePool(ModuleLoadBase);
-        return(Status);
-    }
+    Module = LdrEntry;
 
     /*  Cleanup  */
     ExFreePool(ModuleLoadBase);
@@ -588,7 +510,7 @@
     *ModuleObject = Module;
 
     /* Hook for KDB on loading a driver. */
-    KDB_LOADDRIVER_HOOK(Filename, Module);
+    KDB_LOADDRIVER_HOOK(FileName, Module);
 
     return(STATUS_SUCCESS);
 }

Modified: trunk/reactos/ntoskrnl/mm/mminit.c
URL: http://svn.reactos.org/svn/reactos/trunk/reactos/ntoskrnl/mm/mminit.c?rev=25874&r1=25873&r2=25874&view=diff
==============================================================================
--- trunk/reactos/ntoskrnl/mm/mminit.c (original)
+++ trunk/reactos/ntoskrnl/mm/mminit.c Thu Feb 22 21:02:53 2007
@@ -459,7 +459,18 @@
 MmInitSystem(IN ULONG Phase,
              IN PLOADER_PARAMETER_BLOCK LoaderBlock)
 {
-    if (Phase == 1)
+    if (Phase == 0)
+    {
+        /* Reload boot drivers */
+        MiReloadBootLoadedDrivers(LoaderBlock);
+
+        /* Initialize the loaded module list */
+        MiInitializeLoadedModuleList(LoaderBlock);
+
+        /* We're done, for now */
+        DPRINT("Mm0: COMPLETE\n");
+    }
+    else if (Phase == 1)
     {
         MmInitializeRmapList();
         RmapReady = TRUE;

Modified: trunk/reactos/ntoskrnl/mm/sysldr.c
URL: http://svn.reactos.org/svn/reactos/trunk/reactos/ntoskrnl/mm/sysldr.c?rev=25874&r1=25873&r2=25874&view=diff
==============================================================================
--- trunk/reactos/ntoskrnl/mm/sysldr.c (original)
+++ trunk/reactos/ntoskrnl/mm/sysldr.c Thu Feb 22 21:02:53 2007
@@ -12,7 +12,77 @@
 #define NDEBUG
 #include <debug.h>
 
+/* GLOBALS *******************************************************************/
+
+LIST_ENTRY PsLoadedModuleList;
+KSPIN_LOCK PsLoadedModuleSpinLock;
+PVOID PsNtosImageBase;
+
 /* FUNCTIONS *****************************************************************/
+
+VOID
+NTAPI
+MiUpdateThunks(IN PLOADER_PARAMETER_BLOCK LoaderBlock,
+               IN PVOID OldBase,
+               IN PVOID NewBase,
+               IN ULONG Size)
+{
+    ULONG_PTR OldBaseTop, Delta;
+    PLDR_DATA_TABLE_ENTRY LdrEntry;
+    PLIST_ENTRY NextEntry;
+    ULONG ImportSize;
+    PIMAGE_IMPORT_DESCRIPTOR ImportDescriptor;
+    PULONG ImageThunk;
+
+    /* Calculate the top and delta */
+    OldBaseTop = (ULONG_PTR)OldBase + Size - 1;
+    Delta = (ULONG_PTR)NewBase - (ULONG_PTR)OldBase;
+
+    /* Loop the loader block */
+    for (NextEntry = LoaderBlock->LoadOrderListHead.Flink;
+         NextEntry != &LoaderBlock->LoadOrderListHead;
+         NextEntry = NextEntry->Flink)
+    {
+        /* Get the loader entry */
+        LdrEntry = CONTAINING_RECORD(NextEntry,
+                                     LDR_DATA_TABLE_ENTRY,
+                                     InLoadOrderLinks);
+
+        /* Get the import table */
+        ImportDescriptor = RtlImageDirectoryEntryToData(LdrEntry->DllBase,
+                                                        TRUE,
+                                                        IMAGE_DIRECTORY_ENTRY_IMPORT,
+                                                        &ImportSize);
+        if (!ImportDescriptor) continue;
+
+        /* Make sure we have an IAT */
+        DPRINT("[Mm0]: Updating thunks in: %wZ\n", &LdrEntry->BaseDllName);
+        while ((ImportDescriptor->Name) &&
+               (ImportDescriptor->OriginalFirstThunk))
+        {
+            /* Get the image thunk */
+            ImageThunk = (PVOID)((ULONG_PTR)LdrEntry->DllBase +
+                                 ImportDescriptor->FirstThunk);
+            while (*ImageThunk)
+            {
+                /* Check if it's within this module */
+                if ((*ImageThunk >= (ULONG_PTR)OldBase) && (*ImageThunk <= OldBaseTop))
+                {
+                    /* Relocate it */
+                    DPRINT("[Mm0]: Updating IAT at: %p. Old Entry: %p. New Entry: %p.\n",
+                            ImageThunk, *ImageThunk, *ImageThunk + Delta);
+                    *ImageThunk += Delta;
+                }
+
+                /* Go to the next thunk */
+                ImageThunk++;
+            }
+
+            /* Go to the next import */
+            ImportDescriptor++;
+        }
+    }
+}
 
 NTSTATUS
 NTAPI
@@ -584,3 +654,259 @@
     return STATUS_SUCCESS;
 }
 
+VOID
+NTAPI
+MiReloadBootLoadedDrivers(IN PLOADER_PARAMETER_BLOCK LoaderBlock)
+{
+    PLIST_ENTRY NextEntry;
+    ULONG i = 0;
+    PIMAGE_NT_HEADERS NtHeader;
+    PLDR_DATA_TABLE_ENTRY LdrEntry;
+    PIMAGE_FILE_HEADER FileHeader;
+    BOOLEAN ValidRelocs;
+    PIMAGE_DATA_DIRECTORY DataDirectory;
+    PVOID DllBase, NewImageAddress;
+    NTSTATUS Status;
+    ULONG DriverSize = 0, Size;
+    PIMAGE_SECTION_HEADER Section;
+
+    /* Loop driver list */
+    for (NextEntry = LoaderBlock->LoadOrderListHead.Flink;
+         NextEntry != &LoaderBlock->LoadOrderListHead;
+         NextEntry = NextEntry->Flink)
+    {
+        /* Get the loader entry and NT header */
+        LdrEntry = CONTAINING_RECORD(NextEntry,
+                                     LDR_DATA_TABLE_ENTRY,
+                                     InLoadOrderLinks);
+        NtHeader = RtlImageNtHeader(LdrEntry->DllBase);
+
+        /* Debug info */
+        DPRINT("[Mm0]: Driver at: %p ending at: %p for module: %wZ\n",
+                LdrEntry->DllBase,
+                (ULONG_PTR)LdrEntry->DllBase+ LdrEntry->SizeOfImage,
+                &LdrEntry->FullDllName);
+
+        /* Skip kernel and HAL */
+        /* ROS HACK: Skip BOOTVID/KDCOM too */
+        i++;
+        if (i <= 4) continue;
+
+        /* Skip non-drivers */
+        if (!NtHeader) continue;
+
+#if 1 // Disable for FreeLDR 2.5
+        /*  Get header pointers  */
+        Section = IMAGE_FIRST_SECTION(NtHeader);
+
+        /*  Determine the size of the module  */
+        for (i = 0; i < NtHeader->FileHeader.NumberOfSections; i++)
+        {
+            /* Skip this section if we're not supposed to load it */
+            if (!(Section[i].Characteristics & IMAGE_SCN_TYPE_NOLOAD))
+            {
+                /* Add the size of this section into the total size */
+                Size = Section[i].VirtualAddress + Section[i].Misc.VirtualSize;
+                DriverSize = max(DriverSize, Size);
+            }
+        }
+
+        /* Round up the driver size to section alignment */
+        DriverSize = ROUND_UP(DriverSize, NtHeader->OptionalHeader.SectionAlignment);
+#endif
+
+        /* Get the file header and make sure we can relocate */
+        FileHeader = &NtHeader->FileHeader;
+        if (FileHeader->Characteristics & IMAGE_FILE_RELOCS_STRIPPED) continue;
+        if (NtHeader->OptionalHeader.NumberOfRvaAndSizes <
+            IMAGE_DIRECTORY_ENTRY_BASERELOC) continue;
+
+        /* Everything made sense until now, check the relocation section too */
+        DataDirectory = &NtHeader->OptionalHeader.
+                        DataDirectory[IMAGE_DIRECTORY_ENTRY_BASERELOC];
+        if (!DataDirectory->VirtualAddress)
+        {
+            /* We don't really have relocations */
+            ValidRelocs = FALSE;
+        }
+        else
+        {
+            /* Make sure the size is valid */
+            if ((DataDirectory->VirtualAddress + DataDirectory->Size) >
+                LdrEntry->SizeOfImage)
+            {
+                /* They're not, skip */
+                 continue;
+            }
+
+            /* We have relocations */
+            ValidRelocs = TRUE;
+        }
+
+        /* Remember the original address */
+        DllBase = LdrEntry->DllBase;
+
+        /*  Allocate a virtual section for the module  */
+        NewImageAddress = MmAllocateSection(DriverSize, NULL);
+        if (!NewImageAddress)
+        {
+            /* Shouldn't happen */
+            DPRINT1("[Mm0]: Couldn't allocate driver section!\n");
+            while (TRUE);
+        }
+
+        /* Sanity check */
+        DPRINT("[Mm0]: Copying from: %p to: %p\n", DllBase, NewImageAddress);
+        ASSERT(ExpInitializationPhase == 0);
+
+#if 0 // Enable for FreeLDR 2.5
+        /* Now copy the entire driver over */
+        RtlCopyMemory(NewImageAddress, DllBase, DriverSize);
+#else
+        /* Copy headers over */
+        RtlCopyMemory(NewImageAddress,
+                      DllBase,
+                      NtHeader->OptionalHeader.SizeOfHeaders);
+
+        /*  Copy image sections into virtual section  */
+        for (i = 0; i < NtHeader->FileHeader.NumberOfSections; i++)
+        {
+            /* Get the size of this section and check if it's valid and on-disk */
+            Size = Section[i].VirtualAddress + Section[i].Misc.VirtualSize;
+            if ((Size <= DriverSize) && (Section[i].SizeOfRawData))
+            {
+                /* Copy the data from the disk to the image */
+                RtlCopyMemory((PVOID)((ULONG_PTR)NewImageAddress +
+                                      Section[i].VirtualAddress),
+                              (PVOID)((ULONG_PTR)DllBase +
+                                      Section[i].PointerToRawData),
+                              Section[i].Misc.VirtualSize >
+                              Section[i].SizeOfRawData ?
+                              Section[i].SizeOfRawData :
+                              Section[i].Misc.VirtualSize);
+            }
+        }
+#endif
+
+        /* Sanity check */
+        ASSERT(*(PULONG)NewImageAddress == *(PULONG)DllBase);
+
+        /* Set the image base to the old address */
+        NtHeader->OptionalHeader.ImageBase = (ULONG_PTR)DllBase;
+
+        /* Check if we had relocations */
+        if (ValidRelocs)
+        {
+            /* Relocate the image */
+            Status = LdrRelocateImageWithBias(NewImageAddress,
+                                              0,
+                                              "SYSLDR",
+                                              STATUS_SUCCESS,
+                                              STATUS_CONFLICTING_ADDRESSES,
+                                              STATUS_INVALID_IMAGE_FORMAT);
+            if (!NT_SUCCESS(Status))
+            {
+                /* This shouldn't happen */
+                DPRINT1("Relocations failed!\n");
+                while (TRUE);
+            }
+        }
+
+        /* Update the loader entry */
+        LdrEntry->DllBase = NewImageAddress;
+
+        /* Update the thunks */
+        DPRINT("[Mm0]: Updating thunks to: %wZ\n", &LdrEntry->BaseDllName);
+        MiUpdateThunks(LoaderBlock,
+                       DllBase,
+                       NewImageAddress,
+                       LdrEntry->SizeOfImage);
+
+        /* Update the loader entry */
+        LdrEntry->Flags |= 0x01000000;
+        LdrEntry->EntryPoint = (PVOID)((ULONG_PTR)NewImageAddress +
+                                NtHeader->OptionalHeader.AddressOfEntryPoint);
+        LdrEntry->SizeOfImage = DriverSize;
+    }
+}
+
+BOOLEAN
+NTAPI
+MiInitializeLoadedModuleList(IN PLOADER_PARAMETER_BLOCK LoaderBlock)
+{
+    PLDR_DATA_TABLE_ENTRY LdrEntry, NewEntry;
+    PLIST_ENTRY ListHead, NextEntry;
+    ULONG EntrySize;
+
+    /* Setup the loaded module list and lock */
+    KeInitializeSpinLock(&PsLoadedModuleSpinLock);
+    InitializeListHead(&PsLoadedModuleList);
+
+    /* Get loop variables and the kernel entry */
+    ListHead = &LoaderBlock->LoadOrderListHead;
+    NextEntry = ListHead->Flink;
+    LdrEntry = CONTAINING_RECORD(NextEntry,
+                                 LDR_DATA_TABLE_ENTRY,
+                                 InLoadOrderLinks);
+    PsNtosImageBase = LdrEntry->DllBase;
+
+    /* Loop the loader block */
+    while (NextEntry != ListHead)
+    {
+        /* Get the loader entry */
+        LdrEntry = CONTAINING_RECORD(NextEntry,
+                                     LDR_DATA_TABLE_ENTRY,
+                                     InLoadOrderLinks);
+
+        /* FIXME: ROS HACK. Make sure this is a driver */
+        if (!RtlImageNtHeader(LdrEntry->DllBase))
+        {
+            /* Skip this entry */
+            NextEntry= NextEntry->Flink;
+            continue;
+        }
+
+        /* Calculate the size we'll need and allocate a copy */
+        EntrySize = sizeof(LDR_DATA_TABLE_ENTRY) +
+                    LdrEntry->BaseDllName.MaximumLength +
+                    sizeof(UNICODE_NULL);
+        NewEntry = ExAllocatePoolWithTag(NonPagedPool, EntrySize, TAG_LDR_WSTR);
+        if (!NewEntry) return FALSE;
+
+        /* Copy the entry over */
+        *NewEntry = *LdrEntry;
+
+        /* Allocate the name */
+        NewEntry->FullDllName.Buffer =
+            ExAllocatePoolWithTag(PagedPool,
+                                  LdrEntry->FullDllName.MaximumLength +
+                                  sizeof(UNICODE_NULL),
+                                  TAG_LDR_WSTR);
+        if (!NewEntry->FullDllName.Buffer) return FALSE;
+
+        /* Set the base name */
+        NewEntry->BaseDllName.Buffer = (PVOID)(NewEntry + 1);
+
+        /* Copy the full and base name */
+        RtlCopyMemory(NewEntry->FullDllName.Buffer,
+                      LdrEntry->FullDllName.Buffer,
+                      LdrEntry->FullDllName.MaximumLength);
+        RtlCopyMemory(NewEntry->BaseDllName.Buffer,
+                      LdrEntry->BaseDllName.Buffer,
+                      LdrEntry->BaseDllName.MaximumLength);
+
+        /* Null-terminate the base name */
+        NewEntry->BaseDllName.Buffer[NewEntry->BaseDllName.Length /
+                                     sizeof(WCHAR)] = UNICODE_NULL;
+
+        /* Insert the entry into the list */
+        InsertTailList(&PsLoadedModuleList, &NewEntry->InLoadOrderLinks);
+        NextEntry = NextEntry->Flink;
+    }
+
+    /* Build the import lists for the boot drivers */
+    //MiBuildImportsForBootDrivers();
+
+    /* We're done */
+    return TRUE;
+}




More information about the Ros-diffs mailing list