From eef40edb3f7d909f73e0de8ab8bafa77e9510222 Mon Sep 17 00:00:00 2001 From: pjht Date: Wed, 22 Jul 2020 19:26:55 -0500 Subject: [PATCH] Portability work --- Makefile | 7 +- init/main.c | 3 +- kernel/cpu/{i386 => }/address_spaces.h | 0 kernel/cpu/arch_consts.h | 13 +++ kernel/cpu/cpu_init.h | 4 +- kernel/cpu/i386/address_spaces.c | 19 ++-- kernel/cpu/i386/arch_consts.h | 13 +++ kernel/cpu/i386/cpu_init.c | 13 +-- kernel/cpu/i386/halt.asm | 5 + kernel/cpu/i386/halt.c | 5 - kernel/cpu/i386/interrupt.asm | 11 ++- kernel/cpu/i386/isr.c | 23 +++-- kernel/cpu/i386/isr.h | 72 -------------- kernel/cpu/i386/paging.c | 27 ++++-- kernel/cpu/i386/ports.h | 12 --- kernel/cpu/i386/serial.c | 9 +- kernel/cpu/i386/tasking_helpers.asm | 7 ++ kernel/cpu/isr.h | 19 ++++ kernel/cpu/{i386 => }/paging.h | 11 +-- kernel/cpu/{i386 => }/serial.h | 0 kernel/cpu/tasking.h | 23 ----- kernel/cpu/{i386 => }/tasking_helpers.h | 1 + kernel/cpu/x86_64/arch_consts.h | 7 ++ kernel/cpu/x86_64/cpu_init.c | 13 +-- kernel/cpu/x86_64/interrupt.asm | 6 +- kernel/cpu/x86_64/isr.c | 61 ++++++------ kernel/cpu/x86_64/isr.h | 74 +------------- kernel/cpu/x86_64/paging.h | 10 -- kernel/cpu/x86_64/pmem.c | 123 ------------------------ kernel/cpu/x86_64/pmem.h | 10 -- kernel/cpu/x86_64/ports.c | 31 ------ kernel/kernel.c | 12 ++- kernel/{cpu/i386 => }/kmalloc.c | 9 +- kernel/{cpu/i386 => }/kmalloc.h | 0 kernel/{cpu/i386 => }/pmem.c | 21 ++-- kernel/{cpu/i386 => }/pmem.h | 0 kernel/{cpu/i386 => }/tasking.c | 30 +++--- kernel/{cpu/i386 => }/tasking.h | 23 ++++- {kernel/cpu/i386 => libc}/ports.c | 0 sysroot/usr/include/tasking.h | 2 +- 40 files changed, 230 insertions(+), 499 deletions(-) rename kernel/cpu/{i386 => }/address_spaces.h (100%) create mode 100644 kernel/cpu/arch_consts.h create mode 100644 kernel/cpu/i386/arch_consts.h create mode 100644 kernel/cpu/i386/halt.asm delete mode 100644 kernel/cpu/i386/halt.c delete mode 100644 kernel/cpu/i386/ports.h create mode 100644 kernel/cpu/isr.h rename kernel/cpu/{i386 => }/paging.h (76%) rename kernel/cpu/{i386 => }/serial.h (100%) delete mode 100644 kernel/cpu/tasking.h rename kernel/cpu/{i386 => }/tasking_helpers.h (79%) create mode 100644 kernel/cpu/x86_64/arch_consts.h delete mode 100644 kernel/cpu/x86_64/paging.h delete mode 100644 kernel/cpu/x86_64/pmem.c delete mode 100644 kernel/cpu/x86_64/pmem.h delete mode 100644 kernel/cpu/x86_64/ports.c rename kernel/{cpu/i386 => }/kmalloc.c (90%) rename kernel/{cpu/i386 => }/kmalloc.h (100%) rename kernel/{cpu/i386 => }/pmem.c (87%) rename kernel/{cpu/i386 => }/pmem.h (100%) rename kernel/{cpu/i386 => }/tasking.c (93%) rename kernel/{cpu/i386 => }/tasking.h (54%) rename {kernel/cpu/i386 => libc}/ports.c (100%) diff --git a/Makefile b/Makefile index 7ef9e2d..8ffb9d3 100644 --- a/Makefile +++ b/Makefile @@ -70,7 +70,12 @@ libc: sysroot/usr/lib/libc.a sysroot/usr/lib/libc.a: $(LIBC_OBJ) @$(AR) rcs $@ $^ -%.o: %.c +kernel/cpu/arch_consts.h: kernel/cpu/$(PLAT)/arch_consts.h + cp kernel/cpu/$(PLAT)/arch_consts.h kernel/cpu/arch_consts.h +kernel/cpu/isr.h: kernel/cpu/$(PLAT)/isr.h + cp kernel/cpu/$(PLAT)/isr.h kernel/cpu/isr.h + +%.o: %.c kernel/cpu/arch_consts.h kernel/cpu/isr.h @$(CC) $(CFLAGS) -c $< -o $@ %.o: %.asm diff --git a/init/main.c b/init/main.c index c5b296a..b64a7f7 100644 --- a/init/main.c +++ b/init/main.c @@ -130,8 +130,9 @@ char load_proc(uint32_t datapos,char* initrd) { // return 1; // } -void thread_func() { +void* thread_func(void* arg) { for (;;) yield(); + return NULL; } int main() { diff --git a/kernel/cpu/i386/address_spaces.h b/kernel/cpu/address_spaces.h similarity index 100% rename from kernel/cpu/i386/address_spaces.h rename to kernel/cpu/address_spaces.h diff --git a/kernel/cpu/arch_consts.h b/kernel/cpu/arch_consts.h new file mode 100644 index 0000000..207780c --- /dev/null +++ b/kernel/cpu/arch_consts.h @@ -0,0 +1,13 @@ +#ifndef ARCH_CONSTS_H +#define ARCH_CONSTS_H + +#define PAGE_SZ 4096 +#define FRAME_SZ PAGE_SZ +#define KMALLOC_START 0xFE800000 +#define KMALLOC_SZ 16384 +#define KSTACKS_START 0xC8000000 +#define NUM_FRAMES 1024*1024 +#define FRAME_NO_OFFSET 12 +#define NUM_KERN_FRAMES 4096 + +#endif diff --git a/kernel/cpu/cpu_init.h b/kernel/cpu/cpu_init.h index 6aa3441..392020c 100644 --- a/kernel/cpu/cpu_init.h +++ b/kernel/cpu/cpu_init.h @@ -1,8 +1,6 @@ #ifndef CPU_INIT_H #define CPU_INIT_H -#include - -void cpu_init(struct multiboot_boot_header_tag* tags); +void cpu_init(); #endif diff --git a/kernel/cpu/i386/address_spaces.c b/kernel/cpu/i386/address_spaces.c index e81498f..93fadfe 100644 --- a/kernel/cpu/i386/address_spaces.c +++ b/kernel/cpu/i386/address_spaces.c @@ -1,21 +1,20 @@ -#include "paging.h" +#include "../paging.h" +#include "arch_consts.h" void address_spaces_copy_data(void* cr3, void* data,uint32_t size,void* virt_addr) { - uint32_t old_cr3; - asm volatile("movl %%cr3, %%eax; movl %%eax, %0;":"=m"(old_cr3)::"%eax"); + void* old_cr3=get_cr3(); void* phys_addr=virt_to_phys(data); - load_smap((uint32_t)cr3); - map_pages(virt_addr,phys_addr,(size/4096)+1,1,1); + load_smap(cr3); + map_pages(virt_addr,phys_addr,(size/PAGE_SZ)+1,1,1); load_smap(old_cr3); } void* address_spaces_put_data(void* cr3, void* data,uint32_t size) { - uint32_t old_cr3; - asm volatile("movl %%cr3, %%eax; movl %%eax, %0;":"=m"(old_cr3)::"%eax"); + void* old_cr3=get_cr3(); void* phys_addr=virt_to_phys(data); - load_smap((uint32_t)cr3); - void* virt_addr=find_free_pages((size/4096)+1); - map_pages(virt_addr,phys_addr,(size/4096)+1,1,1); + load_smap(cr3); + void* virt_addr=find_free_pages((size/PAGE_SZ)+1); + map_pages(virt_addr,phys_addr,(size/PAGE_SZ)+1,1,1); load_smap(old_cr3); return virt_addr; } diff --git a/kernel/cpu/i386/arch_consts.h b/kernel/cpu/i386/arch_consts.h new file mode 100644 index 0000000..207780c --- /dev/null +++ b/kernel/cpu/i386/arch_consts.h @@ -0,0 +1,13 @@ +#ifndef ARCH_CONSTS_H +#define ARCH_CONSTS_H + +#define PAGE_SZ 4096 +#define FRAME_SZ PAGE_SZ +#define KMALLOC_START 0xFE800000 +#define KMALLOC_SZ 16384 +#define KSTACKS_START 0xC8000000 +#define NUM_FRAMES 1024*1024 +#define FRAME_NO_OFFSET 12 +#define NUM_KERN_FRAMES 4096 + +#endif diff --git a/kernel/cpu/i386/cpu_init.c b/kernel/cpu/i386/cpu_init.c index 78c9a8f..6fff686 100644 --- a/kernel/cpu/i386/cpu_init.c +++ b/kernel/cpu/i386/cpu_init.c @@ -1,16 +1,5 @@ #include "gdt.h" -#include "paging.h" -#include "isr.h" -#include "pmem.h" -#include "serial.h" -#include "../tasking.h" -void cpu_init(struct multiboot_boot_header_tag* tags) { +void cpu_init() { gdt_init(); - isr_install(); - asm volatile("sti"); - serial_init(); - pmem_init(tags); - paging_init(); - tasking_init(); } diff --git a/kernel/cpu/i386/halt.asm b/kernel/cpu/i386/halt.asm new file mode 100644 index 0000000..ba33eda --- /dev/null +++ b/kernel/cpu/i386/halt.asm @@ -0,0 +1,5 @@ +global halt +halt: +cli +halt_label: hlt +jmp halt_label diff --git a/kernel/cpu/i386/halt.c b/kernel/cpu/i386/halt.c deleted file mode 100644 index 004c90b..0000000 --- a/kernel/cpu/i386/halt.c +++ /dev/null @@ -1,5 +0,0 @@ -void halt() { - asm volatile("cli;\ - hltlabel: hlt;\ - jmp hltlabel"); -} diff --git a/kernel/cpu/i386/interrupt.asm b/kernel/cpu/i386/interrupt.asm index 8968087..e62a9fb 100644 --- a/kernel/cpu/i386/interrupt.asm +++ b/kernel/cpu/i386/interrupt.asm @@ -13,11 +13,12 @@ isr_common_stub: mov es, ax mov fs, ax mov gs, ax - - push esp ; 2. Call C handler + push esp + call isr_handler + ; 3. Restore state pop eax pop eax @@ -41,11 +42,11 @@ irq_common_stub: mov fs, ax mov gs, ax - push esp + push esp call irq_handler ; Different than the ISR code - - pop ebx + + pop ebx pop ebx ; Different than the ISR code mov ds, bx diff --git a/kernel/cpu/i386/isr.c b/kernel/cpu/i386/isr.c index e4664f0..40c5921 100644 --- a/kernel/cpu/i386/isr.c +++ b/kernel/cpu/i386/isr.c @@ -1,21 +1,21 @@ -#include "isr.h" +#include "../isr.h" #include "idt.h" #include "gdt.h" #include -#include "paging.h" +#include "../paging.h" #include "../halt.h" #include "../../vga_err.h" #include "../../kernel.h" -#include "../tasking.h" +#include "../../tasking.h" #include "interrupt.h" -#include "address_spaces.h" +#include "../address_spaces.h" #include #include -#include "serial.h" +#include "../serial.h" #include #include void irq_handler(registers_t* r); -static isr_t interrupt_handlers[256]; +static isr_t irq_handlers[16]; /* Can't do this with a loop because we need the address * of the function names */ @@ -84,6 +84,8 @@ void isr_install() { idt_set_gate(47,(uint32_t)irq15); load_idt(); + + asm volatile("sti"); } @@ -267,7 +269,10 @@ void isr_handler(registers_t* r) { void isr_register_handler(uint8_t n,isr_t handler) { - interrupt_handlers[n] = handler; + if (n>16) { + return; + } + irq_handlers[n] = handler; } void irq_handler(registers_t* r) { @@ -276,8 +281,8 @@ void irq_handler(registers_t* r) { if (r->int_no >= 40) port_byte_out(0xA0,0x20); /* slave */ port_byte_out(0x20,0x20); /* master */ /* Handle the interrupt in a more modular way */ - if (interrupt_handlers[r->int_no] != 0) { - isr_t handler = interrupt_handlers[r->int_no]; + if (irq_handlers[r->int_no-32] != NULL) { + isr_t handler = irq_handlers[r->int_no]; handler(r); } } diff --git a/kernel/cpu/i386/isr.h b/kernel/cpu/i386/isr.h index 0973103..58e8007 100644 --- a/kernel/cpu/i386/isr.h +++ b/kernel/cpu/i386/isr.h @@ -3,58 +3,6 @@ #include -/* ISRs reserved for CPU exceptions */ -extern void isr0(); -extern void isr1(); -extern void isr2(); -extern void isr3(); -extern void isr4(); -extern void isr5(); -extern void isr6(); -extern void isr7(); -extern void isr8(); -extern void isr9(); -extern void isr10(); -extern void isr11(); -extern void isr12(); -extern void isr13(); -extern void isr14(); -extern void isr15(); -extern void isr16(); -extern void isr17(); -extern void isr18(); -extern void isr19(); -extern void isr20(); -extern void isr21(); -extern void isr22(); -extern void isr23(); -extern void isr24(); -extern void isr25(); -extern void isr26(); -extern void isr27(); -extern void isr28(); -extern void isr29(); -extern void isr30(); -extern void isr31(); -extern void isr80(); -/* IRQ definitions */ -extern void irq0(); -extern void irq1(); -extern void irq2(); -extern void irq3(); -extern void irq4(); -extern void irq5(); -extern void irq6(); -extern void irq7(); -extern void irq8(); -extern void irq9(); -extern void irq10(); -extern void irq11(); -extern void irq12(); -extern void irq13(); -extern void irq14(); -extern void irq15(); - /* Struct which aggregates many registers */ typedef struct { uint32_t ds; /* Data segment selector */ @@ -63,29 +11,9 @@ typedef struct { uint32_t eip,cs,eflags,useresp,ss; /* Pushed by the processor automatically */ } registers_t; -#define IRQ0 32 -#define IRQ1 33 -#define IRQ2 34 -#define IRQ3 35 -#define IRQ4 36 -#define IRQ5 37 -#define IRQ6 38 -#define IRQ7 39 -#define IRQ8 40 -#define IRQ9 41 -#define IRQ10 42 -#define IRQ11 43 -#define IRQ12 44 -#define IRQ13 45 -#define IRQ14 46 -#define IRQ15 47 - typedef void (*isr_t)(registers_t*); void isr_install(); -void isr_handler(registers_t* r); -void irq_handler(registers_t* r); - void isr_register_handler(uint8_t n,isr_t handler); #endif diff --git a/kernel/cpu/i386/paging.c b/kernel/cpu/i386/paging.c index 59f3d58..1d26914 100644 --- a/kernel/cpu/i386/paging.c +++ b/kernel/cpu/i386/paging.c @@ -1,14 +1,15 @@ #include #include #include "paging_helpers.h" -#include "paging.h" -#include "pmem.h" -#include "../..//vga_err.h" +#include "../paging.h" +#include "../../pmem.h" +#include "../../vga_err.h" #include #include "../halt.h" +#include "arch_consts.h" static uint32_t page_directory[1024] __attribute__((aligned(4096))); -static uint32_t kern_page_tables[NUM_KERN_DIRS*1024] __attribute__((aligned(4096))); +static uint32_t kern_page_tables[NUM_KERN_FRAMES] __attribute__((aligned(4096))); static uint32_t kstack_page_tables[218*1024] __attribute__((aligned(4096))); static uint32_t kmalloc_page_tables[4*1024] __attribute__((aligned(4096))); static uint32_t smap_page_tables[2048] __attribute__((aligned(4096))); @@ -178,13 +179,13 @@ void* paging_new_address_space() { return dir; } -void load_address_space(uint32_t cr3) { +void load_address_space(void* cr3) { load_smap(cr3); load_page_directory((uint32_t*)cr3); } -void load_smap(uint32_t cr3) { - smap_page_tables[0]=cr3|0x3; +void load_smap(void* cr3) { + smap_page_tables[0]=(uint32_t)cr3|0x3; invl_page(&smap[0]); for (uint32_t i=1;i<2048;i++) { invl_page(&smap[i*1024]); @@ -222,7 +223,7 @@ char make_protector(int page) { return 1; } -char is_in_protector(uint32_t* addr) { +char is_in_protector(void* addr) { int page=((uint32_t)addr)>>12; if (is_page_present(page)) return 0; int table=page>>10; @@ -233,7 +234,7 @@ char is_in_protector(uint32_t* addr) { } void paging_init() { - for (uint32_t i=0;i - -uint8_t port_byte_in(uint16_t port); -void port_byte_out(uint16_t port,uint8_t data); -uint16_t port_word_in(uint16_t port); -void port_word_out(uint16_t port,uint16_t data); -uint32_t port_long_in(uint16_t port); -void port_long_out(uint16_t port,uint32_t data); -#endif diff --git a/kernel/cpu/i386/serial.c b/kernel/cpu/i386/serial.c index 922946e..e66c337 100644 --- a/kernel/cpu/i386/serial.c +++ b/kernel/cpu/i386/serial.c @@ -1,9 +1,8 @@ -#include "ports.h" -#include "../../cpu/i386/isr.h" -#include "serial.h" -#include +#include +#include "../isr.h" +#include "../serial.h" +#include #include -#include #include #define SERIAL_LINE_ENABLE_DLAB 0x80 diff --git a/kernel/cpu/i386/tasking_helpers.asm b/kernel/cpu/i386/tasking_helpers.asm index 1f4a88b..cb9ad10 100644 --- a/kernel/cpu/i386/tasking_helpers.asm +++ b/kernel/cpu/i386/tasking_helpers.asm @@ -66,3 +66,10 @@ task_init: push 0x1B push ebx iret + +global wait_for_unblocked_thread_asm + +wait_for_unblocked_thread_asm: + sti ;As interrupts are stopped in tasking code, re-enable them + hlt ;Wait for an interrupt handler to run and return. + cli ;Clear interrupts, as tasking code must not be run with interrupts on. diff --git a/kernel/cpu/isr.h b/kernel/cpu/isr.h new file mode 100644 index 0000000..58e8007 --- /dev/null +++ b/kernel/cpu/isr.h @@ -0,0 +1,19 @@ +#ifndef ISR_H +#define ISR_H + +#include + +/* Struct which aggregates many registers */ +typedef struct { + uint32_t ds; /* Data segment selector */ + uint32_t edi,esi,ebp,esp,ebx,edx,ecx,eax; /* Pushed by pusha. */ + uint32_t int_no,err_code; /* Interrupt number and error code (if applicable) */ + uint32_t eip,cs,eflags,useresp,ss; /* Pushed by the processor automatically */ +} registers_t; + +typedef void (*isr_t)(registers_t*); + +void isr_install(); +void isr_register_handler(uint8_t n,isr_t handler); + +#endif diff --git a/kernel/cpu/i386/paging.h b/kernel/cpu/paging.h similarity index 76% rename from kernel/cpu/i386/paging.h rename to kernel/cpu/paging.h index 91a8743..63f72dc 100644 --- a/kernel/cpu/i386/paging.h +++ b/kernel/cpu/paging.h @@ -2,9 +2,7 @@ #define PAGING_H #include -#include "paging_helpers.h" - -#define NUM_KERN_DIRS 4 +#include "arch_consts.h" void map_pages(void* virt_addr_ptr,void* phys_addr_ptr,int num_pages,char usr,char wr); int new_kstack(); @@ -13,12 +11,13 @@ void* alloc_pages(int num_pages); void alloc_pages_virt(int num_pages,void* addr); void paging_init(); void* paging_new_address_space(); -void load_address_space(uint32_t cr3); +void load_address_space(void* cr3); void* virt_to_phys(void* virt_addr); void* find_free_pages(int num_pages); void* find_free_pages_wstart(int num_pages,int start_page); -void load_smap(uint32_t cr3); +void load_smap(void* cr3); char make_protector(int page); -char is_in_protector(uint32_t* addr); +char is_in_protector(void* addr); +void* get_cr3(); #endif diff --git a/kernel/cpu/i386/serial.h b/kernel/cpu/serial.h similarity index 100% rename from kernel/cpu/i386/serial.h rename to kernel/cpu/serial.h diff --git a/kernel/cpu/tasking.h b/kernel/cpu/tasking.h deleted file mode 100644 index 7cc68a4..0000000 --- a/kernel/cpu/tasking.h +++ /dev/null @@ -1,23 +0,0 @@ -#ifndef CPU_TASKING_H -#define CPU_TASKING_H - -#include "i386/tasking.h" -#include "i386/isr.h" -#include -#include "../rpc.h" - -extern Thread* currentThread; - -void tasking_createTask(void* eip,void* cr3,char kmode,char param1_exists,uint32_t param1_arg,char param2_exists,uint32_t param2_arg,char isThread); -void tasking_init(); -char tasking_isPrivleged(); -pid_t tasking_getPID(); -int* tasking_get_errno_address(); -uint32_t tasking_new_thread(void* start,pid_t pid,char param_exists,uint32_t param_arg); - -void tasking_exit(uint8_t code); -void tasking_block(ThreadState newstate); -void tasking_unblock(pid_t pid,uint32_t tid); -void tasking_yield(); - -#endif diff --git a/kernel/cpu/i386/tasking_helpers.h b/kernel/cpu/tasking_helpers.h similarity index 79% rename from kernel/cpu/i386/tasking_helpers.h rename to kernel/cpu/tasking_helpers.h index 70a2fc1..771e75a 100644 --- a/kernel/cpu/i386/tasking_helpers.h +++ b/kernel/cpu/tasking_helpers.h @@ -5,5 +5,6 @@ void switch_to_thread_asm(Thread* thread); void task_init(); +void wait_for_unblocked_thread_asm(); #endif diff --git a/kernel/cpu/x86_64/arch_consts.h b/kernel/cpu/x86_64/arch_consts.h new file mode 100644 index 0000000..e738238 --- /dev/null +++ b/kernel/cpu/x86_64/arch_consts.h @@ -0,0 +1,7 @@ +#ifndef ARCH_CONSTS_H +#define ARCH_CONSTS_H + +#define PAGE_SZ 496 +#define FRAME_SZ PAGE_SZ + +#endif diff --git a/kernel/cpu/x86_64/cpu_init.c b/kernel/cpu/x86_64/cpu_init.c index 7225c2b..b9f64a9 100644 --- a/kernel/cpu/x86_64/cpu_init.c +++ b/kernel/cpu/x86_64/cpu_init.c @@ -1,13 +1,2 @@ -#include "paging.h" -#include "isr.h" -#include -#include "pmem.h" -// #include "../tasking.h" -void cpu_init(struct multiboot_boot_header_tag* mbd) { - isr_install(); - asm volatile("sti"); - pmem_init(mbd); - paging_init(); - // tasking_init(); -} +void cpu_init() {} diff --git a/kernel/cpu/x86_64/interrupt.asm b/kernel/cpu/x86_64/interrupt.asm index 3849414..51ee999 100644 --- a/kernel/cpu/x86_64/interrupt.asm +++ b/kernel/cpu/x86_64/interrupt.asm @@ -21,9 +21,10 @@ isr_common_stub: push r13 push r14 push r15 - ; 2. Call C handler + ; 2. Call C handler + mov rdi,rsp call isr_handler - ; 3. Restore state + ; 3. Restore state pop r15 pop r14 pop r13 @@ -65,6 +66,7 @@ irq_common_stub: push r14 push r15 ; 2. Call C handler + mov rdi,rsp call irq_handler ; 3. Restore state pop r15 diff --git a/kernel/cpu/x86_64/isr.c b/kernel/cpu/x86_64/isr.c index ba40479..c19c88d 100644 --- a/kernel/cpu/x86_64/isr.c +++ b/kernel/cpu/x86_64/isr.c @@ -1,4 +1,4 @@ -#include "isr.h" +#include "../isr.h" #include "idt.h" #include // #include "paging.h" @@ -8,8 +8,7 @@ #include "interrupt.h" #include #include -void irq_handler(registers_t r); -static isr_t interrupt_handlers[256]; +static isr_t irq_handlers[16]; /* Can't do this with a loop because we need the address * of the function names */ @@ -78,6 +77,8 @@ void isr_install() { idt_set_gate(47,(uint64_t)irq15); load_idt(); + + asm volatile("sti"); } @@ -120,26 +121,26 @@ static char *exception_messages[] = { "Reserved" }; -void isr_handler(registers_t r) { - switch (r.int_no) { +void isr_handler(registers_t* r) { + switch (r->int_no) { case 14: { uint64_t addr; asm("movq %%cr2,%0": "=r"(addr)); - if (r.err_code==0) { + if (r->err_code==0) { vga_write_string("Kernel process tried to read a non-present page entry at address "); - } else if (r.err_code==1) { + } else if (r->err_code==1) { vga_write_string("Kernel process tried to read a page and caused a protection fault at address "); - } else if (r.err_code==2) { + } else if (r->err_code==2) { vga_write_string("Kernel process tried to write to a non-present page entry at address "); - } else if (r.err_code==3) { + } else if (r->err_code==3) { vga_write_string("Kernel process tried to write a page and caused a protection fault at address "); - } else if (r.err_code==4) { + } else if (r->err_code==4) { vga_write_string("User process tried to read a non-present page entry at address "); - } else if (r.err_code==5) { + } else if (r->err_code==5) { vga_write_string("User process tried to read a page and caused a protection fault at address "); - } else if (r.err_code==6) { + } else if (r->err_code==6) { vga_write_string("User process tried to write to a non-present page entry at address "); - } else if (r.err_code==7) { + } else if (r->err_code==7) { vga_write_string("User process tried to write a page and caused a protection fault at address "); } char str[11]; @@ -147,7 +148,7 @@ void isr_handler(registers_t r) { hex_to_ascii(addr,str); vga_write_string(str); vga_write_string("\n"); - // if ((r.err_code&1)==0) { + // if ((r->err_code&1)==0) { // // int dir_entry=(addr&0xFFC00000)>>22; // // int table_entry=(addr&0x3FF000)>12; // // if (dir_entry_present(dir_entry)) { @@ -167,36 +168,38 @@ void isr_handler(registers_t r) { halt(); break; case 80: - // if (r.eax==1) { + // if (r->eax==1) { // tss_stack_reset(); // tasking_yield(); - // } else if (r.eax==2) { - // tasking_createTask((void*)r.ebx); - // } else if (r.eax==3) { - // r.ebx=(uint64_t)alloc_pages(r.ebx); - // } else if (r.eax==4) { - // alloc_pages_virt(r.ebx,(void*)r.ecx); - // } else if (r.eax==5) { - // r.ebx=(uint64_t)tasking_get_errno_address(); + // } else if (r->eax==2) { + // tasking_createTask((void*)r->ebx); + // } else if (r->eax==3) { + // r->ebx=(uint64_t)alloc_pages(r->ebx); + // } else if (r->eax==4) { + // alloc_pages_virt(r->ebx,(void*)r->ecx); + // } else if (r->eax==5) { + // r->ebx=(uint64_t)tasking_get_errno_address(); // } break; } } } - void isr_register_handler(uint8_t n,isr_t handler) { - interrupt_handlers[n] = handler; + if (n>16) { + return; + } + irq_handlers[n] = handler; } -void irq_handler(registers_t r) { +void irq_handler(registers_t* r) { /* After every interrupt we need to send an EOI to the PICs * or they will not send another interrupt again */ - if (r.int_no >= 40) port_byte_out(0xA0,0x20); /* slave */ + if (r->int_no >= 40) port_byte_out(0xA0,0x20); /* slave */ port_byte_out(0x20,0x20); /* master */ /* Handle the interrupt in a more modular way */ - if (interrupt_handlers[r.int_no] != 0) { - isr_t handler = interrupt_handlers[r.int_no]; + if (irq_handlers[r->int_no-32] != NULL) { + isr_t handler = irq_handlers[r->int_no]; handler(r); } } diff --git a/kernel/cpu/x86_64/isr.h b/kernel/cpu/x86_64/isr.h index 3f389cb..1c00d13 100644 --- a/kernel/cpu/x86_64/isr.h +++ b/kernel/cpu/x86_64/isr.h @@ -3,58 +3,6 @@ #include -/* ISRs reserved for CPU exceptions */ -extern void isr0(); -extern void isr1(); -extern void isr2(); -extern void isr3(); -extern void isr4(); -extern void isr5(); -extern void isr6(); -extern void isr7(); -extern void isr8(); -extern void isr9(); -extern void isr10(); -extern void isr11(); -extern void isr12(); -extern void isr13(); -extern void isr14(); -extern void isr15(); -extern void isr16(); -extern void isr17(); -extern void isr18(); -extern void isr19(); -extern void isr20(); -extern void isr21(); -extern void isr22(); -extern void isr23(); -extern void isr24(); -extern void isr25(); -extern void isr26(); -extern void isr27(); -extern void isr28(); -extern void isr29(); -extern void isr30(); -extern void isr31(); -extern void isr80(); -/* IRQ definitions */ -extern void irq0(); -extern void irq1(); -extern void irq2(); -extern void irq3(); -extern void irq4(); -extern void irq5(); -extern void irq6(); -extern void irq7(); -extern void irq8(); -extern void irq9(); -extern void irq10(); -extern void irq11(); -extern void irq12(); -extern void irq13(); -extern void irq14(); -extern void irq15(); - /* Struct which aggregates many registers */ typedef struct { uint64_t r15,r14,r13,r12,r11,r10,r9,r8,rdi,rsi,rbp,rsp,rbx,rdx,rcx,rax; /* Pushed by our code. */ @@ -62,29 +10,9 @@ typedef struct { uint64_t rip,cs,rflags,userrsp,ss; /* Pushed by the processor automatically */ } registers_t; -#define IRQ0 32 -#define IRQ1 33 -#define IRQ2 34 -#define IRQ3 35 -#define IRQ4 36 -#define IRQ5 37 -#define IRQ6 38 -#define IRQ7 39 -#define IRQ8 40 -#define IRQ9 41 -#define IRQ10 42 -#define IRQ11 43 -#define IRQ12 44 -#define IRQ13 45 -#define IRQ14 46 -#define IRQ15 47 - -typedef void (*isr_t)(registers_t); +typedef void (*isr_t)(registers_t*); void isr_install(); -void isr_handler(registers_t r); -void irq_handler(registers_t r); - void isr_register_handler(uint8_t n,isr_t handler); #endif diff --git a/kernel/cpu/x86_64/paging.h b/kernel/cpu/x86_64/paging.h deleted file mode 100644 index 65115c7..0000000 --- a/kernel/cpu/x86_64/paging.h +++ /dev/null @@ -1,10 +0,0 @@ -#ifndef PAGING_H -#define PAGING_H - -#include - -#define NUM_KERN_DIRS 4 - -void paging_init(); - -#endif diff --git a/kernel/cpu/x86_64/pmem.c b/kernel/cpu/x86_64/pmem.c deleted file mode 100644 index fcaa123..0000000 --- a/kernel/cpu/x86_64/pmem.c +++ /dev/null @@ -1,123 +0,0 @@ -#include -#include "../halt.h" -#include -#include -#include - -static char bmap[131072]; - -static char get_bmap_bit(int index) { - int byte=index/8; - int bit=index%8; - char entry=bmap[byte]; - return (entry&(1<0; -} - -static void set_bmap_bit(int index) { - int byte=index/8; - int bit=index%8; - bmap[byte]=bmap[byte]|(1<type!=0) { - switch (tag->type) { - case MULTIBOOT_TAG_TYPE_MMAP: { - found_mmap=1; - struct multiboot_mmap_entry* orig_ptr=(struct multiboot_mmap_entry*)(((char*)tag)+16); - for (struct multiboot_mmap_entry* ptr=orig_ptr;(char*)ptr<((char*)orig_ptr)+tag->size;ptr++) { - if (ptr->type!=MULTIBOOT_MEMORY_AVAILABLE) continue; - uint32_t size=ptr->len; - uint32_t start=ptr->addr; - if (start<0x100000) continue; - uint32_t end=start+ptr->len-1; - if (start&0xFFF) { - start+=0x1000; - } - start=start>>12; - end=end>>12; - for (uint32_t i=start;isize+7)&0xFFFFFFF8)); - } - if (!found_mmap) { - vga_write_string("[PANIC] No memory map supplied by bootloader!"); - halt(); - } - for (uint32_t i=0;i<2048;i++) { - set_bmap_bit(i); - } -} - -void* pmem_alloc(int num_pages) { - uint32_t bmap_index; - uint32_t remaining_blks; - for(uint32_t i=0;i<131072;i++) { - if (bmap[i]!=0xFF) { - char got_0=0; - remaining_blks=num_pages; - uint32_t old_j; - for (uint32_t j=i*8;;j++) { - char bit=get_bmap_bit(j); - if (got_0) { - if (bit) { - if (remaining_blks==0) { - bmap_index=old_j; - break; - } else { - i+=j/8; - i--; - break; - } - } else { - remaining_blks--; - } - } else { - if (!bit) { - got_0=1; - old_j=j; - remaining_blks--; - } - } - if (remaining_blks==0) { - bmap_index=old_j; - break; - } - } - } - if (remaining_blks==0) { - break; - } - } - if (remaining_blks!=0) { - return NULL; - } - for (int i=0;i - -void pmem_init(struct multiboot_boot_header_tag* tags); -void* pmem_alloc(int num_pages); -void pmem_free(int start_page,int num_pages); - -#endif diff --git a/kernel/cpu/x86_64/ports.c b/kernel/cpu/x86_64/ports.c deleted file mode 100644 index 5991314..0000000 --- a/kernel/cpu/x86_64/ports.c +++ /dev/null @@ -1,31 +0,0 @@ -#include - -uint8_t port_byte_in(uint16_t port) { - uint8_t result; - asm("in %%dx, %%al":"=a"(result):"d"(port)); - return result; -} - -void port_byte_out(uint16_t port,uint8_t data) { - asm("out %%al, %%dx":: "a"(data),"d"(port)); -} - -uint16_t port_word_in(uint16_t port) { - uint16_t result; - asm("in %%dx, %%ax":"=a"(result):"d"(port)); - return result; -} - -void port_word_out(uint16_t port,uint16_t data) { - asm("out %%ax, %%dx":: "a" (data), "d" (port)); -} - -uint32_t port_long_in(uint16_t port) { - uint32_t result; - asm("inl %%dx, %%eax":"=a"(result):"d"(port)); - return result; -} - -void port_long_out(uint16_t port,uint32_t data) { - asm("outl %%eax, %%dx":: "a" (data), "d" (port)); -} diff --git a/kernel/kernel.c b/kernel/kernel.c index f9abfef..c25ceaa 100644 --- a/kernel/kernel.c +++ b/kernel/kernel.c @@ -1,6 +1,7 @@ #include #include #include +#include "tasking.h" #include #include #include @@ -8,6 +9,10 @@ #include "cpu/cpu_init.h" #include "vga_err.h" #include +#include "cpu/serial.h" +#include "pmem.h" +#include "cpu/paging.h" +#include "cpu/isr.h" typedef struct { char filename[100]; @@ -52,7 +57,12 @@ uint32_t getsize(const char *in) { void kmain(struct multiboot_boot_header_tag* hdr) { tags=hdr; - cpu_init(tags); + cpu_init(); + isr_install(); + serial_init(); + pmem_init(tags); + paging_init(); + tasking_init(); vga_init((char*)0xC00B8000); read_initrd(tags); int pos=0; diff --git a/kernel/cpu/i386/kmalloc.c b/kernel/kmalloc.c similarity index 90% rename from kernel/cpu/i386/kmalloc.c rename to kernel/kmalloc.c index a19a1dd..4ce3f0a 100644 --- a/kernel/cpu/i386/kmalloc.c +++ b/kernel/kmalloc.c @@ -2,9 +2,12 @@ #include #include #include +#include "cpu/arch_consts.h" -static char bitmap[2097152]; -static void* data=(void*)0xFE800000; +#define KMALLOC_BMAP_SZ (((KMALLOC_SZ*1024)/4)/8) + +static char bitmap[KMALLOC_BMAP_SZ]; +static void* data=(void*)KMALLOC_START; static char get_bmap_bit(uint32_t index) { @@ -31,7 +34,7 @@ void* kmalloc(uint32_t size) { num_4b_grps+=2; uint32_t bmap_index; uint32_t remaining_blks; - for(uint32_t i=0;i<2097152;i++) { + for(uint32_t i=0;i -#include "../halt.h" -#include "../..//vga_err.h" +#include "cpu/halt.h" +#include "vga_err.h" #include #include #include +#include "cpu/arch_consts.h" -static char bmap[131072]; +#define BMAP_LEN (NUM_FRAMES/8) + +static char bmap[BMAP_LEN]; static char get_bmap_bit(int index) { int byte=index/8; @@ -27,7 +30,7 @@ static void clear_bmap_bit(int index) { } void pmem_init(struct multiboot_boot_header_tag* tags) { - for (int i=0;i<131072;i++) { + for (int i=0;iaddr; if (start<0x100000) continue; uint32_t end=start+ptr->len-1; - if (start&0xFFF) { - start+=0x1000; + if (start&(FRAME_SZ-1)) { + start+=FRAME_SZ; } - start=start>>12; - end=end>>12; + start=start>>FRAME_NO_OFFSET; + end=end>>FRAME_NO_OFFSET; for (uint32_t i=start;i #include "kmalloc.h" -#include "serial.h" -#include "../halt.h" -#include "paging.h" -#include "tasking_helpers.h" +#include "cpu/serial.h" +#include "cpu/halt.h" +#include "cpu/paging.h" +#include "cpu/tasking_helpers.h" #define MAX_PROCS 32768 #define HAS_UNBLOCKED_THREADS(proc) (proc->numThreads!=proc->numThreadsBlocked) #define NUM_UNBLOCKED_THREADS(proc) (proc->numThreads-proc->numThreadsBlocked) @@ -18,7 +17,7 @@ char proc_schedule_bmap[MAX_PROCS/8]; Thread* currentThread; static Thread* readyToRunHead=NULL; static Thread* readyToRunTail=NULL; -static uint32_t* kstacks=(uint32_t*)0xC8000000; +static uint32_t* kstacks=(uint32_t*)KSTACKS_START; static char is_proc_scheduled(uint32_t index) { uint32_t byte=index/8; @@ -90,10 +89,9 @@ void tasking_createTask(void* eip,void* cr3,char kmode,char param1_exists,uint32 thread->errno=0; thread->tid=proc->next_tid; proc->next_tid++; - void* old_cr3; - asm volatile("movl %%cr3, %%eax; movl %%eax, %0;":"=m"(old_cr3)::"%eax"); + void* old_cr3=get_cr3(); uint32_t kstack_num=new_kstack(); - load_address_space((uint32_t)thread->cr3); + load_address_space(thread->cr3); if (kmode) { uint32_t top_idx=(1024*(kstack_num+1)); thread->kernel_esp=((uint32_t)(&kstacks[top_idx-5])); @@ -113,7 +111,7 @@ void tasking_createTask(void* eip,void* cr3,char kmode,char param1_exists,uint32 kstacks[top_idx-2]=(uint32_t)user_stack; kstacks[top_idx-1]=(uint32_t)eip; } - load_address_space((uint32_t)old_cr3); + load_address_space(old_cr3); thread->prevReadyToRun=NULL; thread->nextReadyToRun=NULL; if (isThread) { @@ -150,9 +148,7 @@ void tasking_createTask(void* eip,void* cr3,char kmode,char param1_exists,uint32 } void tasking_init() { - void* cr3; - asm volatile("movl %%cr3, %%eax; movl %%eax, %0;":"=m"(cr3)::"%eax"); - tasking_createTask(NULL,cr3,1,0,0,0,0,0); + tasking_createTask(NULL,get_cr3(),1,0,0,0,0,0); } char tasking_isPrivleged() { @@ -227,7 +223,7 @@ void switch_to_thread(Thread* thread) { mark_proc_scheduled(currentThread->process->pid); } serial_printf("Switching to PID %d TID %d.\n",thread->process->pid,thread->tid); - load_smap((uint32_t)thread->cr3); + load_smap(thread->cr3); switch_to_thread_asm(thread); } @@ -250,11 +246,7 @@ void tasking_yield() { } else { serial_printf("All threads in all processes blocked, waiting for an IRQ which unblocks a thread\n"); // All threads in all processes blocked, so wait for an IRQ whose handler unblocks a thread. - do { - asm volatile("sti"); //As interrupts are stopped, re-enable them. - asm volatile("hlt"); //Wait for an interrupt handler to run and return. - asm volatile("cli"); //Clear interrupts, as tasking code must not be interrupted. - } while (readyToRunHead==NULL); + do { wait_for_unblocked_thread_asm(); } while (readyToRunHead==NULL); } serial_printf("Attempting to switch to PID %d TID %d\n",readyToRunHead->process->pid,readyToRunHead->tid); switch_to_thread(readyToRunHead); diff --git a/kernel/cpu/i386/tasking.h b/kernel/tasking.h similarity index 54% rename from kernel/cpu/i386/tasking.h rename to kernel/tasking.h index 8fe7f7c..9dbf67b 100644 --- a/kernel/cpu/i386/tasking.h +++ b/kernel/tasking.h @@ -1,15 +1,20 @@ -#ifndef INT_TASKING_H -#define INT_TASKING_H +#ifndef KERN_TASKING_H +#define KERN_TASKING_H + +#include + #include #ifndef TASKING_H + typedef enum ThreadState { THREAD_RUNNING, THREAD_READY, THREAD_EXITED, THREAD_BLOCKED } ThreadState; + #endif struct Thread; @@ -37,4 +42,18 @@ typedef struct Thread { Process* process; } Thread; +extern Thread* currentThread; + +void tasking_createTask(void* eip,void* cr3,char kmode,char param1_exists,uint32_t param1_arg,char param2_exists,uint32_t param2_arg,char isThread); +void tasking_init(); +char tasking_isPrivleged(); +pid_t tasking_getPID(); +int* tasking_get_errno_address(); +uint32_t tasking_new_thread(void* start,pid_t pid,char param_exists,uint32_t param_arg); + +void tasking_exit(uint8_t code); +void tasking_block(ThreadState newstate); +void tasking_unblock(pid_t pid,uint32_t tid); +void tasking_yield(); + #endif diff --git a/kernel/cpu/i386/ports.c b/libc/ports.c similarity index 100% rename from kernel/cpu/i386/ports.c rename to libc/ports.c diff --git a/sysroot/usr/include/tasking.h b/sysroot/usr/include/tasking.h index 4ffc79a..4b31581 100644 --- a/sysroot/usr/include/tasking.h +++ b/sysroot/usr/include/tasking.h @@ -4,7 +4,7 @@ #include #include -#ifndef INT_TASKING_H +#ifndef KERN_TASKING_H typedef enum ThreadState { THREAD_RUNNING, THREAD_READY,