Skip to content

Commit 110e37a

Browse files
committed
Initialization of GDT
1 parent fb7e785 commit 110e37a

File tree

11 files changed

+232
-13
lines changed

11 files changed

+232
-13
lines changed

.vscode/settings.json

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,8 @@
11
{
22
"files.associations": {
3-
"terminal.h": "c"
3+
"terminal.h": "c",
4+
"idt.h": "c",
5+
"gdt.h": "c",
6+
"types.h": "c"
47
}
58
}

Makefile

Lines changed: 5 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -10,7 +10,10 @@ TARGET := testos.bin
1010
ALL_OBJ := environment.o \
1111
boot.o \
1212
kernel.o \
13-
string.o
13+
string.o \
14+
idt.o \
15+
gdt.o \
16+
load_gdt.o
1417
ALL_DEP := $(patsubst %.o,.%.d,$(ALL_OBJ))
1518

1619
#Assembly configuration
@@ -25,7 +28,7 @@ CFLAGS := -std=gnu99 -m32 -ffreestanding -O2 -Wall -Wextra
2528
LD := ld
2629
LD_FLAGS := -m elf_i386 -T linker.ld
2730

28-
#all rules
31+
#All rules
2932
.PHONY : all testos clean
3033
all : $(TARGET)
3134
testos : $(TARGET)

boot.asm

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -17,3 +17,4 @@ start:
1717
extern environment
1818
jmp environment
1919
hlt
20+

environment.asm

Lines changed: 0 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -12,8 +12,3 @@ align 4
1212
stack_bottom:
1313
resb 16384
1414
stack_top:
15-
16-
section .text
17-
resb 16384
18-
19-

gdt.c

Lines changed: 42 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,42 @@
1+
#include "gdt.h"
2+
3+
struct gdt_entry gdt_entry(dword base, dword limit, byte flags, byte type_s_dpl_p)
4+
{
5+
struct gdt_entry result;
6+
7+
result.base_lo = base_lo(base);
8+
result.base_mid = base_mid(base);
9+
result.base_hi = base_hi(base);
10+
result.limit_lo = limit_lo(limit);
11+
result.limit_hi_flags = limit_hi_flags(limit, flags);
12+
result.type_s_dpl_p = type_s_dpl_p;
13+
14+
return result;
15+
}
16+
17+
void gdt_init()
18+
{
19+
qword* gdt_d;
20+
byte flags_;
21+
flags_ = flags(0,0,1,1);
22+
23+
/*
24+
we need this since the two first entries (not actually entries)
25+
contain the size of the table and the address to the table
26+
*/
27+
gdt_d = (qword*)gdt;
28+
gdt_d[0] = 6*8; //size of the table
29+
gdt_d[1] = (qword)&gdt; //address of the table
30+
31+
//ring 0 data segment
32+
gdt[2] = gdt_entry(0, 4*1024*1024,flags_, type_s_dpl_p(type(0, 0, 1, 0), 0, 0, 1));
33+
//ring 0 code segment
34+
gdt[3] = gdt_entry(0, 4*1024*1024,flags_, type_s_dpl_p(type(1, 0, 1, 0), 0, 0, 1));
35+
//ring 3 data segment
36+
gdt[4] = gdt_entry(0, 4*1024*1024,flags_, type_s_dpl_p(type(0, 0, 1, 0), 0, 3, 1));
37+
//ring 3 code segment
38+
gdt[5] = gdt_entry(0, 4*1024*1024,flags_, type_s_dpl_p(type(1, 0, 1, 0), 0, 3, 1));
39+
40+
//load the gdt table
41+
load_gdt((dword)gdt, 6*8);
42+
}

gdt.h

