1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
|
#define ASM_FILE
#include <multiboot2.h>
#include "macros.s"
/* Declare a multiboot header that marks this program as a kernel */
.section .multiboot.header, "a"
header_begin:
.align 8
.int MULTIBOOT2_HEADER_MAGIC
.int MULTIBOOT_ARCHITECTURE_I386
.int header_end - header_begin
.int -(MULTIBOOT2_HEADER_MAGIC + MULTIBOOT_ARCHITECTURE_I386 + (header_end - header_begin))
.align 8
header_info_begin:
.short MULTIBOOT_HEADER_TAG_INFORMATION_REQUEST
.short 0 # flags
.int header_info_end - header_info_begin
.int MULTIBOOT_TAG_TYPE_MMAP
header_info_end:
.align 8
.short MULTIBOOT_HEADER_TAG_END
.short 0
.int 8
header_end:
.section .multiboot.pages, "aw", @nobits
.align 4096
bootstrap_page0:
.skip 1024 * 4
.section .multiboot.text, "ax"
.extern k_pagedir
.extern k_stack
.extern k_init
#.global __vaddr_base
#.set __vaddr_base, 0xc0000000
#.global __vaddr_offset
.set __vaddr_offset, 0xc0000000 - 0x2000
.global _start
.type _start, @function
_start:
cli
# check multiboot header
cmp $MULTIBOOT2_BOOTLOADER_MAGIC, %eax
jz c
hlt
c: mov $k_stack - __vaddr_offset, %esp
push %ebx # pointer to multiboot structure
call __multiboot2
# mmap multiboot section into bootstrap page
movl $bootstrap_page0, %edi
movl $1024, %ecx
mmap_section __multiboot_begin, __multiboot_end, PAGE_RW
mmap_section (__text_begin - __vaddr_offset), (__text_end - __vaddr_offset), PAGE_RO
mmap_section (__rodata_begin - __vaddr_offset), (__rodata_end - __vaddr_offset), PAGE_RO
mmap_section (__bss_begin - __vaddr_offset), (__bss_end - __vaddr_offset), PAGE_RW
mmap_section (__data_begin - __vaddr_offset), (__data_end - __vaddr_offset), PAGE_RW
# mmap all the other section into k_ptable0x300
movl $(k_ptable0x300 - __vaddr_offset), %edi
movl $1024, %ecx
mmap_section (__text_begin - __vaddr_offset), (__text_end - __vaddr_offset), PAGE_RO
mmap_section (__rodata_begin - __vaddr_offset), (__rodata_end - __vaddr_offset), PAGE_RO
mmap_section (__bss_begin - __vaddr_offset), (__bss_end - __vaddr_offset), PAGE_RW
mmap_section (__data_begin - __vaddr_offset), (__data_end - __vaddr_offset), PAGE_RW
movl $(bootstrap_page0 + PAGE_RW), k_pagedir - __vaddr_offset + 0 * 4
movl $(k_ptable0x300 - __vaddr_offset + PAGE_RW), k_pagedir - __vaddr_offset + 768 * 4
movl $(k_pagedir - __vaddr_offset), %ecx
movl %ecx, %cr3
# enable paging and the write-protect bit
movl %cr0, %ecx
orl $0x80010000, %ecx
movl %ecx, %cr0
# jump to higher half with an absolute jump
lea (k_init), %ecx
jmp *%ecx
|