Testing paging and entering userland

This commit is contained in:
vanten-s 2025-02-25 18:48:58 +01:00
parent 64f29facc5
commit 98b4afb451
10 changed files with 96 additions and 22 deletions

View file

@ -124,6 +124,19 @@ _start:
# Set up the stack.
mov $stack_top, %esp
# Setup the GDT
call gdt_init
jmp $0x08,$reload_CS
reload_CS:
mov $0x10, %ax
mov %ax, %ds
mov %ax, %es
mov %ax, %fs
mov %ax, %gs
mov %ax, %ss
# Enter the high-level kernel.
call kernel_main

View file

@ -132,6 +132,9 @@ static void add_exceptions()
entry = generate_entry(true, divide_by_zero, 0xF, 0, 0x8);
add_entry(entry, DivisionByZero);
entry = generate_entry(true, page_fault, 0xF, 0, 0x8);
add_entry(entry, PageFault);
entry = generate_entry(true, general_protection_fault, 0xF, 0, 0x8);
add_entry(entry, GenerProtFault);

View file

@ -23,12 +23,14 @@ static void stack_trace()
__attribute__((interrupt)) void divide_by_zero(struct interrupt_frame*)
{
asm("cli");
terminal_writestring("Yo dude u cant divide by zero yao\n");
while (1) { }
}
__attribute__((interrupt)) void general_protection_fault(struct interrupt_frame*)
{
asm("cli");
terminal_writestring("GPF handler called\n");
while (1) {
asm("cli");
@ -38,6 +40,7 @@ __attribute__((interrupt)) void general_protection_fault(struct interrupt_frame*
__attribute__((interrupt)) void double_fault(struct interrupt_frame*)
{
asm("cli");
stack_trace();
terminal_writestring("2 Errors in a row, u better behave naughty naughty\n");
while (1) {
@ -48,10 +51,18 @@ __attribute__((interrupt)) void double_fault(struct interrupt_frame*)
__attribute__((interrupt)) void exception(struct interrupt_frame*)
{
asm("cli");
terminal_writestring("Some weird error code stuff\n");
while (1) { }
}
__attribute__((interrupt)) void page_fault(struct interrupt_frame*)
{
asm("cli");
terminal_writestring("Page Fault\n");
while (1) { }
}
__attribute__((interrupt)) void keyboard_interrupt(struct interrupt_frame*)
{
terminal_writestring("Keyboard Interrupt\n");

View file

@ -11,6 +11,7 @@ struct interrupt_frame {
__attribute__((interrupt)) void divide_by_zero(struct interrupt_frame* frame);
__attribute__((interrupt)) void general_protection_fault(struct interrupt_frame* frame);
__attribute__((interrupt)) void double_fault(struct interrupt_frame* frame);
__attribute__((interrupt)) void page_fault(struct interrupt_frame* frame);
__attribute__((interrupt)) void exception(struct interrupt_frame* frame);

View file

@ -4,6 +4,8 @@
#include <kernel/paging.h>
#include <kernel/tty.h>
#include <debugging.h>
#include <kernel/heap.h>
struct x86_Page_Directory {
bool present: 1;
@ -15,7 +17,7 @@ struct x86_Page_Directory {
bool available_2: 1;
bool page_size: 1;
uint8_t available_1 : 4;
uint32_t address : 20; // Multiply by 0x1000
uintptr_t address : 20; // Multiply by 0x1000
} __attribute__((packed));
struct x86_Page_Table {
@ -29,22 +31,66 @@ struct x86_Page_Table {
bool page_attribute_table: 1;
bool global: 1;
uint8_t available_1 : 3;
uint32_t address : 20; // Multiply by 0x1000
uintptr_t address : 20; // Multiply by 0x1000
} __attribute__((packed));
extern struct x86_Page_Directory boot_page_directory[1024] __attribute__((aligned(4096)));
static struct x86_Page_Table user_code_table __attribute__((aligned(4096)));
static uint8_t user_code[4096] __attribute__((aligned(4096)));
static struct x86_Page_Table user_data_table __attribute__((aligned(4096)));
static uint8_t user_data[4096] __attribute__((aligned(4096)));
static struct x86_Page_Table* get_table(uint16_t index) {
struct x86_Page_Table* table = (struct x86_Page_Table*)(boot_page_directory[index].address * 0x1000 + 0xC0000000);
struct x86_Page_Table* table = (struct x86_Page_Table*)((boot_page_directory[index].address << 12) + 0xC0000000);
return table;
}
void setup_paging() {
struct x86_Page_Table* kernel = get_table(768);
for (int i = 0; i < 1024; i++) {
if (kernel[i].address != 0) {
struct x86_Page_Table test = kernel[i];
}
}
static void reload_pages () {
asm("\
movl %cr3, %ecx; \
movl %ecx, %cr3; \
");
}
static void set_page_directory_entry(uintptr_t address, struct x86_Page_Table* table) {
boot_page_directory[address >> 22].address = ((uintptr_t)(table) - 0xC0000000) >> 12;
boot_page_directory[address >> 22].present = true;
boot_page_directory[address >> 22].read_write = true;
}
void setup_paging() {
struct x86_Page_Table* kernel = get_table(768);
uint16_t i = 0;
while (kernel[i].present == 0) {
i++;
}
terminal_writestring("Kernel Start Page: ");
print_hex_bytes(&i, 2);
while (kernel[i].present != 0) {
i++;
}
terminal_writestring("\nKernel End Page: ");
print_hex_bytes(&i, 2);
terminal_putchar('\n');
set_page_directory_entry(0, &user_code_table);
user_code_table.address = ((uintptr_t)user_code - 0xC0000000) >> 12;
user_code_table.present = true;
user_code_table.read_write = true;
user_code_table.user_supervisor = true;
set_page_directory_entry(0x00400000, &user_data_table);
user_data_table.address = ((uintptr_t)user_data - 0xC0000000) >> 12;
user_data_table.present = true;
user_data_table.read_write = true;
user_data_table.user_supervisor = true;
reload_pages();
}

View file

@ -19,14 +19,14 @@ extern void jump_to_userspace();
void run_program(uint8_t* code, size_t code_length, uint8_t* data, size_t data_length)
{
uint8_t* userland_code = (uint8_t*) 0x00000000;
uint8_t* userland_data = (uint8_t*) 0x00800000;
uint8_t* userland_data = (uint8_t*) 0x00400000;
memcpy(userland_code, code, code_length);
memcpy(userland_data, data, data_length);
struct CPUState target = {
.eip = (size_t) userland_code,
.esp = 0x00000000,
.esp = 0x00400000,
.eax = 0,
.ebx = 0,
.ecx = 0,

View file

@ -3,7 +3,7 @@
#include <kernel/heap.h>
#include <debugging.h>
#define HEAP_SIZE (4096)
#define HEAP_SIZE (1 << 12)
uint8_t* global_heap_data[HEAP_SIZE + sizeof(struct Heap_Block)];
struct Heap_Metadata global_heap;

View file

@ -14,13 +14,7 @@
#endif
uint8_t program[] = {
// 0xba, 0x01, 0x00, 0x00, 0x00, // mov 1, %edx
0xb8, 0x00, 0x00, 0xC0, 0x00, // mov $buffer, %eax
// 0xcd, 0x80, // int 0x80
0xb9, 0x00, 0x00, 0x00, 0x00, // mov 0, %ecx
0xcd, 0x80, // int 0x80
0xb9, 0x00, 0x00, 0x80, 0x00, // mov $start, %ecx
0xff, 0xe1, // jmp *%ecx
};
uint8_t data[] = "Hello From Userspace\n";
@ -39,11 +33,14 @@ void kernel_main(void)
setup_tasks();
setup_paging();
asm("sti");
asm("cli");
run_program(program, sizeof(program), data, sizeof(data));
asm("sti");
while (true) {
terminal_writestring("Hello from Kernelspace\n");
terminal_writestring("Hello from Kernelspace 1\n");
terminal_writestring("Hello from Kernelspace 2\n");
}
}

View file

@ -25,6 +25,7 @@ static void input(char* buffer)
void _syscall(uint32_t a, uint32_t b, uint32_t c)
{
/*
switch (c) {
case 0x00:
print((char*) a);
@ -33,4 +34,6 @@ void _syscall(uint32_t a, uint32_t b, uint32_t c)
input((char*) a);
break;
}
*/
terminal_writestring("waow :3");
}

View file

@ -159,7 +159,7 @@ void _switch_task(
size_t ds_passed
)
{
terminal_writestring("Switching task\n");
// terminal_writestring("Switching task\n");
if (num_tasks == 0) {
return;
};