higher half kernel

This commit is contained in:
rami 2024-07-04 22:03:10 -04:00
parent bd20049519
commit b2b1fc59b7
4 changed files with 58 additions and 62 deletions

View File

@ -2,4 +2,4 @@ ata0-slave: type=cdrom, path=./build/Hazel.iso, status=inserted
magic_break: enabled=1
boot: cdrom
display_library: sdl2
display_library: x

View File

@ -4,7 +4,7 @@
%define VID 1<<2
%define FLAGS (ALIGN | MMAP | VID)
section .multiboot
section .multiboot.data
dd MAGIC
dd FLAGS
dd -(MAGIC + FLAGS)
@ -19,7 +19,7 @@ dd 80 ; width
dd 25 ; height
dd 0 ; depth
section .text
section .multiboot.text
global _start
_start:
cli
@ -28,6 +28,37 @@ _start:
cmp eax, 0x2BADB002
jne halt
; Setup table
; Identity page 0-4 mib
mov eax, 0
mov edx, 0
.fill_table:
mov ecx, edx
or ecx, 3
mov [boot_page_tab-0xC0000000+eax*4], ecx
add edx, 0x1000
inc eax
cmp eax, 1024
jne .fill_table
mov ecx, boot_page_tab
sub ecx, 0xC0000000
or ecx, 3
mov [boot_page_dir-0xC0000000], ecx
mov [boot_page_dir-0xC0000000+768*4], ecx
; Enable paging
mov eax, boot_page_dir
sub eax, 0xC0000000
mov cr3, eax
mov eax, cr0
or eax, (1<<31)
mov cr0, eax
jmp higher_half
section .text
higher_half:
; Load GDT
lgdt [gdtp]
; Offset to kernel data descriptor
@ -52,7 +83,6 @@ halt:
global pit_isr
pit_isr:
cli
extern pit_handler
call pit_handler
iret
@ -187,6 +217,11 @@ gdtp:
dw gdt_end - gdt - 1
dd gdt
align 0x1000
boot_page_dir: times 1024 dd 0
align 0x1000
boot_page_tab: times 1024 dd 0
section .bss
align 16
stack_top:

View File

@ -37,9 +37,6 @@ typedef struct {
uint32_t cr3;
} task_t;
__attribute__((aligned(4096))) uint32_t page_dir[1024];
__attribute__((aligned(4096))) uint32_t page_tab[1024];
void kernel(multiboot_info_t *info) {
if (!CHECK_FLAG(info->flags, 3)) goto halt; // Modules
if (!CHECK_FLAG(info->flags, 6)) goto halt; // Memory map
@ -93,31 +90,11 @@ void kernel(multiboot_info_t *info) {
#define PAGE_TAB_INDEX(x) (((x) >> 12) & 0x3FF)
#define PAGE_OFFSET(x) ((x) & 0xFFF)
for (int i = 0; i < 1024; i++) {
page_tab[i] = (i * 0x1000) | PAGE_PRESENT | PAGE_RW | PAGE_USER;
}
for (int i = 0; i < 1024; i++) {
page_dir[i] = ((uint32_t)page_tab) | PAGE_PRESENT | PAGE_RW | PAGE_USER;
}
//enable_paging(page_dir);
asm volatile("mov %0, %%cr3" :: "r" (page_dir));
asm volatile(
"mov %%cr0, %%eax;"
"or $0x80000000, %%eax;"
"mov %%eax, %%cr0;"
:
:
: "%eax"
);
uint32_t stack = (uint32_t)mmap_find_first_free_block();
multi_mod_t *init = (multi_mod_t *)info->moduleaddress;
LOG("Switching to ring 3... EIP: 0x%08X ESP: 0x%08X\n", init->mod_start, stack+0x1000);
jmp_user_mode(stack+0x1000, init->mod_start);
//jmp_user_mode(stack+0x1000, init->mod_start);
halt:
for (;;) {}

View File

@ -1,52 +1,36 @@
/* The bootloader will look at this image and start execution at the symbol
designated as the entry point. */
ENTRY(_start)
/* Tell where the various sections of the object files will be put in the final
kernel image. */
SECTIONS
{
/* It used to be universally recommended to use 1M as a start offset,
as it was effectively guaranteed to be available under BIOS systems.
However, UEFI has made things more complicated, and experimental data
strongly suggests that 2M is a safer place to load. In 2016, a new
feature was introduced to the multiboot2 spec to inform bootloaders
that a kernel can be loaded anywhere within a range of addresses and
will be able to relocate itself to run from such a loader-selected
address, in order to give the loader freedom in selecting a span of
memory which is verified to be available by the firmware, in order to
work around this issue. This does not use that feature, so 2M was
chosen as a safer option than the traditional 1M. */
. = 1M;
/* First put the multiboot header, as it is required to be put very early
in the image or the bootloader won't recognize the file format.
Next we'll put the .text section. */
.text BLOCK(4K) : ALIGN(4K)
{
*(.multiboot)
*(.text)
_kernel_start = .;
.multiboot.data : {
*(.multiboot.data)
}
.multiboot.text : {
*(.multiboot.text)
}
/* Read-only data. */
.rodata BLOCK(4K) : ALIGN(4K)
. += 0xC0000000;
.text ALIGN (4K) : AT (ADDR (.text) - 0xC0000000)
{
*(.text)
}
.rodata ALIGN (4K) : AT (ADDR (.rodata) - 0xC0000000)
{
*(.rodata)
}
/* Read-write data (initialized) */
.data BLOCK(4K) : ALIGN(4K)
.data ALIGN (4K) : AT (ADDR (.data) - 0xC0000000)
{
*(.data)
}
/* Read-write data (uninitialized) and stack */
.bss BLOCK(4K) : ALIGN(4K)
.bss ALIGN (4K) : AT (ADDR (.bss) - 0xC0000000)
{
*(COMMON)
*(.bss)
*(.bootstrap_stack)
}
/* The compiler may produce other sections, by default it will put them in
a segment with the same name. Simply add stuff here as needed. */
_kernel_end = .;
}