Author: sir_richard Date: Tue Jan 19 19:27:24 2010 New Revision: 45152
URL: http://svn.reactos.org/svn/reactos?rev=45152&view=rev Log: [FREELDR]: Jump to a standard 1-parameter STDCALL kernel entrypoint instead of a FASTCALL double-parameter entrypoint. [NTOS]: Make KiSystemStartup the real C entrypoint of the kernel, and move the "Am I being booted by FreeLDR" logic inside it -- it will then call KiRosPrepareForSystemStartup as earlier. [NTOS]: Move the Double Fault and Boot Stack declaration in C code, with the proper alignment attribute. [NTOS]: Although the concern that KiSystemStartup cannot be 100% C since it modifies ESP is real (Thomas' original fix of Alex's code), we don't need that much of it in assembly. Instead, write a simple trampoline (KiSwitchToBootStack) inline which switches stacks and jumps to a second-stage C function. [NTOS]: Completely remove boot.S as it isn't needed anymore, ReactOS startup is back to being (nearly) 100% C.
Removed: trunk/reactos/ntoskrnl/ke/i386/boot.S Modified: trunk/reactos/boot/freeldr/freeldr/arch/i386/loader.c trunk/reactos/boot/freeldr/freeldr/include/reactos.h trunk/reactos/include/reactos/rosldr.h trunk/reactos/ntoskrnl/include/internal/ke.h trunk/reactos/ntoskrnl/include/internal/trap_x.h trunk/reactos/ntoskrnl/ke/freeldr.c trunk/reactos/ntoskrnl/ke/i386/cpu.c trunk/reactos/ntoskrnl/ke/i386/kiinit.c trunk/reactos/ntoskrnl/ntoskrnl-generic.rbuild
Modified: trunk/reactos/boot/freeldr/freeldr/arch/i386/loader.c URL: http://svn.reactos.org/svn/reactos/trunk/reactos/boot/freeldr/freeldr/arch/i... ============================================================================== --- trunk/reactos/boot/freeldr/freeldr/arch/i386/loader.c [iso-8859-1] (original) +++ trunk/reactos/boot/freeldr/freeldr/arch/i386/loader.c [iso-8859-1] Tue Jan 19 19:27:24 2010 @@ -32,6 +32,7 @@ extern PAGE_DIRECTORY_X86 kuser_pagetable; extern ULONG_PTR KernelBase; extern ROS_KERNEL_ENTRY_POINT KernelEntryPoint; + /* FUNCTIONS *****************************************************************/
/*++ @@ -97,7 +98,7 @@ __writecr0(__readcr0() | CR0_PG | CR0_WP);
/* Jump to Kernel */ - (*KernelEntryPoint)(Magic, &LoaderBlock); + (*KernelEntryPoint)(&LoaderBlock); }
/*++
Modified: trunk/reactos/boot/freeldr/freeldr/include/reactos.h URL: http://svn.reactos.org/svn/reactos/trunk/reactos/boot/freeldr/freeldr/includ... ============================================================================== --- trunk/reactos/boot/freeldr/freeldr/include/reactos.h [iso-8859-1] (original) +++ trunk/reactos/boot/freeldr/freeldr/include/reactos.h [iso-8859-1] Tue Jan 19 19:27:24 2010 @@ -103,7 +103,7 @@ ULONG_PTR NTAPI FrLdrLoadModule(PFILE ModuleImage, LPCSTR ModuleName, PULONG ModuleSize); BOOLEAN NTAPI FrLdrCloseModule(ULONG_PTR ModuleBase, ULONG dwModuleSize); VOID NTAPI FrLdrStartup(ULONG Magic); -typedef VOID (FASTCALL *ROS_KERNEL_ENTRY_POINT)(ULONG Magic, PROS_LOADER_PARAMETER_BLOCK LoaderBlock); +typedef VOID (NTAPI *ROS_KERNEL_ENTRY_POINT)(IN PROS_LOADER_PARAMETER_BLOCK LoaderBlock);
PVOID NTAPI
Modified: trunk/reactos/include/reactos/rosldr.h URL: http://svn.reactos.org/svn/reactos/trunk/reactos/include/reactos/rosldr.h?re... ============================================================================== --- trunk/reactos/include/reactos/rosldr.h [iso-8859-1] (original) +++ trunk/reactos/include/reactos/rosldr.h [iso-8859-1] Tue Jan 19 19:27:24 2010 @@ -48,4 +48,10 @@ ULONG (*FrLdrDbgPrint)(const char *Format, ...); } ROS_LOADER_PARAMETER_BLOCK, *PROS_LOADER_PARAMETER_BLOCK;
+VOID +NTAPI +KiRosPrepareForSystemStartup( + IN PROS_LOADER_PARAMETER_BLOCK LoaderBlock +); + #endif
Modified: trunk/reactos/ntoskrnl/include/internal/ke.h URL: http://svn.reactos.org/svn/reactos/trunk/reactos/ntoskrnl/include/internal/k... ============================================================================== --- trunk/reactos/ntoskrnl/include/internal/ke.h [iso-8859-1] (original) +++ trunk/reactos/ntoskrnl/include/internal/ke.h [iso-8859-1] Tue Jan 19 19:27:24 2010 @@ -103,8 +103,7 @@ extern PULONG KiInterruptTemplateDispatch; extern PULONG KiInterruptTemplate2ndDispatch; extern ULONG KiUnexpectedEntrySize; -extern UCHAR P0BootStack[]; -extern UCHAR KiDoubleFaultStack[]; +extern ULONG_PTR KiDoubleFaultStack; extern EX_PUSH_LOCK KernelAddressSpaceLock; extern ULONG KiMaximumDpcQueueDepth; extern ULONG KiMinimumDpcRate; @@ -812,7 +811,7 @@
VOID NTAPI -KiSystemStartupReal( +KiSystemStartup( IN PLOADER_PARAMETER_BLOCK LoaderBlock );
@@ -1119,6 +1118,7 @@ );
VOID +FASTCALL KiIdleLoop( VOID );
Modified: trunk/reactos/ntoskrnl/include/internal/trap_x.h URL: http://svn.reactos.org/svn/reactos/trunk/reactos/ntoskrnl/include/internal/t... ============================================================================== --- trunk/reactos/ntoskrnl/include/internal/trap_x.h [iso-8859-1] (original) +++ trunk/reactos/ntoskrnl/include/internal/trap_x.h [iso-8859-1] Tue Jan 19 19:27:24 2010 @@ -10,7 +10,7 @@ // Debug Macros // VOID -NTAPI +FORCEINLINE KiDumpTrapFrame(IN PKTRAP_FRAME TrapFrame) { /* Dump the whole thing */ @@ -475,3 +475,22 @@
return Result; } + +VOID +FORCEINLINE +KiSwitchToBootStack(IN ULONG_PTR InitialStack) +{ + /* We have to switch to a new stack before continuing kernel initialization */ + __asm__ __volatile__ + ( + "movl %0, %%esp\n" + "subl %1, %%esp\n" + "pushl %2\n" + "jmp _KiSystemStartupBootStack@0\n" + : + : "c"(InitialStack), + "i"(NPX_FRAME_LENGTH + KTRAP_FRAME_ALIGN + KTRAP_FRAME_LENGTH), + "i"(CR0_EM | CR0_TS | CR0_MP) + : "%esp" + ); +}
Modified: trunk/reactos/ntoskrnl/ke/freeldr.c URL: http://svn.reactos.org/svn/reactos/trunk/reactos/ntoskrnl/ke/freeldr.c?rev=4... ============================================================================== --- trunk/reactos/ntoskrnl/ke/freeldr.c [iso-8859-1] (original) +++ trunk/reactos/ntoskrnl/ke/freeldr.c [iso-8859-1] Tue Jan 19 19:27:24 2010 @@ -1319,9 +1319,8 @@ KiSetupSyscallHandler();
VOID -FASTCALL -KiRosPrepareForSystemStartup(IN ULONG Dummy, - IN PROS_LOADER_PARAMETER_BLOCK LoaderBlock) +NTAPI +KiRosPrepareForSystemStartup(IN PROS_LOADER_PARAMETER_BLOCK LoaderBlock) { PLOADER_PARAMETER_BLOCK NtLoaderBlock; ULONG size, i = 0, *ent; @@ -1411,5 +1410,5 @@ #endif
/* Do general System Startup */ - KiSystemStartupReal(NtLoaderBlock); + KiSystemStartup(NtLoaderBlock); }
Removed: trunk/reactos/ntoskrnl/ke/i386/boot.S URL: http://svn.reactos.org/svn/reactos/trunk/reactos/ntoskrnl/ke/i386/boot.S?rev... ============================================================================== --- trunk/reactos/ntoskrnl/ke/i386/boot.S [iso-8859-1] (original) +++ trunk/reactos/ntoskrnl/ke/i386/boot.S (removed) @@ -1,80 +1,0 @@ -/* - * FILE: ntoskrnl/ke/i386/boot.S - * COPYRIGHT: See COPYING in the top level directory - * PURPOSE: FreeLDR Wrapper Bootstrap Code and Bootstrap Trampoline - * PROGRAMMERs: Alex Ionescu (alex@relsoft.net) - * Thomas Weidenmueller w3seek@reactos.org - */ - -/* INCLUDES ******************************************************************/ - -#include <asm.h> -.intel_syntax noprefix - -/* GLOBALS *******************************************************************/ - -.bss -.align 16 - -/* Kernel Boot Stack */ -.globl _P0BootStack -.space KERNEL_STACK_SIZE -_P0BootStack: - -/* Kernel Double-Fault and Temporary DPC Stack */ -.globl _KiDoubleFaultStack -.space KERNEL_STACK_SIZE -_KiDoubleFaultStack: - -/* FUNCTIONS *****************************************************************/ - -.text -.globl _KiSystemStartup -.func KiSystemStartup -_KiSystemStartup: - - /* NTLDR Boot: Call the main kernel initialization */ - test dword ptr [esp+4], 0x80000000 - jnz _KiSystemStartupReal@4 - - /* FREELDR Boot: Call the FreeLDR wrapper */ - jmp @KiRosPrepareForSystemStartup@8 -.endfunc - -.globl _KiSetupStackAndInitializeKernel@24 -.func KiSetupStackAndInitializeKernel@24 -_KiSetupStackAndInitializeKernel@24: - - /* Save current stack */ - mov esi, esp - - /* Setup the new stack */ - mov esp, [esp+12] - sub esp, NPX_FRAME_LENGTH + KTRAP_FRAME_ALIGN + KTRAP_FRAME_LENGTH - push CR0_EM + CR0_TS + CR0_MP - - /* Copy all parameters to the new stack */ - push [esi+24] - push [esi+20] - push [esi+16] - push [esi+12] - push [esi+8] - push [esi+4] - xor ebp, ebp - call _KiInitializeKernel@24 - - /* Set the priority of this thread to 0 */ - mov ebx, PCR[KPCR_CURRENT_THREAD] - mov byte ptr [ebx+KTHREAD_PRIORITY], 0 - - /* Force interrupts enabled and lower IRQL back to DISPATCH_LEVEL */ - sti - mov ecx, DISPATCH_LEVEL - call @KfLowerIrql@4 - - /* Set the right wait IRQL */ - mov byte ptr [ebx+KTHREAD_WAIT_IRQL], DISPATCH_LEVEL; - - /* Jump into the idle loop */ - jmp @KiIdleLoop@0 -.endfunc
Modified: trunk/reactos/ntoskrnl/ke/i386/cpu.c URL: http://svn.reactos.org/svn/reactos/trunk/reactos/ntoskrnl/ke/i386/cpu.c?rev=... ============================================================================== --- trunk/reactos/ntoskrnl/ke/i386/cpu.c [iso-8859-1] (original) +++ trunk/reactos/ntoskrnl/ke/i386/cpu.c [iso-8859-1] Tue Jan 19 19:27:24 2010 @@ -649,8 +649,8 @@ Tss = (PKTSS)KiDoubleFaultTSS; KiInitializeTSS(Tss); Tss->CR3 = __readcr3(); - Tss->Esp0 = PtrToUlong(KiDoubleFaultStack); - Tss->Esp = PtrToUlong(KiDoubleFaultStack); + Tss->Esp0 = KiDoubleFaultStack; + Tss->Esp = KiDoubleFaultStack; Tss->Eip = PtrToUlong(KiTrap08); Tss->Cs = KGDT_R0_CODE; Tss->Fs = KGDT_R0_PCR; @@ -679,8 +679,8 @@ Tss = (PKTSS)KiNMITSS; KiInitializeTSS(Tss); Tss->CR3 = __readcr3(); - Tss->Esp0 = PtrToUlong(KiDoubleFaultStack); - Tss->Esp = PtrToUlong(KiDoubleFaultStack); + Tss->Esp0 = KiDoubleFaultStack; + Tss->Esp = KiDoubleFaultStack; Tss->Eip = PtrToUlong(KiTrap02); Tss->Cs = KGDT_R0_CODE; Tss->Fs = KGDT_R0_PCR;
Modified: trunk/reactos/ntoskrnl/ke/i386/kiinit.c URL: http://svn.reactos.org/svn/reactos/trunk/reactos/ntoskrnl/ke/i386/kiinit.c?r... ============================================================================== --- trunk/reactos/ntoskrnl/ke/i386/kiinit.c [iso-8859-1] (original) +++ trunk/reactos/ntoskrnl/ke/i386/kiinit.c [iso-8859-1] Tue Jan 19 19:27:24 2010 @@ -11,8 +11,15 @@ #include <ntoskrnl.h> #define NDEBUG #include <debug.h> +#include "internal/trap_x.h"
/* GLOBALS *******************************************************************/ + +/* Boot and double-fault/NMI/DPC stack */ +UCHAR P0BootStackData[KERNEL_STACK_SIZE] __attribute__((aligned (16))); +UCHAR KiDoubleFaultStackData[KERNEL_STACK_SIZE] __attribute__((aligned (16))); +ULONG_PTR P0BootStack = (ULONG_PTR)&P0BootStackData[KERNEL_STACK_SIZE]; +ULONG_PTR KiDoubleFaultStack = (ULONG_PTR)&KiDoubleFaultStackData[KERNEL_STACK_SIZE];
/* Spinlocks used only on X86 */ KSPIN_LOCK KiFreezeExecutionLock; @@ -642,7 +649,36 @@
VOID NTAPI -KiSystemStartupReal(IN PLOADER_PARAMETER_BLOCK LoaderBlock) +KiSystemStartupBootStack(VOID) +{ + PKTHREAD Thread; + + /* Initialize the kernel for the current CPU */ + KiInitializeKernel(&KiInitialProcess.Pcb, + (PKTHREAD)KeLoaderBlock->Thread, + (PVOID)(KeLoaderBlock->KernelStack & ~3), + (PKPRCB)__readfsdword(KPCR_PRCB), + KeNumberProcessors - 1, + KeLoaderBlock); + + /* Set the priority of this thread to 0 */ + Thread = KeGetCurrentThread(); + Thread->Priority = 0; + + /* Force interrupts enabled and lower IRQL back to DISPATCH_LEVEL */ + _enable(); + KfLowerIrql(DISPATCH_LEVEL); + + /* Set the right wait IRQL */ + Thread->WaitIrql = DISPATCH_LEVEL; + + /* Jump into the idle loop */ + KiIdleLoop(); +} + +VOID +NTAPI +KiSystemStartup(IN PLOADER_PARAMETER_BLOCK LoaderBlock) { ULONG Cpu; PKTHREAD InitialThread; @@ -652,6 +688,9 @@ KIDTENTRY NmiEntry, DoubleFaultEntry; PKTSS Tss; PKIPCR Pcr; + + /* Check if we are being booted from FreeLDR */ + if (!((ULONG_PTR)LoaderBlock & 0x80000000)) KiRosPrepareForSystemStartup((PROS_LOADER_PARAMETER_BLOCK)LoaderBlock);
/* Save the loader block and get the current CPU */ KeLoaderBlock = LoaderBlock; @@ -694,7 +733,7 @@ Gdt, Tss, InitialThread, - KiDoubleFaultStack); + (PVOID)KiDoubleFaultStack);
/* Set us as the current process */ InitialThread->ApcState.Process = &KiInitialProcess.Pcb; @@ -758,14 +797,6 @@ /* Raise to HIGH_LEVEL */ KfRaiseIrql(HIGH_LEVEL);
- /* Align stack and make space for the trap frame and NPX frame */ - InitialStack &= ~(KTRAP_FRAME_ALIGN - 1); - /* Switch to new kernel stack and start kernel bootstrapping */ - KiSetupStackAndInitializeKernel(&KiInitialProcess.Pcb, - InitialThread, - (PVOID)InitialStack, - (PKPRCB)__readfsdword(KPCR_PRCB), - (CCHAR)Cpu, - KeLoaderBlock); -} + KiSwitchToBootStack(InitialStack & ~3); +}
Modified: trunk/reactos/ntoskrnl/ntoskrnl-generic.rbuild URL: http://svn.reactos.org/svn/reactos/trunk/reactos/ntoskrnl/ntoskrnl-generic.r... ============================================================================== --- trunk/reactos/ntoskrnl/ntoskrnl-generic.rbuild [iso-8859-1] (original) +++ trunk/reactos/ntoskrnl/ntoskrnl-generic.rbuild [iso-8859-1] Tue Jan 19 19:27:24 2010 @@ -38,7 +38,6 @@ <directory name="ke"> <if property="ARCH" value="i386"> <directory name="i386"> - <file first="true">boot.S</file> <file>abios.c</file> <file>cpu.c</file> <file>ctxswitch.S</file>