From 5f025d18bff04d5affa76cd9cf10c12f73a65dd0 Mon Sep 17 00:00:00 2001 From: rami Date: Sat, 6 Jul 2024 18:00:06 -0400 Subject: [PATCH] task switch progress --- bochsrc | 2 +- include/kernel/task.h | 1 - kernel/init.asm | 22 +++++++++++----------- kernel/kernel.c | 39 +++++++++++++++++++++++++++++++++++---- kernel/pit.c | 11 +++++++++++ 5 files changed, 58 insertions(+), 17 deletions(-) diff --git a/bochsrc b/bochsrc index 387e109..f5de00b 100644 --- a/bochsrc +++ b/bochsrc @@ -2,4 +2,4 @@ ata0-slave: type=cdrom, path=./build/Hazel.iso, status=inserted magic_break: enabled=1 boot: cdrom -display_library: x +display_library: sdl2 diff --git a/include/kernel/task.h b/include/kernel/task.h index 786f61d..72cf9ef 100644 --- a/include/kernel/task.h +++ b/include/kernel/task.h @@ -5,7 +5,6 @@ #include typedef struct { - uint32_t eip; uint32_t esp; uint32_t cr3; uint32_t *next; diff --git a/kernel/init.asm b/kernel/init.asm index 948cb4a..9c3e8b6 100644 --- a/kernel/init.asm +++ b/kernel/init.asm @@ -118,22 +118,22 @@ flush_tss: extern ctx global task_switch task_switch: + ; Save current task's registers push ebx push esi push edi push ebp - mov esi, [ctx+28] - ; Return if only one process is running - mov eax, [esi+12] - cmp eax, 0 - je ret - ; Check if using same virtual memory - cmp [esi+8], [eax+8] - je .ret - mov ecx, [eax+8] - mov cr3, ecx -.ret: + mov edi, [ctx+28] ; EDI = current task + mov esi, [esp+20] ; ESI = next task + ; Save current ESP + mov dword [edi], esp + ; Set current task to next task + mov dword [ctx+28], esi + ; Change to new ESP + mov esp, [esi] + mov ecx, [esi+4] + pop ebp pop edi pop esi diff --git a/kernel/kernel.c b/kernel/kernel.c index f8c12a9..804fa85 100644 --- a/kernel/kernel.c +++ b/kernel/kernel.c @@ -18,6 +18,7 @@ extern uint32_t isr_stub_table[32]; extern void pit_isr(void); extern void jmp_user_mode(uint32_t esp, uint32_t eip); extern void flush_tss(uint32_t segment_selector); +extern void task_switch(task_t *task); extern gdt_t gdt[6]; extern uint32_t boot_page_dir[1024]; extern uint32_t boot_page_tab[1024]; @@ -35,7 +36,7 @@ void sleep(int delay) { cpu_relax; } -void idt_init() { +void idt_init(void) { for (int i = 0; i < 32; i++) { idt_encode_entry(idt, i, isr_stub_table[i], GDT_SEGMENT_SELECTOR(GDT_KERNEL_CODE, RING0), TRAP_GATE_32 | INT_RING0 | INT_PRESENT); } @@ -47,6 +48,13 @@ void idt_init() { asm volatile ("lidt %0" :: "m"(idtr)); } +void test(void) { + for (int i = 0; i < 1000; i++) { + LOG("O"); + } + task_switch((task_t *)ctx.current_task->next); +} + 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 @@ -61,14 +69,12 @@ void kernel(multiboot_info_t *info) { LOG("%d bytes of RAM detected\nCreated a %d byte large physical memory map at 0x%08X\n", ctx.mmap_size*BLOCK_SIZE*8, ctx.mmap_size, (uint32_t)ctx.mmap); idt_init(); - - /* +/* pic_remap(PIC_1_START, PIC_2_START); asm volatile ("sti" ::); ctx.ticks = 0; pit_init(); */ - // Setup TSS uint32_t base = (uint32_t)&tss; uint32_t limit = base + sizeof(tss_t); @@ -87,6 +93,30 @@ void kernel(multiboot_info_t *info) { tss.ss = tss.ds = tss.es = tss.fs = tss.gs = GDT_SEGMENT_SELECTOR(GDT_USER_DATA, RING3); flush_tss(GDT_SEGMENT_SELECTOR(5, RING3)); + task_t task1 = {0}; + task_t task2 = {0}; + task1.cr3 = (uint32_t)boot_page_dir - KERNEL_VMA; + task1.next = (uint32_t *)&task2; + ctx.current_task = &task1; + + uint32_t *stack = mmap_find_first_free_block(); + asm volatile ("mov %%esp, %0" : "=r" (task1.esp)); + stack[1023] = (uint32_t)test; + stack[1022] = 0; + stack[1021] = 0; + stack[1020] = 0; + stack[1019] = 0; + task2.esp = (uint32_t)stack + (0x1000 - 20); + task2.cr3 = (uint32_t)boot_page_dir - KERNEL_VMA; + task2.next = (uint32_t *)&task1; + //task_switch(&task2); + for (int i = 0; i < 1000; i++) { + LOG("_"); + } + task_switch((task_t *)ctx.current_task->next); + task_switch((task_t *)ctx.current_task->next); + + /* multi_mod_t *init = (multi_mod_t *)(info->moduleaddress + KERNEL_VMA); elf_t *elf = (elf_t *)(init->mod_start+KERNEL_VMA); task_t task = {0}; @@ -97,6 +127,7 @@ void kernel(multiboot_info_t *info) { LOG("Switching to ring 3... EIP: 0x%08X ESP: 0x%08X\n", task.eip, task.esp); jmp_user_mode(task.esp, task.eip); + */ halt: for (;;) {} diff --git a/kernel/pit.c b/kernel/pit.c index 9ea19f9..aca8feb 100644 --- a/kernel/pit.c +++ b/kernel/pit.c @@ -12,9 +12,20 @@ void pit_init(void) { outb(PIT_CHAN0_DATA, (uint8_t)((DIVISOR & 0xff00) >> 8)); } +extern void task_switch(task_t *task); + void pit_handler(void) { ctx.ticks++; + if (ctx.current_task->next) { + LOG("TASK SWITCH\n"); + //task_t *old = ctx.current_task; + //task_t *new = (task_t *)ctx.current_task->next; + //new->next = (uint32_t *)old; + //old->next = (uint32_t *)new; + task_switch((task_t *)ctx.current_task->next); + } + outb(PIT_CHAN0_DATA, (uint8_t)(DIVISOR & 0xff)); outb(PIT_CHAN0_DATA, (uint8_t)((DIVISOR & 0xff00) >> 8)); pic_send_eoi(0);