Lines changed: 151 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,151 @@
1+
/*
2+
This header file declares all the necessary bits to initialize and load the GDT (global decriptor table)
3+
*/
4+
5+
#ifndef __gdt_h__
6+
#define __gdt_h__
7+
8+
#include "types.h"
9+
10+
enum gdt_entry_type
11+
{
12+
ACCESSED = 1 << 0,
13+
WR = 1 << 1,
14+
EC = 1 << 2,
15+
CS = 1 << 3
16+
};
17+
18+
/*
19+
GDT entry structure (bit representation):
20+
0-15 : Segment limit - low portion | WORD
21+
16-31 : Base address - low portion | WORD
22+
32-39 : Base address - mid portion | BYTE
23+
40-43 : Type (Page 2758 in IA-32 manual) | BYTE
24+
44 : S (system/cs-ds) | " "
25+
45-6 : DPL (privilege ring 0 to 3) | " "
26+
47 : P (present in memory) | " "
27+
48-51 : Segment limit - high portion | BYTE
28+
52 : AVL (available bit) | " " (flags)
29+
53 : L (32/64 bit segment) | " " (flags)
30+
54 : D/B (16 bit/32 bit) | " " (flags)
31+
55 : G (granularity) | " " (flags)
32+
56-63 : Base address - high portion | BYTE
33+
*/
34+
35+
/*
36+
base structure:
37+
0x0000FFFF low
38+
0x00FF0000 mid
39+
0xFF000000 high
40+
*/
41+
42+
/*
43+
limit structure:
44+
0x0000FFFF low
45+
0x000F0000 high
46+
*/
47+
48+
struct gdt_entry
49+
{
50+
word limit_lo;
51+
word base_lo;
52+
byte base_mid;
53+
byte type_s_dpl_p;
54+
byte limit_hi_flags;
55+
byte base_hi;
56+
} __attribute__((packed));
57+
58+
inline word limit_lo(dword limit)
59+
{
60+
word result;
61+
62+
result = limit & 0x0000FFFF;
63+
64+
return result;
65+
}
66+
67+
inline word base_lo(dword base)
68+
{
69+
word result;
70+
71+
result = base & 0x0000FFFF;
72+
73+
return result;
74+
}
75+
76+
inline byte base_mid(dword base)
77+
{
78+
byte result;
79+
80+
result = (base & 0x00FF0000) >> 4*4;
81+
82+
return result;
83+
}
84+
85+
inline byte limit_hi_flags(dword limit, byte flags)
86+
{
87+
byte limit_hi, result;
88+
89+
//take bits 16-19 from limit and put them in limit_hi
90+
limit_hi = (limit & 0x000F0000) >> (4*4);
91+
92+
//or limit_hi and flags together
93+
result = limit_hi | (flags << 4);
94+
95+
return result;
96+
}
97+
98+
inline byte base_hi(dword base)
99+
{
100+
byte result;
101+
102+
result = (base & 0xFF000000) >> (4*6);
103+
104+
return result;
105+
}
106+
107+
inline byte flags(byte avl, byte l, byte db, byte g)
108+
{
109+
byte result;
110+
111+
result = ((avl & 1) << 0) |
112+
((l & 1) << 2) |
113+
((db & 1) << 3) |
114+
((g & 1) << 4);
115+
116+
return result;
117+
}
118+
119+
inline byte type(byte ds_cs, byte ec, byte rw, byte a)
120+
{
121+
byte result;
122+
123+
result = ((a & 1) << 0) |
124+
((rw & 1) << 1) |
125+
((ec & 1) << 2) |
126+
((ds_cs & 1) << 3);
127+
128+
return result;
129+
}
130+
131+
inline byte type_s_dpl_p(byte type, byte s, byte dpl, byte p)
132+
{
133+
byte result;
134+
135+
result = (type )|
136+
((s & 1) << 4)|
137+
((dpl & (1|2)) << 5)|
138+
((p & 1) << 7);
139+
140+
return result;
141+
}
142+
143+
struct gdt_entry gdt_entry(dword base, dword limit, byte flags, byte type_s_dpl_p);
144+
145+
extern void load_gdt(dword gdt_ptr, word table_size);
146+
147+
void gdt_init();
148+
149+
struct gdt_entry gdt[6];
150+
151+
#endif

gdt.s

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1 @@
1+
.file "gdt.c"

idt.c

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1 @@
1+
#include "idt.h"

idt.h

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,6 @@
1+
#ifndef __idt_h__
2+
#define __idt_h__
3+
4+
#include "types.h"
5+
6+
#endif

kernel.c

Lines changed: 9 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -1,12 +1,16 @@
11
#include "terminal.h"
2+
#include "gdt.h"
23

34
void kernel_main()
45
{
56
terminal_clear(vga_entry(' ', vga_entry_color(VGA_COLOR_GRAY, VGA_COLOR_BLUE)));
6-
terminal_write_str("Hello kernel world! 1\n");
7-
8-
9-
7+
terminal_write_str("TestOS V 0.0000001\n");
8+
gdt_init();
109

1110
return;
12-
}
11+
}
12+
13+
void* do_nothing(void* ptr)
14+
{
15+
return ptr + 1;
16+
}

0 commit comments

Comments
 (0)