Nabend zusammen,
mir ist aufgefallen, dass mein GDT nicht richtig war, wodurch das mit dem TSS nicht richtig geklappt hat.
Nun habe ich den GDT ein wenig umgeschrieben, allerdings bekomme ich erst eine DPF und dann einen GPF.
Das Problem tritt auf, wenn ich den GDT update.
Der Code sieht wie folgt aus:
//memset(&GDT , 0 , GDT_SIZE * sizeof(struct gd_table));
gdt_set_gate(1, 0, 0xFFFFF, GDT_SEGMENT | GDT_PRESENT | GDT_CODE , GDT_RING_0); // Kernel code
gdt_set_gate(2, 0, 0xFFFFF, GDT_SEGMENT | GDT_PRESENT | GDT_DATA , GDT_RING_0); // Kernel data
gdt_set_gate(3, 0, 0xFFFFF, GDT_SEGMENT | GDT_PRESENT | GDT_CODE , GDT_RING_3); // User code
gdt_set_gate(4, 0, 0xFFFFF, GDT_SEGMENT | GDT_PRESENT | GDT_DATA , GDT_RING_3); // User data
puts("set up gates");
gdt_set_gran_bit(5 , (uint32_t)&krn_tss , sizeof(krn_tss) - 1 , GDT_PRESENT | GDT_TSS, GDT_RING_3);
puts("\nset up granularity");
gdt_update();
gdt_update sieht wie folgt aus:
/* Defines the Pointer to a GDT entry */
struct gdt_ptr{
uint16_t limit;
uint32_t base;
} __attribute__((packed)) gp = {
.limit = sizeof(struct gd_table)*GDT_SIZE - 1,
.base = (uint32_t)&GDT,
};
__asm__("lgdtl %0\n\t"
"ljmpl $0x08, $1f\n\t"
"1:\n\t"
"mov $0x10, %%eax\n\t"
"mov %%eax, %%ds\n\t"
"mov %%eax, %%es\n\t"
"mov %%eax, %%fs\n\t"
"mov %%eax, %%gs\n\t"
"mov %%eax, %%ss\n\t" : : "m" (gp) : "eax");
gdt_set_gate und gdt_set_gran_bit sehen wie folgt aus:
void gdt_set_gate(uint8_t num , uint32_t base , uint32_t limit , uint8_t access , uint8_t priv){
if(num < GDT_SIZE){
GDT[num].limit_low = (limit & 0xFFFF);
GDT[num].flags = ((limit >> 16) & 0x0F);
GDT[num].base_low = (base & 0xFFFF);
GDT[num].base_middle = (base >> 16) & 0xFF;
GDT[num].base_high = (base >> 24) & 0xFF;
GDT[num].access = access | ((priv & 3) << 5);
}
else
panic("Tried to set a wrong GDT-Gate.");
}
void gdt_set_gran_bit(uint8_t num , uint32_t base , uint32_t limit , uint8_t access , uint8_t priv){
gdt_set_gate(num , base , limit , access , priv);
GDT[num].flags = ((limit >> 16) & 0x0F) | 0x40;
}
Mein GDT sieht wie folgt aus:
struct gd_table{
uint16_t limit_low;
uint16_t base_low;
uint8_t base_middle;
uint8_t access;
uint8_t flags;
uint8_t base_high;
};
seht ihr den fehler?
Die Definitionen bei gdt_set_gate und gdt_set_gran_bit sind richtig.
Die habe ich kontrolliert.
Danke für eure Hilfe.