[FREELDR]
[reactos.git] / reactos / boot / freeldr / freeldr / arch / i386 / entry.S
1 /*
2 * FreeLoader
3 * Copyright (C) 1998-2002 Brian Palmer <brianp@sginet.com>
4 *
5 * This program is free software; you can redistribute it and/or modify
6 * it under the terms of the GNU General Public License as published by
7 * the Free Software Foundation; either version 2 of the License, or
8 * (at your option) any later version.
9 *
10 * This program is distributed in the hope that it will be useful,
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 * GNU General Public License for more details.
14 *
15 * You should have received a copy of the GNU General Public License along
16 * with this program; if not, write to the Free Software Foundation, Inc.,
17 * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
18 */
19
20 #include <asm.inc>
21 #include <arch/pc/x86common.h>
22
23 EXTERN _BootMain:PROC
24 EXTERN _InitIdt:PROC
25 EXTERN _i386Idt:DWORD
26 //EXTERN _i386idtptr:FWORD
27
28 .code32
29
30 PUBLIC _RealEntryPoint
31 _RealEntryPoint:
32
33 /* Setup segment selectors */
34 mov ax, PMODE_DS
35 mov ds, ax
36 mov es, ax
37 mov fs, ax
38 mov gs, ax
39 mov ss, ax
40
41 /* Setup protected mode stack */
42 mov esp, dword ptr ds:[stack32]
43
44 /* Load the IDT */
45 #ifdef _USE_ML
46 lidt fword ptr ds:[i386idtptr]
47 #else
48 lidt i386idtptr
49 #endif
50
51 /* Continue execution */
52 jmp dword ptr ds:[ContinueAddress]
53
54 ContinueAddress:
55 .long _FrldrStartup
56
57
58 _FrldrStartup:
59
60 /* Store BootDrive and BootPartition */
61 mov byte ptr ds:[_FrldrBootDrive], dl
62 xor eax, eax
63 mov al, dh
64 mov dword ptr ds:[_FrldrBootPartition], eax
65
66 /* Patch long jump with real mode entry point */
67 mov eax, dword ptr ds:[BSS_RealModeEntry]
68 mov dword ptr ds:[SwitchToReal16Address], eax
69
70 /* Initialize the idt */
71 call _InitIdt
72
73 #ifndef _USE_ML
74 /* Clean out bss */
75 xor eax, eax
76 mov edi, offset __bss_start__
77 mov ecx, offset __bss_end__ + 3
78 sub ecx, edi
79 shr ecx, 2
80 rep stosd
81
82 /* Pass the command line to BootMain */
83 mov eax, offset cmdline
84 #else
85 xor eax, eax
86 #endif
87
88 /* GO! */
89 push eax
90 call _BootMain
91
92 /* We should never get here */
93 stop:
94 jmp stop
95 nop
96 nop
97
98 Int386_regsin:
99 .long 0
100 Int386_regsout:
101 .long 0
102
103 /*
104 * int Int386(int ivec, REGS* in, REGS* out);
105 */
106 PUBLIC _Int386
107 _Int386:
108
109 /* Get the function parameters */
110 mov eax, dword ptr [esp + 4]
111 mov dword ptr ds:[BSS_IntVector], eax
112 mov eax, dword ptr [esp + 8]
113 mov dword ptr [Int386_regsin], eax
114 mov eax, dword ptr [esp + 12]
115 mov dword ptr [Int386_regsout], eax
116
117 /* Save all registers + segment registers */
118 push ds
119 push es
120 push fs
121 push gs
122 pusha
123
124 /* Copy input registers */
125 mov esi, dword ptr [Int386_regsin]
126 mov edi, BSS_RegisterSet
127 mov ecx, REGS_SIZE / 4
128 rep movsd
129
130 /* Set the function ID */
131 mov bx, FNID_Int386
132
133 /* Set continue address and switch to real mode */
134 mov dword ptr [ContinueAddress], offset Int386_return
135 jmp SwitchToReal
136
137 Int386_return:
138
139 /* Copy output registers */
140 mov esi, BSS_RegisterSet
141 mov edi, dword ptr [Int386_regsout]
142 mov ecx, REGS_SIZE / 4
143 rep movsd
144
145 popa
146 pop gs
147 pop fs
148 pop es
149 pop ds
150 ret
151
152
153 /*
154 * U16 PxeCallApi(U16 Segment, U16 Offset, U16 Service, VOID *Parameter);
155 *
156 * RETURNS:
157 */
158 PUBLIC _PxeCallApi
159 _PxeCallApi:
160 push ebp
161 mov ebp, esp
162
163 pusha
164 push es
165
166 /* copy entry point */
167 mov eax, [ebp + 8]
168 shl eax, 16
169 mov ax, [ebp + 12]
170 mov dword ptr ds:[BSS_PxeEntryPoint], eax
171
172 /* copy function */
173 mov ax, [ebp + 16]
174 mov word ptr ds:[BSS_PxeFunction], ax
175
176 /* convert pointer to data buffer to segment/offset */
177 mov eax, [ebp + 20]
178 shr eax, 4
179 and eax, HEX(0f000)
180 mov word ptr ds:[BSS_PxeBufferSegment], ax
181 mov eax, [ebp + 20]
182 and eax, HEX(0ffff)
183 mov word ptr ds:[BSS_PxeBufferOffset], ax
184
185 /* Set the function ID and call realmode */
186 mov bx, FNID_PxeCallApi
187 call i386CallRealMode
188
189 pop es
190 popa
191
192 mov esp, ebp
193 pop ebp
194
195 mov ax, word ptr [BSS_PxeResult]
196
197 ret
198
199
200 PUBLIC _SoftReboot
201 _SoftReboot:
202 /* Set the function ID */
203 mov bx, FNID_SoftReboot
204
205 /*Switch to real mode (We don't return) */
206 jmp SwitchToReal
207
208
209 PUBLIC _ChainLoadBiosBootSectorCode
210 _ChainLoadBiosBootSectorCode:
211 /* Set the boot drive */
212 mov dl, byte ptr [_FrldrBootDrive]
213
214 /* Set the function ID */
215 mov bx, FNID_ChainLoadBiosBootSectorCode
216
217 /*Switch to real mode (We don't return) */
218 jmp SwitchToReal
219
220
221 PUBLIC i386CallRealMode
222 i386CallRealMode:
223 /* Set continue address and switch to real mode */
224 mov dword ptr [ContinueAddress], offset i386CallRealMode_return
225 jmp SwitchToReal
226 i386CallRealMode_return:
227 ret
228
229
230 /* Entrypoint for realmode function calls
231 * ContinueAddress must be set to the return point from realmode
232 * bx must be set to the ID of the realmode function to call. */
233 SwitchToReal:
234 /* Set sane segments */
235 mov ax, PMODE_DS
236 mov ds, ax
237 mov es, ax
238 mov fs, ax
239 mov gs, ax
240 mov ss, ax
241
242 /* Save 32-bit stack pointer */
243 mov dword ptr [stack32], esp
244
245 /* jmp to 16-bit segment to set the limit correctly */
246 .byte HEX(0ea) // jmp far RMODE_CS:switch_to_real16
247 SwitchToReal16Address:
248 .long 0 // receives address of switch_to_real16
249 .word RMODE_CS
250 nop
251
252
253 /* 16-bit stack pointer */
254 stack16:
255 .word STACK16ADDR
256
257 /* 32-bit stack pointer */
258 stack32:
259 .long STACK32ADDR
260
261 .align 4 /* force 4-byte alignment */
262 gdt:
263 /* NULL Descriptor */
264 .word HEX(0000)
265 .word HEX(0000)
266 .word HEX(0000)
267 .word HEX(0000)
268
269 /* 32-bit flat CS */
270 .word HEX(FFFF)
271 .word HEX(0000)
272 .word HEX(9A00)
273 .word HEX(00CF)
274
275 /* 32-bit flat DS */
276 .word HEX(FFFF)
277 .word HEX(0000)
278 .word HEX(9200)
279 .word HEX(00CF)
280
281 /* 16-bit real mode CS */
282 .word HEX(FFFF)
283 .word HEX(0000)
284 .word HEX(9E00)
285 .word HEX(0000)
286
287 /* 16-bit real mode DS */
288 .word HEX(FFFF)
289 .word HEX(0000)
290 .word HEX(9200)
291 .word HEX(0000)
292
293 /* GDT table pointer */
294 gdtptr:
295 .word HEX(27) /* Limit */
296 .long gdt /* Base Address */
297
298 /* Real-mode IDT pointer */
299 rmode_idtptr:
300 .word HEX(3ff) /* Limit */
301 .long 0 /* Base Address */
302
303 PUBLIC i386idtptr
304 i386idtptr:
305 .word 255 /* Limit */
306 .long _i386Idt /* Base Address */
307
308 PUBLIC _FrldrBootDrive
309 _FrldrBootDrive:
310 .byte 0
311
312 PUBLIC _FrldrBootPartition
313 _FrldrBootPartition:
314 .long 0
315
316 END