feat(cpu): add GDT and TSS for ring 0 and ring 3 segments
This commit is contained in:
1 parent
7b52e9d3f9
commit
4843406bf3
4 files changed
+117
No files matched your search
@@ -0,0 +1,15 @@
|
|||||||
|
#ifndef FROSTBYTE_GDT_H
|
||||||
|
#define FROSTBYTE_GDT_H
|
||||||
|
|
||||||
|
#include "types.h"
|
||||||
|
|
||||||
|
#define kernelCodeSelector 0x08
|
||||||
|
#define kernelDataSelector 0x10
|
||||||
|
#define userCodeSelector 0x18
|
||||||
|
#define userDataSelector 0x20
|
||||||
|
#define tssSelector 0x28
|
||||||
|
|
||||||
|
void gdtInit(void);
|
||||||
|
void gdtInstallTss(uint64 base, uint32 limit);
|
||||||
|
|
||||||
|
#endif
|
||||||
@@ -0,0 +1,9 @@
|
|||||||
|
#ifndef FROSTBYTE_TSS_H
|
||||||
|
#define FROSTBYTE_TSS_H
|
||||||
|
|
||||||
|
#include "types.h"
|
||||||
|
|
||||||
|
void tssInit(uint64 rsp0);
|
||||||
|
void tssSetRsp0(uint64 rsp0);
|
||||||
|
|
||||||
|
#endif
|
||||||
@@ -0,0 +1,55 @@
|
|||||||
|
#include "gdt.h"
|
||||||
|
#include "types.h"
|
||||||
|
|
||||||
|
typedef struct GdtPointer {
|
||||||
|
uint16 limit;
|
||||||
|
uint64 base;
|
||||||
|
} __attribute__((packed)) GdtPointer;
|
||||||
|
|
||||||
|
static uint64 gdtEntries[7];
|
||||||
|
static GdtPointer gdtPointer;
|
||||||
|
|
||||||
|
void gdtInit(void)
|
||||||
|
{
|
||||||
|
gdtEntries[0] = 0x0000000000000000ull;
|
||||||
|
gdtEntries[1] = 0x00AF9A000000FFFFull;
|
||||||
|
gdtEntries[2] = 0x00CF92000000FFFFull;
|
||||||
|
gdtEntries[3] = 0x00AFFA000000FFFFull;
|
||||||
|
gdtEntries[4] = 0x00CFF2000000FFFFull;
|
||||||
|
gdtEntries[5] = 0x0000000000000000ull;
|
||||||
|
gdtEntries[6] = 0x0000000000000000ull;
|
||||||
|
|
||||||
|
gdtPointer.limit = (uint16)(sizeof(gdtEntries) - 1);
|
||||||
|
gdtPointer.base = (uint64)&gdtEntries;
|
||||||
|
|
||||||
|
__asm__ volatile(
|
||||||
|
"lgdt %0\n"
|
||||||
|
"pushq $0x08\n"
|
||||||
|
"leaq 1f(%%rip), %%rax\n"
|
||||||
|
"pushq %%rax\n"
|
||||||
|
"lretq\n"
|
||||||
|
"1:\n"
|
||||||
|
"movw $0x10, %%ax\n"
|
||||||
|
"movw %%ax, %%ds\n"
|
||||||
|
"movw %%ax, %%es\n"
|
||||||
|
"movw %%ax, %%ss\n"
|
||||||
|
"movw %%ax, %%fs\n"
|
||||||
|
"movw %%ax, %%gs\n"
|
||||||
|
:
|
||||||
|
: "m"(gdtPointer)
|
||||||
|
: "rax", "memory");
|
||||||
|
}
|
||||||
|
|
||||||
|
void gdtInstallTss(uint64 base, uint32 limit)
|
||||||
|
{
|
||||||
|
uint64 low = 0;
|
||||||
|
low |= (uint64)(limit & 0xFFFF);
|
||||||
|
low |= (base & 0xFFFFull) << 16;
|
||||||
|
low |= ((base >> 16) & 0xFFull) << 32;
|
||||||
|
low |= (uint64)0x89 << 40;
|
||||||
|
low |= (uint64)((limit >> 16) & 0xF) << 48;
|
||||||
|
low |= ((base >> 24) & 0xFFull) << 56;
|
||||||
|
|
||||||
|
gdtEntries[5] = low;
|
||||||
|
gdtEntries[6] = (base >> 32) & 0xFFFFFFFFull;
|
||||||
|
}
|
||||||
@@ -0,0 +1,38 @@
|
|||||||
|
#include "tss.h"
|
||||||
|
#include "gdt.h"
|
||||||
|
#include "string.h"
|
||||||
|
|
||||||
|
typedef struct Tss {
|
||||||
|
uint32 reserved0;
|
||||||
|
uint64 rsp0;
|
||||||
|
uint64 rsp1;
|
||||||
|
uint64 rsp2;
|
||||||
|
uint64 reserved1;
|
||||||
|
uint64 ist1;
|
||||||
|
uint64 ist2;
|
||||||
|
uint64 ist3;
|
||||||
|
uint64 ist4;
|
||||||
|
uint64 ist5;
|
||||||
|
uint64 ist6;
|
||||||
|
uint64 ist7;
|
||||||
|
uint64 reserved2;
|
||||||
|
uint16 reserved3;
|
||||||
|
uint16 iomapBase;
|
||||||
|
} __attribute__((packed)) Tss;
|
||||||
|
|
||||||
|
static Tss tss;
|
||||||
|
|
||||||
|
void tssInit(uint64 rsp0)
|
||||||
|
{
|
||||||
|
memset(&tss, 0, sizeof(tss));
|
||||||
|
tss.rsp0 = rsp0;
|
||||||
|
tss.iomapBase = sizeof(Tss);
|
||||||
|
|
||||||
|
gdtInstallTss((uint64)&tss, sizeof(Tss) - 1);
|
||||||
|
__asm__ volatile("ltr %w0" : : "r"((uint16)tssSelector));
|
||||||
|
}
|
||||||
|
|
||||||
|
void tssSetRsp0(uint64 rsp0)
|
||||||
|
{
|
||||||
|
tss.rsp0 = rsp0;
|
||||||
|
}
|
||||||
Reference in new issue
Block a user