diff --git a/src/arch/i386/idt.S b/src/arch/i386/idt.S index ed00656..a18c141 100644 --- a/src/arch/i386/idt.S +++ b/src/arch/i386/idt.S @@ -13,22 +13,26 @@ .type __arch_setidt, @function #endif __arch_setidt: - lea idt, %ecx + lea idt_descriptor, %ecx + /* set the offset of the IDT */ mov 0x4(%esp), %eax mov %eax, 0x2(%ecx) + /* set the size of the IDT */ mov 0x8(%esp), %eax dec %eax mov %ax, (%ecx) + /* load the IDT */ - lidt (%ecx) + lidt (idt_descriptor) + ret /* bss */ .section .bss .align 16 -idt: +idt_descriptor: .skip 2 /* size */ .skip 4 /* offset */ diff --git a/src/arch/i386/idt.h b/src/arch/i386/idt.h index 56a2ba5..635cfa6 100644 --- a/src/arch/i386/idt.h +++ b/src/arch/i386/idt.h @@ -12,15 +12,28 @@ /* public */ /* types */ -typedef struct _IDT +typedef struct _IDT IDT; + +typedef struct _IDTEntry { - uint32_t base; + uint16_t offsetl; uint16_t selector; - uint8_t flags; -} IDT; + uint8_t __padding; + uint8_t type:4; + uint8_t flags:4; + uint16_t offseth; +} IDTEntry; + + +/* constants */ +# define IDT_FLAG_PRESENT 0x8 +# define IDT_FLAG_RING(level) ((level) << 1) + +# define IDT_TYPE_INT_GATE 0xe +# define IDT_TYPE_TRAP_GATE 0xf /* prototypes */ -int _arch_setidt(IDT const * idt, size_t count); +IDT * idt_init(void); #endif /* !UKERNEL_ARCH_I386_IDT_H */ diff --git a/src/kernel/idt.c b/src/kernel/idt.c index 6e697ae..cca38f3 100644 --- a/src/kernel/idt.c +++ b/src/kernel/idt.c @@ -1,58 +1,7 @@ /* $Id$ */ -/* Copyright (c) 2018 Pierre Pronchery */ +/* Copyright (c) 2018-2025 Pierre Pronchery */ /* This file is part of DeforaOS uKernel */ -#if defined(__amd64__) || defined(__i386__) -# include -# include -# include -# include "arch/i386/idt.h" - - -/* prototypes */ -extern void __arch_setidt(uint8_t * buf, size_t count); - - -/* variables */ -/* FIXME correct the size */ -static uint8_t _buf[65536]; - - -/* functions */ -/* arch_setidt */ -int _arch_setidt(IDT const * idt, size_t count) -{ - uint8_t * buf = _buf; - size_t i; - IDT const * t; - - memset(&_buf, 0, sizeof(_buf)); - /* check for errors */ - if(/* count == 0 ||*/ count > sizeof(_buf) / sizeof(*idt)) - { - errno = ERANGE; - return -1; - } - for(i = 0; i < count; i++) - { - t = &idt[i]; - buf = &_buf[sizeof(t) * i]; - /* encode the address */ - buf[0] = (t->base >> 8) & 0xff; - buf[1] = t->base & 0xff; - buf[6] = (t->base >> 24) & 0xff; - buf[7] = (t->base >> 16) & 0xff; - /* selector */ - buf[2] = (t->selector >> 8) & 0xff; - buf[3] = t->selector & 0xff; - /* padding */ - buf[4] = 0x0; - /* flags */ - buf[5] = t->flags; - } - __arch_setidt(_buf, count); - return 0; -} -#endif +#include "../loader/idt.c" diff --git a/src/kernel/multiboot.c b/src/kernel/multiboot.c index 5bcb92c..ce1debe 100644 --- a/src/kernel/multiboot.c +++ b/src/kernel/multiboot.c @@ -33,10 +33,6 @@ static const GDTTable _gdt_4gb[2] = { 0x00000000, 0xffffffff, GDT_PROT_READ | GDT_PROT_WRITE } }; -static const IDT _idt[] = -{ -}; - /* public */ /* functions */ @@ -113,7 +109,7 @@ int multiboot(const ukMultibootInfo * mi) } /* setup the IDT */ - if(_arch_setidt(_idt, sizeof(_idt) / sizeof(*_idt)) != 0) + if(idt_init() == NULL) { puts("Could not setup the IDT"); return 5; diff --git a/src/kernel/project.conf b/src/kernel/project.conf index b96ddc6..f9e8f00 100644 --- a/src/kernel/project.conf +++ b/src/kernel/project.conf @@ -42,6 +42,12 @@ depends=../common/crti.S,../arch/amd64/crti.S,../arch/i386/crti.S [crtn.S] depends=../common/crtn.S,../arch/amd64/crtn.S,../arch/i386/crtn.S +[gdt.c] +depends=../loader/gdt.c + +[idt.c] +depends=../loader/idt.c + [multiboot.c] depends=../loader/multiboot.c,../drivers/boot/multiboot.h diff --git a/src/loader/multiboot.c b/src/loader/multiboot.c index fa1b10f..7f01af6 100644 --- a/src/loader/multiboot.c +++ b/src/loader/multiboot.c @@ -13,6 +13,7 @@ # include # include "arch/amd64/gdt.h" # include "arch/i386/gdt.h" +# include "arch/i386/idt.h" # include "drivers/boot/multiboot.h" # ifndef LOADER_CLOCK @@ -93,6 +94,13 @@ int multiboot(const ukMultibootInfo * mi) return 4; } + /* setup the IDT */ + if(idt_init() == NULL) + { + puts("Could not setup the IDT"); + return 5; + } + /* load the kernel */ if(!(mi->flags & BOOT_MULTIBOOT_INFO_HAS_MODS)) { diff --git a/src/loader/project.conf b/src/loader/project.conf index b242d23..6ca0ca5 100644 --- a/src/loader/project.conf +++ b/src/loader/project.conf @@ -36,7 +36,7 @@ ldflags=`../../tools/platform.sh -V LIBULOADER_LDFLAGS -C "$$ARCH"` [uLoader.bin] type=binary depends=$(OBJDIR)crtbegin.o,$(OBJDIR)crtend.o,$(OBJDIR)crti.o,$(OBJDIR)crtn.o,$(OBJDIR)libuLoader.a,../arch/amd64/uKernel.ld,../arch/i386/uKernel.ld -sources=arch.S,gdt.c,main.c,multiboot.c,start.S +sources=arch.S,gdt.c,idt.c,main.c,multiboot.c,start.S asflags=`../../tools/platform.sh -V ULOADER_CFLAGS -C "$$ARCH"` cflags=`../../tools/platform.sh -V ULOADER_CFLAGS -C "$$ARCH"` ldflags=$(OBJDIR)crti.o $(OBJDIR)crtbegin.o $(OBJDIR)crtend.o $(OBJDIR)crtn.o $(OBJDIR)libuLoader.a `../../tools/platform.sh -V ULOADER_LDFLAGS -C "$$ARCH"` @@ -85,7 +85,7 @@ depends=$(OBJDIR)../lib/libk.a depends=../drivers/boot/multiboot.h,../../include/kernel/drivers/bus.h,../../include/kernel/drivers/console.h [start.S] -depends=../arch/i386/gdt.S,../arch/i386/intr.S,../arch/i386/loader.S,../arch/i386/multiboot.S +depends=../arch/i386/gdt.S,../arch/i386/idt.S,../arch/i386/intr.S,../arch/i386/loader.S,../arch/i386/multiboot.S [syscalls.S] depends=$(OBJDIR)../lib/libc/src/syscalls.o diff --git a/src/loader/start.S b/src/loader/start.S index 1d0ca4e..5125389 100644 --- a/src/loader/start.S +++ b/src/loader/start.S @@ -7,6 +7,7 @@ /* check for supported architectures */ #if defined(__i386__) # include "../arch/i386/gdt.S" +# include "../arch/i386/idt.S" # include "../arch/i386/intr.S" # include "../arch/i386/loader.S" #else