Skip to content

Commit a9c82d1

Browse files
committed
And finally add IDT files (I suck at git)
1 parent 402ea85 commit a9c82d1

File tree

2 files changed

+112
-0
lines changed

2 files changed

+112
-0
lines changed

arch/idt.c

Lines changed: 86 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,86 @@
1+
/** @author Levente Kurusa <[email protected]> **/
2+
#include <stdint.h>
3+
#include "../include/x86/idt.h"
4+
#include "../include/display.h"
5+
6+
MODULE("IDT");
7+
8+
static uint32_t idt_location = 0;
9+
static uint32_t idtr_location = 0;
10+
static uint16_t idt_size = 0x800;
11+
12+
static uint8_t test_success = 0;
13+
static uint32_t test_timeout = 0x1000;
14+
15+
void __idt_default_handler();
16+
void __idt_test_handler();
17+
18+
void idt_init()
19+
{
20+
idt_location = 0x402000;
21+
mprint("Location: 0x%x\n", idt_location);
22+
idtr_location = 0x401F00;
23+
mprint("IDTR location: 0x%x\n", idtr_location);
24+
for(uint8_t i = 0; i < 255; i++)
25+
{
26+
idt_register_interrupt(i, __idt_default_handler);
27+
}
28+
idt_register_interrupt(0x2f, __idt_test_handler);
29+
mprint("Registered all interrupts to default handler.\n");
30+
/* create IDTR now */
31+
*(uint16_t*)idtr_location = idt_size - 1;
32+
*(uint32_t*)(idtr_location + 2) = idt_location;
33+
mprint("IDTR.size = 0x%x IDTR.offset = 0x%x\n", *(uint16_t*)idtr_location, *(uint32_t*)(idtr_location + 2));
34+
_set_idtr();
35+
mprint("IDTR set, testing link.\n");
36+
asm volatile("int $0x2f");
37+
while(test_timeout != 0)
38+
{
39+
if(test_success != 0)
40+
{
41+
mprint("Test succeeded, disabling INT#0x2F\n");
42+
idt_register_interrupt(0x2F, __idt_default_handler);
43+
break;
44+
}
45+
}
46+
if(!test_success)
47+
panic("Link test failed.");
48+
return;
49+
}
50+
51+
void __idt_test_handler()
52+
{
53+
INT_START;
54+
test_success = 1;
55+
INT_END;
56+
}
57+
58+
void __idt_default_handler()
59+
{
60+
panic("Unhandled interrupt!\n");
61+
}
62+
63+
void idt_register_interrupt(uint8_t i, void(*callback)())
64+
{
65+
idt_descriptor desc = {0};
66+
desc.offset_0_15 = (uint16_t)callback;
67+
desc.selector = 0x8;
68+
desc.zero = 0;
69+
desc.type_attr = 0 | IDT_32BIT_INTERRUPT_GATE | IDT_DPL_3 | IDT_PRESENT;
70+
desc.offset_16_31 = (uint16_t)((uint32_t)callback >> 16);
71+
/*mprint("Descriptor: id%d offset 0x%x, orig 0x%x\n",
72+
i,
73+
desc.offset_16_31 << 16 | desc.offset_0_15,
74+
(uint32_t)callback);*/
75+
add_idt_descriptor(i, desc);
76+
}
77+
78+
void add_idt_descriptor(uint8_t id, idt_descriptor desc)
79+
{
80+
*(uint16_t*)(idt_location + sizeof(idt_descriptor)*id + 0) = desc.offset_0_15;
81+
*(uint16_t*)(idt_location + sizeof(idt_descriptor)*id + 2) = desc.selector;
82+
*(uint8_t*) (idt_location + sizeof(idt_descriptor)*id + 4) = desc.zero;
83+
*(uint8_t*) (idt_location + sizeof(idt_descriptor)*id + 5) = desc.type_attr;
84+
*(uint16_t*)(idt_location + sizeof(idt_descriptor)*id + 6) = desc.offset_16_31;
85+
return;
86+
}

include/x86/idt.h

Lines changed: 26 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,26 @@
1+
/** @author Levente Kurusa <[email protected]> **/
2+
#ifndef __IDT_H_
3+
#define __IDT_H_
4+
5+
typedef struct {
6+
uint16_t offset_0_15;
7+
uint16_t selector;
8+
uint8_t zero;
9+
uint8_t type_attr;
10+
uint16_t offset_16_31;
11+
} __attribute__((packed)) idt_descriptor;
12+
13+
#define IDT_32BIT_INTERRUPT_GATE 0xE
14+
#define IDT_STORAGE_SEGMENT 0x20
15+
#define IDT_DPL_3 0x60
16+
#define IDT_PRESENT 0x80
17+
18+
#define INT_START asm volatile("pusha");
19+
#define INT_END asm volatile("popa"); \
20+
asm volatile("iret");
21+
22+
extern void idt_init();
23+
extern void idt_register_interrupt(uint8_t i, void(*callback)());
24+
extern void add_idt_descriptor(uint8_t id, idt_descriptor desc);
25+
26+
#endif

0 commit comments

Comments
 (0)