Where to load the GDT?
Posted: Thu Jan 25, 2024 2:34 pm
I've been looking at examples and it isn't clear to me where you're supposed to load the GDT. I've seen some examples where the GDT is a global variable and the structure is loaded like so:
Or should I hardcode the address of `gdt` like
Thoughts?
Code: Select all
#pragma pack(push, 1)
struct Descriptor
{
std::uint16_t segment_limit_low;
std::uint16_t base_address_low;
std::uint8_t base_address_mid;
std::uint8_t type : 4;
std::uint8_t system : 1;
std::uint8_t descriptor_privilege_level : 1;
std::uint8_t present : 1;
std::uint8_t segment_limit_high : 4;
std::uint8_t available : 1;
std::uint8_t d_or_b : 1;
std::uint8_t granularity : 1;
std::uint8_t base_address_high;
};
#pragma pack(pop)
struct [[gnu::packed]] DescriptorPointer
{
std::uint16_t limit;
void *base;
};
void load_gtdr(DescriptorPointer gdtr)
{
asm volatile(
"cli;"
"lgdtl %0;"
"sti;" ::"m"(gdtr));
}
// Global Variable
auto gdt = Lib::Array<Descriptor, 7> {};
void gdt_init()
{
auto gdtr = DescriptorPointer { .limit = 0xFFFF, &gdt };
load_gdt(gdtr)
}
Code: Select all
void gdt_init()
{
auto gdtr = DescriptorPointer { .limit = 0xFFFF, std::bit_cast<std::uint16_t*>(0xFFFF) };
load_gdt(gdtr)
}