diff --git a/linker.ld b/linker.ld index cfb6ff1..37b5f48 100644 --- a/linker.ld +++ b/linker.ld @@ -1,30 +1,25 @@ ENTRY(_start) +KERNEL_VIRT_BASE = 0xC0000000; +KERNEL_PHYS_BASE = 0x00100000; + SECTIONS { - . = ALIGN(8); - .boot : { - KEEP(*(.multiboot)) + . = KERNEL_VIRT_BASE; + + .text : AT(KERNEL_PHYS_BASE) { + *(.text) } - . = 1M; /* Load kernel at 1MB */ - .text BLOCK(4K) : ALIGN(4K) - { - *(.text) - } + .rodata : AT(KERNEL_PHYS_BASE + (ADDR(.rodata) - KERNEL_VIRT_BASE)) { + *(.rodata) + } - .rodata BLOCK(4K) : ALIGN(4K) - { - *(.rodata) - } + .data : AT(KERNEL_PHYS_BASE + (ADDR(.data) - KERNEL_VIRT_BASE)) { + *(.data) + } - .data BLOCK(4K) : ALIGN(4K) - { - *(.data) - } - - .bss BLOCK(4K) : ALIGN(4K) - { - *(COMMON) - *(.bss) - } + .bss : AT(KERNEL_PHYS_BASE + (ADDR(.bss) - KERNEL_VIRT_BASE)) { + *(COMMON) + *(.bss) + } } \ No newline at end of file diff --git a/src/bootload/GDT.asm b/src/bootload/GDT.asm index 67323e2..d3187a4 100644 --- a/src/bootload/GDT.asm +++ b/src/bootload/GDT.asm @@ -22,7 +22,7 @@ gdt_end: gdt_descriptor: dw gdt_end - gdt_start - 1 - dd gdt_start + dd gdt_start - 0xC0000000 + 0x00100000 ; paging, thank me later. CODE_SEG equ gdt_code - gdt_start DATA_SEG equ gdt_data - gdt_start \ No newline at end of file diff --git a/src/bootload/boot.asm b/src/bootload/boot.asm index 6c9b583..7cce3de 100644 --- a/src/bootload/boot.asm +++ b/src/bootload/boot.asm @@ -1,8 +1,17 @@ +; TODO: +; load GDT [x] +; enter long m. [x] +; enable paging [x] +; fix damn grub parameter passing [x] + ; constants for multiboot MAGIC equ 0xE85250D6 ARCH equ 0 ; 0 for i386, 4 for MIPS HDRLEN equ 24 ; Total length: 4 fields + end tag CHECKSUM equ -(MAGIC + ARCH + HDRLEN) +KERNEL_VIRT_BASE equ 0xC0000000 +KERNEL_PHYS_BASE equ 0x00100000 +KERNEL_OFFSET equ (-KERNEL_VIRT_BASE)+KERNEL_PHYS_BASE section .multiboot_header align 8 @@ -25,6 +34,16 @@ stack_bottom: resb 16384 ; 16 KiB is reserved for stack stack_top: +align 4096 +PAG_mainPD: + resd 1024 +align 4096 +PAG_identityPT: + resd 1024 +align 4096 +PAG_kernelPT: + resd 1024 + section .rodata %include "src/bootload/GDT.asm" @@ -32,24 +51,12 @@ section .text ; entrypoint for bootloader [BITS 32] global _start:function (_start.end - _start) _start: - ; To set up a stack, we set the esp register to point to the top of our - ; stack (as it grows downwards on x86 systems). This is necessarily done - ; in assembly as languages such as C cannot function without a stack. - mov esp, stack_top - mov ebp, esp - - mov ecx, eax ; move multiboot magic number to ecx - - ; TODO: - ; load GDT [x] - ; enter long m. [ ] - ; init FPU [ ] - - ; load GDT cli - lgdt [gdt_descriptor] - jmp CODE_SEG:.final ; if I get problems, check this line here, future me! + lgdt [gdt_descriptor + KERNEL_OFFSET] + jmp CODE_SEG:.final + KERNEL_OFFSET ; if I get problems, check this line here, future me! .final: + mov edx, eax ; we need the boot shit from grub still + ; so now eax -> edx and ebx -> ebx mov AX, DATA_SEG ; data segment selectors mov DS, AX mov ES, AX @@ -57,8 +64,53 @@ _start: mov GS, AX mov SS, AX - push ecx ; magic number - push ebx ; info structure + mov ecx, 1024 ; 1024 * 4KB = 4MB + mov edi, PAG_identityPT + KERNEL_OFFSET + mov eax, 0 + + .fill_identity: + mov [edi], eax + or dword [edi], 0x3 + add eax, 0x1000 + add edi, 4 + loop .fill_identity + + mov ecx, 1024 + mov edi, PAG_kernelPT + KERNEL_OFFSET + mov eax, KERNEL_PHYS_BASE + + .fill_kernel: + mov [edi], eax + or dword [edi], 0x3 + add eax, 0x1000 + add edi, 4 + loop .fill_kernel + + ; identity PT = entry 0 + mov eax, PAG_identityPT + KERNEL_OFFSET + or eax, 0x3 + mov [PAG_mainPD + KERNEL_OFFSET + 0*4], eax + + ; kernel PT = entry 768 + mov eax, PAG_kernelPT + KERNEL_OFFSET + or eax, 0x3 + mov [PAG_mainPD + KERNEL_OFFSET + 768*4], eax + + mov eax, PAG_mainPD + KERNEL_OFFSET + mov cr3, eax + mov eax, cr0 + or eax, 0x80000000 + mov cr0, eax + + jmp .pagingfinished +.pagingfinished + ; fix stack once again and since we need to keep the contents, we just add an offset + mov esp, stack_top + mov ebp, stack_bottom + + push edx + push ebx + extern kernel_main call kernel_main add esp, 8 ; remove arguments diff --git a/src/headers/paging.h b/src/headers/paging.h index e69de29..66a1989 100644 --- a/src/headers/paging.h +++ b/src/headers/paging.h @@ -0,0 +1,9 @@ +#include "stddef.h" +#include "stdlib.h" + +typedef uint32_t PAG_PT_entry_t; +typedef PAG_PT_entry_t PAG_PT_t[1024]; +typedef PAG_PT_t PAG_PD_t[1024]; + +extern PAG_PD_t PAG_mainPD; + diff --git a/src/kernel/entry.c b/src/kernel/entry.c index 1649da7..c472f36 100644 --- a/src/kernel/entry.c +++ b/src/kernel/entry.c @@ -32,15 +32,9 @@ void kernel_main(struct multiboot_info* header, uint32_t magic) { kputstr("Hello JPOS, World!\n"); - if (magic != MULTIBOOT2_BOOTLOADER_MAGIC) { - kputstr("Invalid magic from bootloader.\n"); - return; - } - - kputstr("Got past magic check.\n"); - kputstr("Entering Graphics mode: "); VGA_switch(VGA_values); + *(uint8_t*)0xA0000 = 1; kputstr("OK\n"); VGA_clear((VGA_pixel){0xFF,0xFF,0xFF}); @@ -56,6 +50,13 @@ void kernel_main(struct multiboot_info* header, uint32_t magic) { } kputstr("OK\n"); + if (magic != MULTIBOOT2_BOOTLOADER_MAGIC) { + kputstr("Invalid magic from bootloader.\n"); + return; + } + + kputstr("Got past magic check.\n"); + kputstr("Setting up IRQs: "); for (uint8_t i=0;i<16;i++) { idt_set_descriptor(i+0x20, irq_stub_table[i], 0x8E); @@ -86,7 +87,5 @@ void kernel_main(struct multiboot_info* header, uint32_t magic) { IRQ_registerhandler(0x00, &tick); - - while (1) {} } \ No newline at end of file