source: grub-pc/trunk/fuentes/grub-core/boot/i386/pc/startup_raw.S @ 22

Last change on this file since 22 was 22, checked in by mabarracus, 4 years ago

updated version and apply net.ifnames=0 into debian/rules

File size: 7.5 KB
Line 
1/*
2 *  GRUB  --  GRand Unified Bootloader
3 *  Copyright (C) 1999,2000,2001,2002,2003,2005,2006,2007,2008,2009,2011 Free Software Foundation, Inc.
4 *
5 *  GRUB 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 3 of the License, or
8 *  (at your option) any later version.
9 *
10 *  GRUB 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
16 *  along with GRUB.  If not, see <http://www.gnu.org/licenses/>.
17 */
18
19#include <config.h>
20#include <grub/symbol.h>
21#include <grub/offsets.h>
22#include <grub/machine/boot.h>
23#include <grub/machine/memory.h>
24#include <grub/machine/kernel.h>
25
26#define ABS(x)  ((x) - LOCAL (base) + GRUB_BOOT_MACHINE_KERNEL_ADDR + 0x200)
27
28        .file   "startup_raw.S"
29
30        .text
31
32        /* Tell GAS to generate 16-bit instructions so that this code works
33           in real mode. */
34        .code16
35
36        .globl  start, _start
37start:
38_start:
39LOCAL (base):
40        /*
41         *  Guarantee that "main" is loaded at 0x0:0x8200.
42         */
43#ifdef __APPLE__
44        ljmp $0, $(ABS(LOCAL (codestart)) - 0x10000)
45#else
46        ljmp $0, $ABS(LOCAL (codestart))
47#endif
48
49        /*
50         *  This is a special data area.
51         */
52
53        . = _start + GRUB_DECOMPRESSOR_MACHINE_COMPRESSED_SIZE
54LOCAL(compressed_size):
55        .long 0
56        . = _start + GRUB_DECOMPRESSOR_MACHINE_UNCOMPRESSED_SIZE
57LOCAL(uncompressed_size):
58        .long 0
59
60        . = _start + GRUB_KERNEL_I386_PC_REED_SOLOMON_REDUNDANCY
61reed_solomon_redundancy:
62        .long   0
63        . = _start + GRUB_KERNEL_I386_PC_NO_REED_SOLOMON_LENGTH
64        .short  (LOCAL(reed_solomon_part) - _start)
65
66/*
67 *  This is the area for all of the special variables.
68 */
69        . = _start + GRUB_DECOMPRESSOR_I386_PC_BOOT_DEVICE
70LOCAL(boot_dev):
71        .byte   0xFF, 0xFF, 0xFF
72LOCAL(boot_drive):
73        .byte   0x00
74
75/* the real mode code continues... */
76LOCAL (codestart):
77        cli             /* we're not safe here! */
78
79        /* set up %ds, %ss, and %es */
80        xorw    %ax, %ax
81        movw    %ax, %ds
82        movw    %ax, %ss
83        movw    %ax, %es
84
85        /* set up the real mode/BIOS stack */
86        movl    $GRUB_MEMORY_MACHINE_REAL_STACK, %ebp
87        movl    %ebp, %esp
88
89        sti             /* we're safe again */
90
91        /* save the boot drive */
92        ADDR32  movb    %dl, LOCAL(boot_drive)
93
94        /* reset disk system (%ah = 0) */
95        int     $0x13
96
97        /* transition to protected mode */
98        DATA32  call real_to_prot
99
100        /* The ".code32" directive takes GAS out of 16-bit mode. */
101        .code32
102
103        cld
104        call    grub_gate_a20
105
106        movl    LOCAL(compressed_size), %edx
107#ifdef __APPLE__
108        addl    $decompressor_end, %edx
109        subl    $(LOCAL(reed_solomon_part)), %edx
110#else
111        addl    $(LOCAL(decompressor_end) - LOCAL(reed_solomon_part)), %edx
112#endif
113        movl    reed_solomon_redundancy, %ecx
114        leal    LOCAL(reed_solomon_part), %eax
115        cld
116        call    EXT_C (grub_reed_solomon_recover)
117        jmp     post_reed_solomon
118
119#include "../../../kern/i386/realmode.S"
120
121#include <rs_decoder.h>
122
123        .text
124
125/*
126 * grub_gate_a20(void)
127 *
128 * Gate address-line 20 for high memory.
129 *
130 * This routine is probably overconservative in what it does, but so what?
131 *
132 * It also eats any keystrokes in the keyboard buffer.  :-(
133 */
134
135grub_gate_a20: 
136gate_a20_test_current_state:
137        /* first of all, test if already in a good state */
138        call    gate_a20_check_state
139        testb   %al, %al
140        jnz     gate_a20_try_bios
141        ret
142
143gate_a20_try_bios:
144        /* second, try a BIOS call */
145        pushl   %ebp
146        call    prot_to_real
147
148        .code16
149        movw    $0x2401, %ax
150        int     $0x15
151
152        DATA32  call    real_to_prot
153        .code32
154
155        popl    %ebp
156        call    gate_a20_check_state
157        testb   %al, %al
158        jnz     gate_a20_try_system_control_port_a
159        ret
160
161gate_a20_try_system_control_port_a:
162        /*
163         * In macbook, the keyboard test would hang the machine, so we move
164         * this forward.
165         */
166        /* fourth, try the system control port A */
167        inb     $0x92
168        andb    $(~0x03), %al
169        orb     $0x02, %al
170        outb    $0x92
171
172        call    gate_a20_check_state
173        testb   %al, %al
174        jnz     gate_a20_try_keyboard_controller
175        ret
176
177gate_a20_flush_keyboard_buffer:
178        inb     $0x64
179        andb    $0x02, %al
180        jnz     gate_a20_flush_keyboard_buffer
1812:
182        inb     $0x64
183        andb    $0x01, %al
184        jz      3f
185        inb     $0x60
186        jmp     2b
1873:
188        ret
189
190gate_a20_try_keyboard_controller:
191        /* third, try the keyboard controller */
192        call    gate_a20_flush_keyboard_buffer
193
194        movb    $0xd1, %al
195        outb    $0x64
1964:
197        inb     $0x64
198        andb    $0x02, %al
199        jnz     4b
200
201        movb    $0xdf, %al
202        outb    $0x60
203        call    gate_a20_flush_keyboard_buffer
204
205        /* output a dummy command (USB keyboard hack) */
206        movb    $0xff, %al
207        outb    $0x64
208        call    gate_a20_flush_keyboard_buffer
209
210        call    gate_a20_check_state
211        testb   %al, %al
212        /* everything failed, so restart from the beginning */
213        jnz     gate_a20_try_bios
214        ret
215
216gate_a20_check_state:
217        /* iterate the checking for a while */
218        movl    $100, %ecx
2191:
220        call    3f
221        testb   %al, %al
222        jz      2f
223        loop    1b
2242:
225        ret
2263:
227        pushl   %ebx
228        pushl   %ecx
229        xorl    %eax, %eax
230        /* compare the byte at 0x8000 with that at 0x108000 */
231        movl    $GRUB_BOOT_MACHINE_KERNEL_ADDR, %ebx
232        pushl   %ebx
233        /* save the original byte in CL */
234        movb    (%ebx), %cl
235        /* store the value at 0x108000 in AL */
236        addl    $0x100000, %ebx
237        movb    (%ebx), %al
238        /* try to set one less value at 0x8000 */
239        popl    %ebx
240        movb    %al, %ch
241        decb    %ch
242        movb    %ch, (%ebx)
243        /* serialize */
244        outb    %al, $0x80
245        outb    %al, $0x80
246        /* obtain the value at 0x108000 in CH */
247        pushl   %ebx
248        addl    $0x100000, %ebx
249        movb    (%ebx), %ch
250        /* this result is 0 if A20 is on or 1 if it is off */
251        subb    %ch, %al
252        /* restore the original */
253        popl    %ebx
254        movb    %cl, (%ebx)
255        popl    %ecx
256        popl    %ebx
257        ret
258
259LOCAL(reed_solomon_part):
260
261/*
262 * Support for booting GRUB from a Multiboot boot loader (e.g. GRUB itself).
263 * This uses the a.out kludge to load raw binary to the area starting at 1MB,
264 * and relocates itself after loaded.
265 */
266        .p2align        2       /* force 4-byte alignment */
267multiboot_header:
268        /* magic */
269        .long   0x1BADB002
270        /* flags */
271        .long   (1 << 16)
272        /* checksum */
273        .long   -0x1BADB002 - (1 << 16)
274        /* header addr */
275        .long   multiboot_header - _start + 0x100000 + 0x200
276        /* load addr */
277        .long   0x100000
278        /* load end addr */
279        .long   0
280        /* bss end addr */
281        .long   0
282        /* entry addr */
283        .long   multiboot_entry - _start + 0x100000 + 0x200
284
285multiboot_entry:
286        .code32
287        /* obtain the boot device */
288        movl    12(%ebx), %edx
289
290        movl    $GRUB_MEMORY_MACHINE_PROT_STACK, %ebp
291        movl    %ebp, %esp
292
293        /* relocate the code */
294#ifdef __APPLE__
295        LOCAL(compressed_size_offset) = LOCAL(compressed_size) - LOCAL(base)
296        movl    $0x200, %ecx
297        addl    $decompressor_end, %ecx
298        subl    $LOCAL(base), %ecx
299        addl    LOCAL(compressed_size_offset) + 0x100000 + 0x200, %ecx
300#else
301        movl    $(LOCAL(decompressor_end) - _start + 0x200), %ecx
302        addl    LOCAL(compressed_size) - _start + 0x100000 + 0x200, %ecx
303#endif
304        movl    $0x100000, %esi
305        movl    $GRUB_BOOT_MACHINE_KERNEL_ADDR, %edi
306        cld
307        rep
308        movsb
309        /* jump to the real address */
310        movl    $multiboot_trampoline, %eax
311        jmp     *%eax
312
313multiboot_trampoline:
314        /* fill the boot information */
315        movl    %edx, LOCAL(boot_dev)
316        shrl    $24, %edx
317        /* enter the usual booting */
318        call    prot_to_real
319        .code16
320        jmp     LOCAL (codestart)
321        .code32
322
323post_reed_solomon:
324
325#ifdef ENABLE_LZMA
326        movl    $GRUB_MEMORY_MACHINE_DECOMPRESSION_ADDR, %edi
327#ifdef __APPLE__
328        movl    $decompressor_end, %esi
329#else
330        movl    $LOCAL(decompressor_end), %esi
331#endif
332        pushl   %edi
333        movl    LOCAL (uncompressed_size), %ecx
334        leal    (%edi, %ecx), %ebx
335        /* Don't remove this push: it's an argument.  */
336        push    %ecx
337        call    _LzmaDecodeA
338        pop     %ecx
339        /* _LzmaDecodeA clears DF, so no need to run cld */
340        popl    %esi
341#endif
342
343        movl    LOCAL(boot_dev), %edx
344        movl    $prot_to_real, %edi
345        movl    $real_to_prot, %ecx
346        movl    $LOCAL(realidt), %eax
347        jmp     *%esi
348
349#ifdef ENABLE_LZMA
350#include "lzma_decode.S"
351#endif
352
353        .p2align 4
354
355#ifdef __APPLE__
356        .zerofill __DATA, __aa_before_bss, decompressor_end, 10, 0
357#else
358        .bss
359LOCAL(decompressor_end):
360#endif
Note: See TracBrowser for help on using the repository browser.