📄 winldr.c
字号:
Status = WinLdrCheckForLoadedDll(LoaderBlock, DllName, DriverDTE);
if (Status)
{
// We've got the pointer to its DTE, just return success
return TRUE;
}
// It's not loaded, we have to load it
sprintf(FullPath,"%s%wZ", BootPath, FilePath);
Status = WinLdrLoadImage(FullPath, &DriverBase);
if (!Status)
return FALSE;
// Allocate a DTE for it
Status = WinLdrAllocateDataTableEntry(LoaderBlock, DllName, DllName, DriverBase, DriverDTE);
if (!Status)
{
DbgPrint((DPRINT_WINDOWS, "WinLdrAllocateDataTableEntry() failed\n"));
return FALSE;
}
// Modify any flags, if needed
(*DriverDTE)->Flags |= Flags;
// Look for any dependencies it may have, and load them too
sprintf(FullPath,"%s%s", BootPath, DriverPath);
Status = WinLdrScanImportDescriptorTable(LoaderBlock, FullPath, *DriverDTE);
if (!Status)
{
DbgPrint((DPRINT_WINDOWS, "WinLdrScanImportDescriptorTable() failed for %s\n",
FullPath));
return FALSE;
}
return TRUE;
}
BOOLEAN
WinLdrLoadBootDrivers(PLOADER_PARAMETER_BLOCK LoaderBlock,
LPSTR BootPath)
{
PLIST_ENTRY NextBd;
PBOOT_DRIVER_LIST_ENTRY BootDriver;
BOOLEAN Status;
// Walk through the boot drivers list
NextBd = LoaderBlock->BootDriverListHead.Flink;
while (NextBd != &LoaderBlock->BootDriverListHead)
{
BootDriver = CONTAINING_RECORD(NextBd, BOOT_DRIVER_LIST_ENTRY, ListEntry);
//DbgPrint((DPRINT_WINDOWS, "BootDriver %wZ DTE %08X RegPath: %wZ\n", &BootDriver->FilePath,
// BootDriver->DataTableEntry, &BootDriver->RegistryPath));
// Paths are relative (FIXME: Are they always relative?)
// Load it
Status = WinLdrLoadDeviceDriver(LoaderBlock, BootPath, &BootDriver->FilePath,
0, &BootDriver->DataTableEntry);
// If loading failed - cry loudly
//FIXME: Maybe remove it from the list and try to continue?
if (!Status)
{
UiMessageBox("Can't load boot driver!");
return FALSE;
}
NextBd = BootDriver->ListEntry.Flink;
}
return TRUE;
}
VOID
LoadAndBootWindows(PCSTR OperatingSystemName, WORD OperatingSystemVersion)
{
CHAR MsgBuffer[256];
CHAR SystemPath[1024], SearchPath[1024];
CHAR FileName[1024];
CHAR BootPath[256];
PVOID NtosBase = NULL, HalBase = NULL, KdComBase = NULL;
BOOLEAN Status;
ULONG SectionId;
ULONG BootDevice;
PLOADER_PARAMETER_BLOCK LoaderBlock, LoaderBlockVA;
KERNEL_ENTRY_POINT KiSystemStartup;
PLDR_DATA_TABLE_ENTRY KernelDTE, HalDTE, KdComDTE = NULL;
// Mm-related things
PVOID GdtIdt;
ULONG PcrBasePage=0;
ULONG TssBasePage=0;
//sprintf(MsgBuffer,"Booting Microsoft(R) Windows(R) OS version '%04x' is not implemented yet", OperatingSystemVersion);
//UiMessageBox(MsgBuffer);
// Open the operating system section
// specified in the .ini file
if (!IniOpenSection(OperatingSystemName, &SectionId))
{
sprintf(MsgBuffer,"Operating System section '%s' not found in freeldr.ini", OperatingSystemName);
UiMessageBox(MsgBuffer);
return;
}
UiDrawBackdrop();
UiDrawStatusText("Detecting Hardware...");
UiDrawProgressBarCenter(1, 100, "Loading Windows...");
//FIXME: This is needed only for MachHwDetect() which performs registry operations!
RegInitializeRegistry();
/* Make sure the system path is set in the .ini file */
if (!IniReadSettingByName(SectionId, "SystemPath", SystemPath, sizeof(SystemPath)))
{
UiMessageBox("System path not specified for selected operating system.");
return;
}
if (!MachDiskNormalizeSystemPath(SystemPath,
sizeof(SystemPath)))
{
UiMessageBox("Invalid system path");
return;
}
/* Detect hardware */
MachHwDetect();
UiDrawStatusText("Loading...");
/* Try to open system drive */
BootDevice = 0xffffffff;
if (!FsOpenSystemVolume(SystemPath, BootPath, &BootDevice))
{
UiMessageBox("Failed to open boot drive.");
return;
}
/* append a backslash */
if ((strlen(BootPath)==0) ||
BootPath[strlen(BootPath)] != '\\')
strcat(BootPath, "\\");
DbgPrint((DPRINT_WINDOWS,"SystemRoot: '%s'\n", BootPath));
// Allocate and minimalistic-initialize LPB
AllocateAndInitLPB(&LoaderBlock);
// Load kernel
strcpy(FileName, BootPath);
strcat(FileName, "SYSTEM32\\NTOSKRNL.EXE");
Status = WinLdrLoadImage(FileName, &NtosBase);
DbgPrint((DPRINT_WINDOWS, "Ntos loaded with status %d at %p\n", Status, NtosBase));
// Load HAL
strcpy(FileName, BootPath);
strcat(FileName, "SYSTEM32\\HAL.DLL");
Status = WinLdrLoadImage(FileName, &HalBase);
DbgPrint((DPRINT_WINDOWS, "HAL loaded with status %d at %p\n", Status, HalBase));
// Load kernel-debugger support dll
if (OperatingSystemVersion > _WIN32_WINNT_NT4)
{
strcpy(FileName, BootPath);
strcat(FileName, "SYSTEM32\\KDCOM.DLL");
Status = WinLdrLoadImage(FileName, &KdComBase);
DbgPrint((DPRINT_WINDOWS, "KdCom loaded with status %d at %p\n", Status, KdComBase));
}
// Allocate data table entries for above-loaded modules
WinLdrAllocateDataTableEntry(LoaderBlock, "ntoskrnl.exe",
"WINNT\\SYSTEM32\\NTOSKRNL.EXE", NtosBase, &KernelDTE);
WinLdrAllocateDataTableEntry(LoaderBlock, "hal.dll",
"WINNT\\SYSTEM32\\HAL.DLL", HalBase, &HalDTE);
if (OperatingSystemVersion > _WIN32_WINNT_NT4)
{
WinLdrAllocateDataTableEntry(LoaderBlock, "kdcom.dll",
"WINNT\\SYSTEM32\\KDCOM.DLL", KdComBase, &KdComDTE);
}
/* Load all referenced DLLs for kernel, HAL and kdcom.dll */
strcpy(SearchPath, BootPath);
strcat(SearchPath, "SYSTEM32\\");
WinLdrScanImportDescriptorTable(LoaderBlock, SearchPath, KernelDTE);
WinLdrScanImportDescriptorTable(LoaderBlock, SearchPath, HalDTE);
if (KdComDTE)
WinLdrScanImportDescriptorTable(LoaderBlock, SearchPath, KdComDTE);
/* Load Hive, and then NLS data, OEM font, and prepare boot drivers list */
Status = WinLdrLoadAndScanSystemHive(LoaderBlock, BootPath);
DbgPrint((DPRINT_WINDOWS, "SYSTEM hive loaded and scanned with status %d\n", Status));
/* Load boot drivers */
Status = WinLdrLoadBootDrivers(LoaderBlock, BootPath);
DbgPrint((DPRINT_WINDOWS, "Boot drivers loaded with status %d\n", Status));
/* Initialize Phase 1 - no drivers loading anymore */
WinLdrInitializePhase1(LoaderBlock);
/* Alloc PCR, TSS, do magic things with the GDT/IDT */
WinLdrSetupForNt(LoaderBlock, &GdtIdt, &PcrBasePage, &TssBasePage);
/* Save entry-point pointer (VA) */
KiSystemStartup = (KERNEL_ENTRY_POINT)KernelDTE->EntryPoint;
LoaderBlockVA = PaToVa(LoaderBlock);
/* Debugging... */
//DumpMemoryAllocMap();
/* Turn on paging mode of CPU*/
WinLdrTurnOnPaging(LoaderBlock, PcrBasePage, TssBasePage, GdtIdt);
DbgPrint((DPRINT_WINDOWS, "Hello from paged mode, KiSystemStartup %p, LoaderBlockVA %p!\n",
KiSystemStartup, LoaderBlockVA));
WinLdrpDumpMemoryDescriptors(LoaderBlockVA);
WinLdrpDumpBootDriver(LoaderBlockVA);
WinLdrpDumpArcDisks(LoaderBlockVA);
//FIXME: If I substitute this debugging checkpoint, GCC will "optimize away" the code below
//while (1) {};
/*asm(".intel_syntax noprefix\n");
asm("test1:\n");
asm("jmp test1\n");
asm(".att_syntax\n");*/
(*KiSystemStartup)(LoaderBlockVA);
return;
}
VOID
WinLdrpDumpMemoryDescriptors(PLOADER_PARAMETER_BLOCK LoaderBlock)
{
PLIST_ENTRY NextMd;
PMEMORY_ALLOCATION_DESCRIPTOR MemoryDescriptor;
NextMd = LoaderBlock->MemoryDescriptorListHead.Flink;
while (NextMd != &LoaderBlock->MemoryDescriptorListHead)
{
MemoryDescriptor = CONTAINING_RECORD(NextMd, MEMORY_ALLOCATION_DESCRIPTOR, ListEntry);
DbgPrint((DPRINT_WINDOWS, "BP %08X PC %04X MT %d\n", MemoryDescriptor->BasePage,
MemoryDescriptor->PageCount, MemoryDescriptor->MemoryType));
NextMd = MemoryDescriptor->ListEntry.Flink;
}
}
VOID
WinLdrpDumpBootDriver(PLOADER_PARAMETER_BLOCK LoaderBlock)
{
PLIST_ENTRY NextBd;
PBOOT_DRIVER_LIST_ENTRY BootDriver;
NextBd = LoaderBlock->BootDriverListHead.Flink;
while (NextBd != &LoaderBlock->BootDriverListHead)
{
BootDriver = CONTAINING_RECORD(NextBd, BOOT_DRIVER_LIST_ENTRY, ListEntry);
DbgPrint((DPRINT_WINDOWS, "BootDriver %wZ DTE %08X RegPath: %wZ\n", &BootDriver->FilePath,
BootDriver->DataTableEntry, &BootDriver->RegistryPath));
NextBd = BootDriver->ListEntry.Flink;
}
}
VOID
WinLdrpDumpArcDisks(PLOADER_PARAMETER_BLOCK LoaderBlock)
{
PLIST_ENTRY NextBd;
PARC_DISK_SIGNATURE ArcDisk;
NextBd = LoaderBlock->ArcDiskInformation->DiskSignatureListHead.Flink;
while (NextBd != &LoaderBlock->ArcDiskInformation->DiskSignatureListHead)
{
ArcDisk = CONTAINING_RECORD(NextBd, ARC_DISK_SIGNATURE, ListEntry);
DbgPrint((DPRINT_WINDOWS, "ArcDisk %s checksum: 0x%X, signature: 0x%X\n",
ArcDisk->ArcName, ArcDisk->CheckSum, ArcDisk->Signature));
NextBd = ArcDisk->ListEntry.Flink;
}
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -