OurOS 0.1
Operating System built by McGill Students
 
Loading...
Searching...
No Matches
gdt.h
1#ifndef _CPU_GDT_H
2#define _CPU_GDT_H
3
4#include <stdint.h>
5
6// High flags
7// Note that in long mode: D=0, L=1
8#define GDT_LONG_MODE 0x20
9// Low flags
10#define GDT_PRESENT 0x80
11// a. Descriptor Privilege Level
12#define GDT_RING_0 0x00
13#define GDT_RING_1 0x20
14#define GDT_RING_2 0x40
15#define GDT_RING_3 0x60
16// b. Conforming
17#define GDT_CONFORMING 0x04
18
19// For now, we make use of three GDT entries
20#define GDT_SEGMENTS 3
21// 1. "null" descriptor
22#define GDT_NULL_OFFSET 0x00
23// 2. kernel code descriptor
24//
25// Note: In 64-bit code segments descriptors,
26// the CPU recognizes:
27// a. Present bit
28// b. DPL field
29// c. Conforming bit
30// All other fields are ignored.
31#define GDT_KCODE 0x08
32#define GDT_KCODE_LIMIT 0
33#define GDT_KCODE_BASE 0
34#define GDT_KCODE_MISC_LOW GDT_PRESENT + GDT_RING_0
35#define GDT_KCODE_MISC_HIGH GDT_LONG_MODE
36// 3. kernel data descriptor
37//
38// Note: In 64-bit code segments descriptors,
39// the CPU recognizes only the Present bit.
40// All other fields are ignored.
41#define GDT_KDATA 0x10
42#define GDT_KDATA_LIMIT 0
43#define GDT_KDATA_BASE 0
44#define GDT_KDATA_MISC_LOW GDT_PRESENT
45#define GDT_KDATA_MISC_HIGH 0
46
47
48#define GDT_ENTRY_CREATE(lim, base, low, high) { \
49 lim & 0xffff, /* Segment limit (low) */ \
50 base & 0xffff, /* Base Address (low) */ \
51 (base >> 16) & 0xff, /* Base Address (med) */ \
52 low, /* Present/DPL/Conform */ \
53 high + (lim >> 16), /* Flags/Limit (high) */ \
54 base >> 24, /* Base Address (high) */ \
55}
56
57// A GDT is necessary for our kernel
58struct cpu_gdt_entry {
59 uint16_t limit_low;
60 uint16_t base_low;
61 uint8_t base_med;
62 uint8_t present_dpl_and_conform;
63 uint8_t flags_and_limit_high;
64 uint8_t base_high;
65} __attribute__((packed));
66
67// lgdt loads this data into the register
68struct cpu_gdt_register {
69 uint16_t limit;
70 uint64_t base;
71} __attribute__((packed));
72
73// Load the kernel's gdt in the GDT register
74void cpu_gdt_bind(void);
75// Describe the currently loaded GDT.
76void cpu_gdt_describe(char *buf, uint64_t bufsz);
77
78#endif