diff options
| -rw-r--r-- | kernel/gdt.c | 71 | ||||
| -rw-r--r-- | kernel/gdt.h | 54 | ||||
| -rw-r--r-- | kernel/interrupts.c | 19 | ||||
| -rw-r--r-- | kernel/interrupts.h | 29 | ||||
| -rw-r--r-- | kernel/kernel.c | 32 |
5 files changed, 116 insertions, 89 deletions
diff --git a/kernel/gdt.c b/kernel/gdt.c index f72f1ab..24b52f7 100644 --- a/kernel/gdt.c +++ b/kernel/gdt.c @@ -1,4 +1,3 @@ -// http://wiki.osdev.org/GDT_Tutorial #include "kernel.h" #include "gdt.h" #include "asm_gdt.h" @@ -8,28 +7,69 @@ #define GDT_SIZE 6 -//https://wiki.osdev.org/Task_State_Segment -//Define the TSS as a global structure, boah TODO: move to own page? +static uint8_t gdt_structs[GDT_SIZE*8*SMP_MAX_PROC]; // GLOBAL DESCRIPTOR TABLES + +typedef volatile struct strtss{ + unsigned short link; + unsigned short link_h; + unsigned long esp0; + unsigned short ss0; + unsigned short ss0_h; + unsigned long esp1; + unsigned short ss1; + unsigned short ss1_h; + unsigned long esp2; + unsigned short ss2; + unsigned short ss2_h; + unsigned long cr3; + unsigned long eip; + unsigned long eflags; + unsigned long eax; + unsigned long ecx; + unsigned long edx; + unsigned long ebx; + unsigned long esp; + unsigned long ebp; + unsigned long esi; + unsigned long edi; + unsigned short es; + unsigned short es_h; + unsigned short cs; + unsigned short cs_h; + unsigned short ss; + unsigned short ss_h; + unsigned short ds; + unsigned short ds_h; + unsigned short fs; + unsigned short fs_h; + unsigned short gs; + unsigned short gs_h; + unsigned short ldt; + unsigned short ldt_h; + unsigned short trap; + unsigned short iomap; +}__attribute__((packed)) tss_struct; + tss_struct sys_tss[SMP_MAX_PROC]; +typedef struct GDT_struct +{ + uint32_t base; + uint32_t limit; + uint32_t type; +}GDT; + void install_tss(uint32_t cpu,uint32_t esp0){ // now fill each value // set values necessary sys_tss[cpu].ss0 = 0x10; //kernel data sys_tss[cpu].esp0 = esp0; - // now set the IO bitmap (not necessary, so set above limit) // sys_tss.iomap = ( unsigned short ) sizeof( tss_struct ); } -typedef struct GDT_struct -{ - uint32_t base; - uint32_t limit; - uint32_t type; -}GDT; - +/* //alternative struct gdt_entry_bits { @@ -51,6 +91,7 @@ struct gdt_entry_bits unsigned int gran :1; //1 to use 4k page addressing, 0 for byte addressing unsigned int base_high :8; } __packed; //or __attribute__((packed)) +*/ void setup_gdt(uint8_t *gdt_struct) { @@ -105,6 +146,8 @@ void gdt_init() { static int last_cpu=0; + if(last_cpu>=SMP_MAX_PROC)kpanic("not enough SMP_MAX_PROC"); + /* Pr=1 Privl 1 Exec DC RW Ac 0x9A == 1001 1010 == 1 00 1 1 0 1 0 @@ -113,8 +156,9 @@ void gdt_init() 0xF2 == 1111 0010 == 1 11 1 0 0 1 0 */ -//static uint8_t gdt_struct[GDT_SIZE*8]; // GLOBAL DESCRIPTOR TABLE - uint8_t *gdt_struct=kballoc(1); //[GDT_SIZE*8]; // GLOBAL DESCRIPTOR TABLE + //static uint8_t gdt_struct[GDT_SIZE*8]; // GLOBAL DESCRIPTOR TABLE + //uint8_t *gdt_struct=kballoc(1); //[GDT_SIZE*8]; // GLOBAL DESCRIPTOR TABLE + uint8_t *gdt_struct=&gdt_structs[GDT_SIZE*8*last_cpu]; GDT myGDT[GDT_SIZE]; //selector 0x0 @@ -156,6 +200,5 @@ void gdt_init() last_cpu++; setup_gdt(gdt_struct); - } diff --git a/kernel/gdt.h b/kernel/gdt.h index 314cc99..9b7eece 100644 --- a/kernel/gdt.h +++ b/kernel/gdt.h @@ -1,49 +1,21 @@ // https://xarnze.com/posts/post/Tutorial:%20Entering%20User%20mode // http://wiki.osdev.org/TSS // http://wiki.osdev.org/Global_Descriptor_Table +// http://wiki.osdev.org/GDT_Tutorial +//https://wiki.osdev.org/Task_State_Segment #include <stdint.h> -typedef volatile struct strtss{ - unsigned short link; - unsigned short link_h; - unsigned long esp0; - unsigned short ss0; - unsigned short ss0_h; - unsigned long esp1; - unsigned short ss1; - unsigned short ss1_h; - unsigned long esp2; - unsigned short ss2; - unsigned short ss2_h; - unsigned long cr3; - unsigned long eip; - unsigned long eflags; - unsigned long eax; - unsigned long ecx; - unsigned long edx; - unsigned long ebx; - unsigned long esp; - unsigned long ebp; - unsigned long esi; - unsigned long edi; - unsigned short es; - unsigned short es_h; - unsigned short cs; - unsigned short cs_h; - unsigned short ss; - unsigned short ss_h; - unsigned short ds; - unsigned short ds_h; - unsigned short fs; - unsigned short fs_h; - unsigned short gs; - unsigned short gs_h; - unsigned short ldt; - unsigned short ldt_h; - unsigned short trap; - unsigned short iomap; -}__attribute__((packed)) tss_struct; - +/** Call this one on each CPU to get a fresh 6-entries GDT + * * 0 + * * ring0 code + * * ring0 data + * * ring3 code + * * ring3 data + * * tss + */ void gdt_init(); + +/** update tss.esp0 for a given cpu + */ void install_tss(uint32_t cpu,uint32_t esp0); diff --git a/kernel/interrupts.c b/kernel/interrupts.c index d0de5ed..44ab9b5 100644 --- a/kernel/interrupts.c +++ b/kernel/interrupts.c @@ -242,23 +242,22 @@ void interrupts_init(uint16_t sel) int_install_ir(17, 0b10001110, 0x08,&exc17); int_install_ir(18, 0b10001110, 0x08,&exc18); - // PIT + // PIT (IOAPIC) int_install_ir(0x90, 0b10001110, 0x08,&int0); - // Keyboard + // Keyboard (IOAPIC) int_install_ir(0x91, 0b10001110, 0x08,&int1); - // Mouse + // Mouse (IOAPIC) int_install_ir(0x92, 0b10001110, 0x08,&int12); - // System Calls / they can be called from ring3 (0b11) - int_install_ir(0x80, 0b11101110, 0x08,&int128); + // APIC Timer (LAPIC) + int_install_ir(0x8C, 0b10001110, 0x08,&int200); - // IPI - int_install_ir(0x81, 0b11101110, 0x08,&int129); + // System Calls (User Software / Ring 3) + int_install_ir(0x80, 0b11101110, 0x08,&int128); - int_install_ir(170, 0b11101110, 0x08,&int170); + // Inter Processesor Interrupts (Kernel Software) + int_install_ir(0x81, 0b10001110, 0x08,&int129); - // APIC Timer - int_install_ir(0x8C, 0b11101110, 0x08,&int200); } diff --git a/kernel/interrupts.h b/kernel/interrupts.h index 48e8c20..80fa95e 100644 --- a/kernel/interrupts.h +++ b/kernel/interrupts.h @@ -11,29 +11,38 @@ * * Exceptions * ---------- - * 0x00-0x12 Exceptions + * * 0x00-0x12 Exceptions * * Legacy PIC * ---------- - * 0x20-0x27 disabled pic - * 0x28-0x36 disabled pic + * * 0x20-0x27 disabled pic + * * 0x28-0x36 disabled pic * * Hardware Interrupts * ------------------- * This interrupts are remapped by the IOAPIC * - * 0x0 PIT Timer -> 0x90 - * 0x1 Keyboard -> 0x91 - * 0xC Mouse -> 0x92 + * * 0x0 PIT Timer -> 0x90 + * * 0x1 Keyboard -> 0x91 + * * 0xC Mouse -> 0x92 * * Local Interrupts from LAPICs * ---------------------- - * 0x8C APIC Timer + * * 0x8C APIC Timer * * Software Interrupts * ------------------- - * 0x80 System Call - * 0x81 IPI + * * 0x80 System Call + * * 0x81 IPI + * + * Usage + * ----- + * + * Run interrupts_init() once first with the desired selector, usually 0x08. + * After that you can install the interrupts on each cpu via interrupts_install. + * interrupt_handler() and exception_handler() will be called accordingly from + * the interrupt handlers this functionality is backed by. You can find them + * in asm_int.h */ #define INTERRUPT_PIT_TIMER 0x90 @@ -46,5 +55,7 @@ void interrupts_init(uint16_t sel); void interrupts_install(); +uint32_t interrupt_handler(uint32_t esp, uint32_t irq); +void exception_handler(uint32_t esp, uint32_t irq); #endif diff --git a/kernel/kernel.c b/kernel/kernel.c index 724b1a0..12b2063 100644 --- a/kernel/kernel.c +++ b/kernel/kernel.c @@ -37,9 +37,25 @@ void kernel_main(uint32_t eax,uint32_t ebx) klog("Compiled on: %s at %s",__DATE__,__TIME__); klog("Version: git-commit: %s",GIT_REVISION); klog("======================================"); - + klog("Communication Port (COM1) init ..."); //delayed info + fixme("Check if kernel size does not exceed memory limits!"); + + // collect some info (before we start paging) + klog("Search / Read Multiboot Structures ... "); + multiboot_information *info; + info=get_multiboot(eax, ebx); + + klog("Search / Read ACPI Structures... "); + smp_processors procdata; + bool acpi_found=acpi_find(&procdata); + + klog("Search / Read MP Structures... "); + smp_processors procdata2; + bool mp_found=mp_find(&procdata2); + // + klog("Global Descriptor Table (GDT) init ..."); gdt_init(); @@ -56,20 +72,6 @@ void kernel_main(uint32_t eax,uint32_t ebx) klog("Mouse init ..."); mouse_init(); - // gather some info (before we start paging) - klog("Search / Read Multiboot Structures ... "); - multiboot_information *info; - info=get_multiboot(eax, ebx); - - klog("Search / Read ACPI Structures... "); - smp_processors procdata; - bool acpi_found=acpi_find(&procdata); - - klog("Search / Read MP Structures... "); - smp_processors procdata2; - bool mp_found=mp_find(&procdata2); - // - // memory management klog("Memory init ... "); uint32_t kernel_blocks=mem_init(info); |
