Merge branch 'afs' into befs2
[grub2/phcoder.git] / loader / i386 / multiboot_helper.S
blobd7539f193bda0bfae8b92f84b0757f27c3469702
1 /*
2  *  GRUB  --  GRand Unified Bootloader
3  *  Copyright (C) 1999,2000,2001,2002,2003,2005,2006,2007,2008,2009  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  */
19 #include <grub/symbol.h>
20 #include <multiboot.h>
21 #include <multiboot2.h>
23         .p2align        2       /* force 4-byte alignment */
26  * This starts the multiboot kernel.
27  */
29 VARIABLE(grub_multiboot_payload_size)
30         .long   0
31 VARIABLE(grub_multiboot_payload_orig)
32         .long   0
33 VARIABLE(grub_multiboot_payload_dest)
34         .long   0
35 VARIABLE(grub_multiboot_payload_entry_offset)
36         .long   0
39  * The relocators below understand the following parameters:
40  * ecx: Size of the block to be copied.
41  * esi: Where to copy from (always lowest address, even if we're relocating
42  *      backwards).
43  * edi: Where to copy to (likewise).
44  * edx: Offset of the entry point (relative to the beginning of the block).
45  */
47 VARIABLE(grub_multiboot_forward_relocator)
48         /* Add entry offset.  */
49         addl    %edi, %edx
51         /* Forward copy.  */
52         cld
53         rep
54         movsb
56         jmp     *%edx
57 VARIABLE(grub_multiboot_forward_relocator_end)
59 VARIABLE(grub_multiboot_backward_relocator)
60         /* Add entry offset (before %edi is mangled).  */
61         addl    %edi, %edx
63         /* Backward movsb is implicitly off-by-one.  compensate that.  */
64         decl    %esi
65         decl    %edi
67         /* Backward copy.  */
68         std
69         addl    %ecx, %esi
70         addl    %ecx, %edi
71         rep
72         movsb
74         jmp     *%edx
75 VARIABLE(grub_multiboot_backward_relocator_end)
77 FUNCTION(grub_multiboot_real_boot)
78         /* Push the entry address on the stack.  */
79         pushl   %eax
80         /* Move the address of the multiboot information structure to ebx.  */
81         movl    %edx,%ebx
83         /* Interrupts should be disabled.  */
84         cli
86         /* Where do we copy what from.  */
87         movl    EXT_C(grub_multiboot_payload_size), %ecx
88         movl    EXT_C(grub_multiboot_payload_orig), %esi
89         movl    EXT_C(grub_multiboot_payload_dest), %edi
90         movl    EXT_C(grub_multiboot_payload_entry_offset), %edx
92         /* Move the magic value into eax.  */
93         movl    $MULTIBOOT_MAGIC2, %eax
95         /* Jump to the relocator.  */
96         popl    %ebp
97         jmp     *%ebp
100  * This starts the multiboot 2 kernel.
101  */
103 FUNCTION(grub_multiboot2_real_boot)
104         /* Push the entry address on the stack.  */
105         pushl   %eax
106         /* Move the address of the multiboot information structure to ebx.  */
107         movl    %edx,%ebx
109         /* Interrupts should be disabled.  */
110         cli
112         /* Move the magic value into eax and jump to the kernel.  */
113         movl    $MULTIBOOT2_BOOTLOADER_MAGIC,%eax
114         popl    %ecx
115         jmp     *%ecx