feat(cpu): install IDT with exception and syscall gate handling

This commit is contained in:
dualfroz committed 2026-08-24 19:45:21 +02:00
1 parent 4843406bf3
commit e5c4139e49
4 files changed
+145

No files matched your search

+48
View File
@@ -0,0 +1,48 @@
#include "idt.h"
#include "types.h"
typedef struct IdtEntry {
uint16 offsetLow;
uint16 selector;
uint8 ist;
uint8 typeAttr;
uint16 offsetMid;
uint32 offsetHigh;
uint32 reserved;
} __attribute__((packed)) IdtEntry;
typedef struct IdtPointer {
uint16 limit;
uint64 base;
} __attribute__((packed)) IdtPointer;
static IdtEntry idtEntries[256];
static IdtPointer idtPointer;
extern void* isrStubTable[];
extern void isrStub128(void);
static void setGate(int vector, void* handler, uint8 typeAttr)
{
uint64 address = (uint64)handler;
idtEntries[vector].offsetLow = (uint16)(address & 0xFFFF);
idtEntries[vector].selector = 0x08;
idtEntries[vector].ist = 0;
idtEntries[vector].typeAttr = typeAttr;
idtEntries[vector].offsetMid = (uint16)((address >> 16) & 0xFFFF);
idtEntries[vector].offsetHigh = (uint32)((address >> 32) & 0xFFFFFFFF);
idtEntries[vector].reserved = 0;
}
void idtInit(void)
{
for (int vector = 0; vector < 48; vector++)
setGate(vector, isrStubTable[vector], 0x8E);
setGate(0x80, (void*)isrStub128, 0xEE);
idtPointer.limit = (uint16)(sizeof(idtEntries) - 1);
idtPointer.base = (uint64)&idtEntries;
__asm__ volatile("lidt %0" : : "m"(idtPointer));
}
+75
View File
@@ -0,0 +1,75 @@
#include "isr.h"
#include "console.h"
#include "pic.h"
#include "pit.h"
#include "keyboard.h"
#include "sched.h"
#include "ports.h"
static const char* exceptionNames[32] = {
"divide by zero",
"debug",
"non maskable interrupt",
"breakpoint",
"overflow",
"bound range exceeded",
"invalid opcode",
"device not available",
"double fault",
"coprocessor segment overrun",
"invalid tss",
"segment not present",
"stack segment fault",
"general protection fault",
"page fault",
"reserved",
"x87 floating point",
"alignment check",
"machine check",
"simd floating point",
"virtualization",
"control protection",
"reserved", "reserved", "reserved", "reserved",
"reserved", "reserved", "reserved", "reserved",
"hypervisor injection", "vmm communication"
};
static void panicOnException(Registers* regs)
{
uint64 faultAddress = 0;
if (regs->intNo == 14)
__asm__ volatile("mov %%cr2, %0" : "=r"(faultAddress));
kprintf("\n[PANIC] exception %lu (%s)\n", regs->intNo, exceptionNames[regs->intNo]);
kprintf(" errCode=%lx rip=%lx cs=%lx rflags=%lx\n",
regs->errCode, regs->rip, regs->cs, regs->rflags);
if (regs->intNo == 14)
kprintf(" cr2=%lx (faulting address)\n", faultAddress);
kprintf(" rax=%lx rbx=%lx rcx=%lx rdx=%lx\n", regs->rax, regs->rbx, regs->rcx, regs->rdx);
kprintf(" system halted\n");
for (;;)
__asm__ volatile("cli; hlt");
}
uint64 isrDispatch(Registers* regs)
{
if (regs->intNo < 32)
panicOnException(regs);
if (regs->intNo == 128)
return syscallDispatch(regs);
uint8 irq = (uint8)(regs->intNo - 32);
uint64 nextRsp = (uint64)regs;
if (irq == 0) {
pitTick();
nextRsp = schedule((uint64)regs);
} else if (irq == 1) {
keyboardHandler();
}
picSendEoi(irq);
return nextRsp;
}