COBE 0.1 ALPHA
|
00001 #include <gdt.h> 00002 #include <stdint.h> 00003 #include <multitasking.h> 00004 #include <stdio.h> 00005 00011 00012 gdt_entry gdt[6]; //----------Erzeugt sechs GDT Einträge und einen Pointer---------- 00014 gdt_ptr gdt_pointer; 00015 00017 extern new_tss_t tss; 00018 00020 00029 void init_gdt() { 00030 00031 gdt_pointer.limit_gdt = (sizeof(gdt_entry) * 6) -1; //----------Setzt das Limit der GDT und die Basis-Addresse---------- 00032 gdt_pointer.base_gdt = (unsigned int)&gdt; 00033 00034 set_gdt(0, 0, 0, 0, 0); //----------Der erste GDT Eintrag muss 0 sein---------- 00035 set_gdt(1, 0, 0xFFFFFFFF, 0x9A, 0xCF); //----------Das CodeSegment wird beschrieben---------- 00036 set_gdt(2, 0, 0xFFFFFFFF, 0x92, 0xCF); //----------Das DatenSegment wird beschrieben---------- 00037 set_gdt(3, 0, 0xFFFFFFFF, 0xFA, 0xCF); //----------Das erste User-DatenSegment wird beschrieben---------- 00038 set_gdt(4, 0, 0xFFFFFFFF, 0xF2, 0xCF); //----------Das zweite User-DatenSegment wird beschrieben---------- 00039 set_gdt(5, (uint32_t) &tss, (uint32_t) &tss + sizeof(tss), 0xE9, 0x00); //----------Das Task-State-Segment wird beschrieben---------- 00040 00041 kmemset(&tss, 0, sizeof(tss)); //----------Die TSS wird mit 0 belegt---------- 00042 tss.ss0 = 0x10; //----------ss0 ist Standardmäßig 0x10, CS auf 0x08 für RING0---------- 00043 tss.cs = 0x08; 00044 00045 __asm volatile("lgdt (gdt_pointer)"); //----------Der Pointer auf die GDT wird in das GDT-Register geschrieben---------- 00046 00047 //----------Die DatenSegmente werden geladen, in das Code-Segment kann nur gesprungen werden---------- 00048 __asm volatile( 00049 "mov $0x10, %ax;" 00050 "mov %ax, %ds;" 00051 "mov %ax, %es;" 00052 "mov %ax, %ss;" 00053 "ljmp $0x8, $.1;" 00054 ".1:" 00055 ); 00056 00057 __asm volatile("ltr %%ax" :: "a" (5 << 3)); //----------Das Task-Register wird neu geladen---------- 00058 return; 00059 } 00060 00062 00075 void set_gdt(int gdt_num, unsigned int adress, unsigned int size, unsigned char access, unsigned char flags) { 00076 00077 //----------Die Basisadresse wird in drei Teile gesplittet, ist aber immer in modernen Systemen 0---------- 00078 gdt[gdt_num].s_adress_low = (adress & 0xFFFF); 00079 gdt[gdt_num].s_adress_mid = (adress >> 16) & 0xFF; 00080 gdt[gdt_num].s_adress_high = (adress >> 24) & 0xFF; 00081 00082 gdt[gdt_num].s_size = (size & 0xFFFF); //----------Das Limit des Segments wird geschrieben---------- 00083 gdt[gdt_num].accs = access; //----------Das Access-Byte wird in die GDT geschrieben---------- 00084 00085 gdt[gdt_num].flags = (size >> 16) & 0x0F; //----------Die Flags sind in zwei Teile zerlegt, werden hier geschrieben---------- 00086 gdt[gdt_num].flags |= flags & 0xF0; 00087 return; 00088 }