Loading GDT in C.
This commit is contained in:
parent
879bfb0c8a
commit
a495a08cc0
@ -47,6 +47,8 @@ if(${CMAKE_SYSTEM_PROCESSOR} MATCHES "i.86")
|
|||||||
set(SRCS
|
set(SRCS
|
||||||
src/kernel/arch/x86/boot.s
|
src/kernel/arch/x86/boot.s
|
||||||
${SRCS}
|
${SRCS}
|
||||||
|
src/kernel/arch/x86/gdt.s
|
||||||
|
src/kernel/arch/x86/gdt.c
|
||||||
src/kernel/arch/x86/tty.c)
|
src/kernel/arch/x86/tty.c)
|
||||||
set(CMAKE_EXE_LINKER_FLAGS
|
set(CMAKE_EXE_LINKER_FLAGS
|
||||||
"-T ${CMAKE_CURRENT_SOURCE_DIR}/src/kernel/arch/x86/linker.ld -ffreestanding -nostdlib")
|
"-T ${CMAKE_CURRENT_SOURCE_DIR}/src/kernel/arch/x86/linker.ld -ffreestanding -nostdlib")
|
||||||
|
@ -45,8 +45,8 @@ stack_bottom:
|
|||||||
.skip 16384 # 16 KiB
|
.skip 16384 # 16 KiB
|
||||||
stack_top:
|
stack_top:
|
||||||
|
|
||||||
.section .data
|
/*.section .data
|
||||||
.include "gdt.s"
|
.include "gdt.s"*/
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* The linker script specifies the `_start' label as the entry point to the kernel
|
* The linker script specifies the `_start' label as the entry point to the kernel
|
||||||
@ -59,19 +59,10 @@ stack_top:
|
|||||||
_start:
|
_start:
|
||||||
# set the position of `%esp' to the top of the stack
|
# set the position of `%esp' to the top of the stack
|
||||||
mov $stack_top, %esp
|
mov $stack_top, %esp
|
||||||
|
mov %esp, %ebp
|
||||||
|
|
||||||
# GDT, paging, and other features
|
# GDT, paging, and other features
|
||||||
flush_gdt:
|
call gdt_install
|
||||||
cli
|
|
||||||
lgdt (gdtr)
|
|
||||||
movw $0x10, %ax
|
|
||||||
movw %ax, %ds
|
|
||||||
movw %ax, %es
|
|
||||||
movw %ax, %fs
|
|
||||||
movw %ax, %gs
|
|
||||||
movw %ax, %ss
|
|
||||||
ljmp $0x08, $flush_end
|
|
||||||
flush_end:
|
|
||||||
|
|
||||||
boot_kernel:
|
boot_kernel:
|
||||||
# enter high-level kernel (C)
|
# enter high-level kernel (C)
|
||||||
|
58
src/kernel/arch/x86/gdt.c
Normal file
58
src/kernel/arch/x86/gdt.c
Normal file
@ -0,0 +1,58 @@
|
|||||||
|
/*
|
||||||
|
* Copyright (C) 2018 Ortega Froysa, Nicolás <nortega@themusicinnoise.net>
|
||||||
|
* Author: Ortega Froysa, Nicolás <nortega@themusicinnoise.net>
|
||||||
|
*
|
||||||
|
* This program is free software: you can redistribute it and/or modify
|
||||||
|
* it under the terms of the GNU General Public License as published by
|
||||||
|
* the Free Software Foundation, either version 3 of the License, or
|
||||||
|
* (at your option) any later version.
|
||||||
|
*
|
||||||
|
* This program is distributed in the hope that it will be useful,
|
||||||
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
|
* GNU General Public License for more details.
|
||||||
|
*
|
||||||
|
* You should have received a copy of the GNU General Public License
|
||||||
|
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include "gdt.h"
|
||||||
|
|
||||||
|
/*
|
||||||
|
* ENTRIES:
|
||||||
|
* 0 - NULL entry
|
||||||
|
* 1/2 - kernel entries
|
||||||
|
* 3/4 - user entries
|
||||||
|
* 5 - TSS entry
|
||||||
|
*/
|
||||||
|
#define GDT_SIZE 3
|
||||||
|
|
||||||
|
struct segdesc gdt[GDT_SIZE];
|
||||||
|
struct segreg gdtr;
|
||||||
|
|
||||||
|
void gdt_entry_set(struct segdesc *entry, uint32_t base,
|
||||||
|
uint32_t limit, uint8_t access, uint8_t gran) {
|
||||||
|
// base
|
||||||
|
entry->base_low = base & 0xFFFF;
|
||||||
|
entry->base_mid = (base >> 16) & 0xFF;
|
||||||
|
entry->base_high = (base >> 24) & 0xFF;
|
||||||
|
|
||||||
|
// limit
|
||||||
|
entry->limit_low = limit & 0xFFFF;
|
||||||
|
entry->gran = (limit >> 16) & 0x0F;
|
||||||
|
|
||||||
|
// access and granularity flags
|
||||||
|
entry->gran |= gran & 0xF0;
|
||||||
|
entry->access = access;
|
||||||
|
}
|
||||||
|
|
||||||
|
void gdt_install() {
|
||||||
|
gdtr.base = (uint32_t)gdt;
|
||||||
|
gdtr.limit = sizeof(gdt)-1;
|
||||||
|
|
||||||
|
gdt_entry_set(&gdt[0], 0, 0, 0, 0);
|
||||||
|
gdt_entry_set(&gdt[1], 0, 0xFFFFFFFF, 0x9A, 0xCF);
|
||||||
|
gdt_entry_set(&gdt[2], 0, 0xFFFFFFFF, 0x92, 0xCF);
|
||||||
|
|
||||||
|
gdt_flush(&gdtr);
|
||||||
|
}
|
26
src/kernel/arch/x86/gdt.h
Normal file
26
src/kernel/arch/x86/gdt.h
Normal file
@ -0,0 +1,26 @@
|
|||||||
|
/*
|
||||||
|
* Copyright (C) 2018 Ortega Froysa, Nicolás <nortega@themusicinnoise.net>
|
||||||
|
* Author: Ortega Froysa, Nicolás <nortega@themusicinnoise.net>
|
||||||
|
*
|
||||||
|
* This program is free software: you can redistribute it and/or modify
|
||||||
|
* it under the terms of the GNU General Public License as published by
|
||||||
|
* the Free Software Foundation, either version 3 of the License, or
|
||||||
|
* (at your option) any later version.
|
||||||
|
*
|
||||||
|
* This program is distributed in the hope that it will be useful,
|
||||||
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
|
* GNU General Public License for more details.
|
||||||
|
*
|
||||||
|
* You should have received a copy of the GNU General Public License
|
||||||
|
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#pragma once
|
||||||
|
|
||||||
|
#include "structs.h"
|
||||||
|
|
||||||
|
extern void gdt_flush(struct segreg *gdtr);
|
||||||
|
void gdt_entry_set(struct segdesc *entry, uint32_t base,
|
||||||
|
uint32_t limit, uint8_t access, uint8_t gran);
|
||||||
|
void gdt_install();
|
@ -16,57 +16,22 @@
|
|||||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
/*
|
.section .text
|
||||||
* Create the GDT
|
.global gdt_flush
|
||||||
*/
|
.type gdt_flush, @function
|
||||||
gdt_start:
|
gdt_flush:
|
||||||
gdt_null:
|
pushl %ebp
|
||||||
.long 0x0
|
movl %esp, %ebp
|
||||||
.long 0x0
|
movl 8(%ebp), %eax
|
||||||
|
cli
|
||||||
gdt_kcode:
|
lgdt (%eax)
|
||||||
.word 0xFFFF # limit
|
movw $0x10, %ax
|
||||||
.word 0x0 # base
|
movw %ax, %ds
|
||||||
.byte 0x0 # base
|
movw %ax, %es
|
||||||
.byte 0b10011010 # 1st flags | type flags
|
movw %ax, %fs
|
||||||
.byte 0b11001111 # 2nd flags | limit
|
movw %ax, %gs
|
||||||
.byte 0x0 # base
|
movw %ax, %ss
|
||||||
|
ljmp $0x0008, $gdt_flush_end
|
||||||
gdt_kdata:
|
gdt_flush_end:
|
||||||
.word 0xFFFF # limit
|
popl %ebp
|
||||||
.word 0x0 # base
|
ret
|
||||||
.byte 0x0 # base
|
|
||||||
.byte 0b10010010 # 1st flags | type flags
|
|
||||||
.byte 0b11001111 # 2nd flags | limit
|
|
||||||
.byte 0x0 # base
|
|
||||||
|
|
||||||
gdt_ucode:
|
|
||||||
.word 0xFFFF # limit
|
|
||||||
.word 0x0 # base
|
|
||||||
.byte 0x0 # base
|
|
||||||
.byte 0b11111010 # 1st flags | type flags
|
|
||||||
.byte 0b11001111 # 2nd flags | limit
|
|
||||||
.byte 0x0 # base
|
|
||||||
|
|
||||||
gdt_udata:
|
|
||||||
.word 0xFFFF # limit
|
|
||||||
.word 0x0 # base
|
|
||||||
.byte 0x0 # base
|
|
||||||
.byte 0b11110010 # 1st flags | type flags
|
|
||||||
.byte 0b11001111 # 2nd flags | limit
|
|
||||||
.byte 0x0 # base
|
|
||||||
|
|
||||||
# TODO: setup the TSS
|
|
||||||
gdt_tss:
|
|
||||||
.word 0x0 # size of TSS (set later)
|
|
||||||
.word 0x0 # address of TSS (set later)
|
|
||||||
.byte 0x0 # address of TSS (set later)
|
|
||||||
.byte 0b10010001 # 1st flags | type flags
|
|
||||||
.byte 0b01000000 # 2nd flags | size of TSS (set later
|
|
||||||
.byte 0x0 # address of TSS (set later)
|
|
||||||
|
|
||||||
gdt_end:
|
|
||||||
|
|
||||||
gdtr:
|
|
||||||
.word (gdt_end - gdt_start - 1)
|
|
||||||
.long gdt_start
|
|
||||||
|
@ -18,10 +18,12 @@
|
|||||||
|
|
||||||
#pragma once
|
#pragma once
|
||||||
|
|
||||||
|
#include <stdint.h>
|
||||||
|
|
||||||
struct segdesc {
|
struct segdesc {
|
||||||
uint16_t limit_low;
|
uint16_t limit_low;
|
||||||
uint16_t base_low;
|
uint16_t base_low;
|
||||||
uint8_t base_middle;
|
uint8_t base_mid;
|
||||||
uint8_t access;
|
uint8_t access;
|
||||||
uint8_t gran;
|
uint8_t gran;
|
||||||
uint8_t base_high;
|
uint8_t base_high;
|
||||||
@ -72,3 +74,8 @@ struct tss {
|
|||||||
uint16_t iopb_r; // reserved
|
uint16_t iopb_r; // reserved
|
||||||
uint16_t iopb;
|
uint16_t iopb;
|
||||||
} __attribute__((packed));
|
} __attribute__((packed));
|
||||||
|
|
||||||
|
struct segreg {
|
||||||
|
uint16_t limit;
|
||||||
|
uint32_t base;
|
||||||
|
} __attribute__((packed));
|
||||||
|
Loading…
Reference in New Issue
Block a user