3 #include "../../include/arch/pc/x86common.h"
5 #define IMAGE_DOS_HEADER_e_lfanew 60
6 #define IMAGE_FILE_HEADER_SIZE 20
7 #define IMAGE_OPTIONAL_HEADER_AddressOfEntryPoint 16
12 #include "fathelp.inc"
19 /* Setup segment registers */
28 mov sp, word ptr ds:stack16
30 /* Enable A20 address line */
33 /* Safe real mode entry point in shared memory */
34 mov dword ptr [BSS_RealModeEntry], offset switch_to_real16
36 /* Get address of optional header */
37 mov eax, dword ptr ds:[FREELDR_PE_BASE + IMAGE_DOS_HEADER_e_lfanew]
38 add eax, FREELDR_PE_BASE + 4 + IMAGE_FILE_HEADER_SIZE
40 /* Get address of entry point */
41 mov eax, dword ptr ds:[eax + IMAGE_OPTIONAL_HEADER_AddressOfEntryPoint]
42 add eax, FREELDR_PE_BASE
44 /* Patch the long jump instruction */
45 mov word ptr [pm_offset], ax
50 /* This is the entry point from protected mode */
53 /* Restore segment registers to correct limit */
61 /* Disable Protected Mode */
66 /* Clear prefetch queue & correct CS */
70 /* Set real mode segments */
78 /* Clear out the high 16-bits of ESP */
79 /* This is needed because I have one */
80 /* machine that hangs when booted to dos if */
81 /* anything other than 0x0000 is in the high */
82 /* 16-bits of ESP. Even though real-mode */
83 /* code should only use SP and not ESP. */
86 /* Restore real mode stack */
87 mov sp, word ptr ds:[stack16]
89 /* Load IDTR with real mode value */
92 sti /* These are ok now */
94 /* Do the callback, specified by bx */
96 call word ptr ds:[callback_table + bx]
100 * Switches the processor to protected mode
107 /* Safe current stack pointer */
108 mov word ptr ds:[stack16], sp
113 /* Enable Protected Mode */
118 /* Clear prefetch queue & correct CS */
119 .byte HEX(0ea) // jmp far PMODE_CS:entry_point
121 .word 0 // receives address of PE entry point
124 // FIXME: use ljmp16 PMODE_CS:inpmode + hexed 32bit jump
131 .word ChainLoadBiosBootSectorCode
133 .word PnpBiosGetDeviceNodeCount
134 .word PnpBiosGetDeviceNode
137 /* 16-bit stack pointer */
142 .align 4 /* force 4-byte alignment */
144 /* NULL Descriptor */
162 /* 16-bit real mode CS */
168 /* 16-bit real mode DS */
174 /* GDT table pointer */
176 .word HEX(27) /* Limit */
177 .long gdt /* Base Address */
179 /* Real-mode IDT pointer */
181 .word HEX(3ff) /* Limit */
182 .long 0 /* Base Address */
186 #include "int386.inc"
189 #include "helpers.inc"
191 .org (FREELDR_PE_BASE - FREELDR_BASE)