Add protos abstraction and stivale and qword protocols

This commit is contained in:
mintsuki 2020-03-25 21:05:14 +01:00
parent c66d052afc
commit 8494b1d880
6 changed files with 105 additions and 67 deletions

View File

@ -48,7 +48,7 @@ struct elf_phdr {
#define FIXED_HIGHER_HALF_OFFSET ((uint64_t)0xffffffff80000000)
int elf_load(struct echfs_file_handle *fd) {
int elf_load(struct echfs_file_handle *fd, uint64_t *entry_point) {
struct elf_hdr hdr;
echfs_read(fd, &hdr, 0, sizeof(struct elf_hdr));
@ -89,60 +89,7 @@ int elf_load(struct echfs_file_handle *fd) {
}
}
volatile struct {
uint64_t pml4[512];
uint64_t pml3_lo[512];
uint64_t pml3_hi[512];
uint64_t pml2_0gb[512];
uint64_t pml2_1gb[512];
uint64_t pml2_2gb[512];
uint64_t pml2_3gb[512];
} *pagemap = (void *)0x10000;
// first, zero out the pagemap
for (uint64_t *p = (uint64_t *)pagemap; p < &pagemap->pml3_hi[512]; p++)
*p = 0;
pagemap->pml4[511] = (uint64_t)(size_t)pagemap->pml3_hi | 0x03;
pagemap->pml4[256] = (uint64_t)(size_t)pagemap->pml3_lo | 0x03;
pagemap->pml4[0] = (uint64_t)(size_t)pagemap->pml3_lo | 0x03;
pagemap->pml3_hi[510] = (uint64_t)(size_t)pagemap->pml2_0gb | 0x03;
pagemap->pml3_hi[511] = (uint64_t)(size_t)pagemap->pml2_1gb | 0x03;
pagemap->pml3_lo[0] = (uint64_t)(size_t)pagemap->pml2_0gb | 0x03;
pagemap->pml3_lo[1] = (uint64_t)(size_t)pagemap->pml2_1gb | 0x03;
pagemap->pml3_lo[2] = (uint64_t)(size_t)pagemap->pml2_2gb | 0x03;
pagemap->pml3_lo[3] = (uint64_t)(size_t)pagemap->pml2_3gb | 0x03;
// populate the page directories
for (size_t i = 0; i < 512 * 4; i++)
(&pagemap->pml2_0gb[0])[i] = (i * 0x1000) | 0x03 | (1 << 7);
asm volatile (
"cli\n\t"
"mov cr3, eax\n\t"
"mov eax, cr4\n\t"
"or eax, 1 << 5 | 1 << 7\n\t"
"mov cr4, eax\n\t"
"mov ecx, 0xc0000080\n\t"
"rdmsr\n\t"
"or eax, 1 << 8\n\t"
"wrmsr\n\t"
"mov eax, cr0\n\t"
"or eax, 1 << 31\n\t"
"mov cr0, eax\n\t"
"jmp 0x28:1f\n\t"
"1: .code64\n\t"
"mov ax, 0x30\n\t"
"mov ds, ax\n\t"
"mov es, ax\n\t"
"mov fs, ax\n\t"
"mov gs, ax\n\t"
"mov ss, ax\n\t"
"jmp [rbx]\n\t"
".code32\n\t"
:
: "a" (pagemap), "b" (&hdr.entry)
);
*entry_point = hdr.entry;
return 0;
}

View File

@ -1,8 +1,9 @@
#ifndef __LIB__ELF_H__
#define __LIB__ELF_H__
#include <stdint.h>
#include <fs/echfs.h>
int elf_load(struct echfs_file_handle *fd);
int elf_load(struct echfs_file_handle *fd, uint64_t *entry_point);
#endif

View File

@ -8,11 +8,13 @@ asm (
#include <drivers/vga_textmode.h>
#include <lib/real.h>
#include <lib/blib.h>
#include <lib/libc.h>
#include <lib/mbr.h>
#include <lib/config.h>
#include <fs/echfs.h>
#include <sys/interrupt.h>
#include <lib/elf.h>
#include <protos/stivale.h>
#define CONFIG_NAME "qloader2.cfg"
@ -56,7 +58,7 @@ void main(int boot_drive) {
}
int drive, part;
char path[128], cmdline[128];
char path[128], cmdline[128], proto[64];
if (config_loaded) {
char buf[32];
@ -66,6 +68,7 @@ void main(int boot_drive) {
part = (int)strtoui(buf);
config_get_value(path, 128, (void*)0x100000, "KERNEL_PATH");
config_get_value(cmdline, 128, (void*)0x100000, "KERNEL_CMDLINE");
config_get_value(proto, 64, (void*)0x100000, "KERNEL_PROTO");
} else {
print(" !! NO CONFIG FILE FOUND ON BOOT DRIVE !!");
for (;;);
@ -80,17 +83,24 @@ void main(int boot_drive) {
break;
}
}
print("\n");
echfs_open(&f, drive, part, path);
echfs_read(&f, (void *)0x100000, 0, f.dir_entry.size);
//elf_load(&f);
// Boot the kernel.
asm volatile (
"cli\n\t"
"jmp 0x100000\n\t"
:
: "b" (cmdline)
: "memory"
);
if (!strcmp(proto, "stivale")) {
stivale_load(&f);
} else if (!strcmp(proto, "qword")) {
echfs_read(&f, (void *)0x100000, 0, f.dir_entry.size);
// Boot the kernel.
asm volatile (
"cli\n\t"
"jmp 0x100000\n\t"
:
: "b" (cmdline)
: "memory"
);
} else {
print("Invalid protocol specified: `%s`.\n", proto);
for (;;);
}
}

71
src/protos/stivale.c Normal file
View File

@ -0,0 +1,71 @@
#include <stdint.h>
#include <stddef.h>
#include <protos/stivale.h>
#include <lib/elf.h>
struct stivale_header {
uint64_t magic;
uint64_t stack;
uint8_t video_mode; // 0 = default at boot (CGA text mode). 1 = graphical VESA
};
void stivale_load(struct echfs_file_handle *fd) {
uint64_t entry_point;
elf_load(fd, &entry_point);
volatile struct {
uint64_t pml4[512];
uint64_t pml3_lo[512];
uint64_t pml3_hi[512];
uint64_t pml2_0gb[512];
uint64_t pml2_1gb[512];
uint64_t pml2_2gb[512];
uint64_t pml2_3gb[512];
} *pagemap = (void *)0x10000;
// first, zero out the pagemap
for (uint64_t *p = (uint64_t *)pagemap; p < &pagemap->pml3_hi[512]; p++)
*p = 0;
pagemap->pml4[511] = (uint64_t)(size_t)pagemap->pml3_hi | 0x03;
pagemap->pml4[256] = (uint64_t)(size_t)pagemap->pml3_lo | 0x03;
pagemap->pml4[0] = (uint64_t)(size_t)pagemap->pml3_lo | 0x03;
pagemap->pml3_hi[510] = (uint64_t)(size_t)pagemap->pml2_0gb | 0x03;
pagemap->pml3_hi[511] = (uint64_t)(size_t)pagemap->pml2_1gb | 0x03;
pagemap->pml3_lo[0] = (uint64_t)(size_t)pagemap->pml2_0gb | 0x03;
pagemap->pml3_lo[1] = (uint64_t)(size_t)pagemap->pml2_1gb | 0x03;
pagemap->pml3_lo[2] = (uint64_t)(size_t)pagemap->pml2_2gb | 0x03;
pagemap->pml3_lo[3] = (uint64_t)(size_t)pagemap->pml2_3gb | 0x03;
// populate the page directories
for (size_t i = 0; i < 512 * 4; i++)
(&pagemap->pml2_0gb[0])[i] = (i * 0x1000) | 0x03 | (1 << 7);
asm volatile (
"cli\n\t"
"mov cr3, eax\n\t"
"mov eax, cr4\n\t"
"or eax, 1 << 5 | 1 << 7\n\t"
"mov cr4, eax\n\t"
"mov ecx, 0xc0000080\n\t"
"rdmsr\n\t"
"or eax, 1 << 8\n\t"
"wrmsr\n\t"
"mov eax, cr0\n\t"
"or eax, 1 << 31\n\t"
"mov cr0, eax\n\t"
"jmp 0x28:1f\n\t"
"1: .code64\n\t"
"mov ax, 0x30\n\t"
"mov ds, ax\n\t"
"mov es, ax\n\t"
"mov fs, ax\n\t"
"mov gs, ax\n\t"
"mov ss, ax\n\t"
"jmp [rbx]\n\t"
".code32\n\t"
:
: "a" (pagemap), "b" (&entry_point)
);
}

8
src/protos/stivale.h Normal file
View File

@ -0,0 +1,8 @@
#ifndef __PROTOS__STIVALE_H__
#define __PROTOS__STIVALE_H__
#include <fs/echfs.h>
void stivale_load(struct echfs_file_handle *fd);
#endif

View File

@ -1,4 +1,5 @@
KERNEL_DRIVE=128
KERNEL_PARTITION=0
KERNEL_PATH=test.elf
KERNEL_PROTO=stivale
KERNEL_CMDLINE=none