Compare commits

...

4 Commits

Author SHA1 Message Date
brice.boisson 5492a13018 Fix: warning 2023-10-11 10:13:35 +09:00
brice.boisson 37dbb99f50 Add: userland hello world code 2023-10-11 09:38:29 +09:00
BOISSON Brice 917988e871
Merge pull request #3 from BriceBoisson/brice-elf
Brice elf
2023-09-27 10:39:36 +09:00
BOISSON Brice 883afe0753
Update README.md 2023-09-07 14:41:46 +09:00
21 changed files with 88 additions and 49 deletions

View File

@ -11,8 +11,8 @@ install:
bin:
$(MAKE) -C $(LIB)
gcc -c test.c -Ilibk -Llibk -lk -m32
ld -m elf_i386 -Ttext=0x6000000 --entry=main test.o -L./libk/ -lk
gcc -c ./app/$(APP).c -Ilibk -Llibk -lk -m32
ld -m elf_i386 -Ttext=0x6000000 --entry=main ./$(APP).o -L./libk/ -lk
objcopy --input binary --output elf32-i386 --binary-architecture i386 --rename-section .data=.rodata,CONTENTS,ALLOC,LOAD,READONLY,DATA a.out myfile.o
cp myfile.o $(SOURCEDIR)/myfile.o

View File

@ -5,3 +5,4 @@ GRUBDIR = iso
SOURCEDIR = src
TARGET = kernel
LIB=libk
APP=hello_world

View File

@ -6,7 +6,9 @@ This kernel is written as a educative project. The goal is to have a kernel able
- [X] Manage IRQ (enable PIC)
- [X] Running and Userland (TSS)
- [X] Let the userland call the kernel (syscall)
- [ ] Use paging
- [ ] Running multiple userland (ordonnanceur)
- [ ] Using ext2 File System
- [ ] Running elf binary
- [ ] Having a small libc and needed syscall to run the shell
- [ ] (Bonus) Having a basic visual interface (VGA ?)

10
app/hello_world.c Normal file
View File

@ -0,0 +1,10 @@
#include <syscall.h>
static char s[] = "Hello from userland!\n";
int main(void)
{
write(1, s, 21);
while (1);
return 0;
}

View File

@ -16,6 +16,7 @@ OBJS = \
paging.o \
elf.o \
myfile.o \
tools.o \
DEPS = $(OBJS:.o=.d)

View File

@ -19,7 +19,7 @@ int print_variadic(char *msg, va_list args)
write_serial(va_arg(args, char *));
break;
case 'b':
write_serial_bin(va_arg(args, char *), false);
write_serial_bin((int) va_arg(args, char *), false);
break;
case 'c':
write_serial_char(va_arg(args, int));
@ -36,12 +36,14 @@ int print_variadic(char *msg, va_list args)
msg++;
}
}
return 0;
}
int debug_info(char *fnt, char *msg, ...)
int debug_info(const char *fnt, char *msg, ...)
{
write_serial("\033[0;34m[INFO]\033[0m ");
write_serial(fnt);
write_serial((char *) fnt);
write_serial("\t: ");
va_list args;
@ -54,10 +56,10 @@ int debug_info(char *fnt, char *msg, ...)
return 0;
}
int debug_warn(char *fnt, char *msg, ...)
int debug_warn(const char *fnt, char *msg, ...)
{
write_serial("\033[0;33m[WARNING]\033[0m ");
write_serial(fnt);
write_serial((char *) fnt);
write_serial("\t: ");
va_list args;
@ -70,10 +72,10 @@ int debug_warn(char *fnt, char *msg, ...)
return 0;
}
int debug_err(char *fnt, char *msg, ...)
int debug_err(const char *fnt, char *msg, ...)
{
write_serial("\033[0;31m[ERROR]\033[0m ");
write_serial(fnt);
write_serial((char *) fnt);
write_serial("\t: ");
va_list args;

View File

@ -15,8 +15,8 @@
#define DEBUG_ERR(...)
#endif
int debug_info(char *fnt, char *msg, ...);
int debug_warn(char *fnt, char *msg, ...);
int debug_err(char *fnt, char *msg, ...);
int debug_info(const char *fnt, char *msg, ...);
int debug_warn(const char *fnt, char *msg, ...);
int debug_err(const char *fnt, char *msg, ...);
#endif /* DEBUG_H */

View File

@ -4,6 +4,7 @@
#include "serial.h"
#include "debug.h"
#include "paging.h"
#include "tools.h"
int load_elf(char *elf_data_start, int uid)
{
@ -29,13 +30,15 @@ int load_elf(char *elf_data_start, int uid)
allocate_new_page(uid, mem << 12);
}
memcpy(elf_header_table->p_vaddr, elf_data_start + elf_header_table->p_offset, elf_header_table->p_filesz);
memcpy((void *) elf_header_table->p_vaddr, elf_data_start + elf_header_table->p_offset, elf_header_table->p_filesz);
if (elf_header_table->p_filesz < elf_header_table->p_memsz)
{
for (int i = elf_header_table->p_filesz; i < elf_header_table->p_memsz; i++)
for (u32 i = elf_header_table->p_filesz; i < elf_header_table->p_memsz; i++)
elf_header_table->p_vaddr[elf_data_start + elf_header_table->p_offset + i] = 0;
}
}
}
return 0;
}

View File

@ -48,4 +48,4 @@ enum elf_segment_type {
int load_elf(char *elf_data_start, int uid);
#endif ELF_H
#endif /* !ELF_H */

View File

@ -8,19 +8,6 @@
#include "tss.h"
#include "userland.h"
void *memcpy(void *dest, const void *src, size_t n)
{
const char *s = src;
char *d = dest;
for (size_t i = 0; i < n; i++)
{
*d++ = *s++;
}
return dest;
}
struct tss user_land_tss;
struct segment_desc_param {
@ -66,8 +53,9 @@ void init_gdt(void)
{
DEBUG_INFO("Initializing GDT");
u16 gdt_size = sizeof(gdt) / sizeof(struct segdesc);
DEBUG_INFO("GDT BASE ADDRESS: %d", (u32) &kgdtr);
DEBUG_INFO("GDT LIMIT: %d", sizeof(gdt) - 1);
DEBUG_INFO("GDT LIMIT: %d", gdt_size - 1);
kgdtr.limit = sizeof(gdt) - 1;
kgdtr.base = (u32) gdt;
@ -102,10 +90,10 @@ void init_gdt(void)
DEBUG_INFO("TSS BASE ADDRESS: %d", (u32) &user_land_tss);
gdt[5] = init_descriptor((struct segment_desc_param) { .Limit_1 = sizeof(user_land_tss),
.Base = &user_land_tss, .Type = 0x09, .S = 0, .DPL = 3, .P = 1,
.Base = (u32) &user_land_tss, .Type = 0x09, .S = 0, .DPL = 3, .P = 1,
.Limit_2 = 0x00, .AVL = 0, .L = 0, .D_B = 0, .G = 0 });
for (int i = 0; i < sizeof(gdt) / 8; i++)
for (size_t i = 0; i < gdt_size; i++)
{
char *ptr = (char *) &gdt[i];
DEBUG_INFO("--------------------");

View File

@ -46,6 +46,7 @@ struct idt_segdesc init_gate(struct interrupt_gate_param param)
descriptor.Type = param.Type | (param.D << 3);
descriptor.Flags = 0;
descriptor.Flags |= param.DPL << 1;
descriptor.Flags |= param.P << 3;
@ -56,12 +57,13 @@ void init_idt(void)
{
DEBUG_INFO("Initializing IDT");
u16 idt_size = sizeof(idt) / sizeof(struct idt_segdesc);
DEBUG_INFO("IDT BASE ADDRESS: %d", (u32) &kidtr);
DEBUG_INFO("IDT LIMIT: %d", sizeof(idt) - 1);
DEBUG_INFO("IDT LIMIT: %d", idt_size - 1);
kidtr.limit = sizeof(idt) - 1;
kidtr.base = (u32) idt;
for (int i = 0; i < sizeof(idt); i++)
for (size_t i = 0; i < idt_size; i++)
{
idt[i] = init_gate((struct interrupt_gate_param) { .Offset = (u32) _asm_default_int, .SegSelect = 0x08,
.Type = 0x06, .D = 1, .DPL = 0, .P = 1 });

View File

@ -18,9 +18,7 @@ void main(void)
{
DEBUG_INFO("Entering Main Function");
char *data_start = &_binary_a_out_start;
char *data_end = _binary_a_out_end;
size_t data_size = (size_t)_binary_a_out_size;
char *data_start = (char *) &_binary_a_out_start;
create_process(0, data_start);
switch_to_process(0);

View File

@ -3,7 +3,7 @@
#include "tss.h"
#include "debug.h"
void launch_process(u16 tss, int memory_start, int userland_stack, int userland_code, u16 userland_data)
void launch_process(u16 tss, int userland_stack, int userland_code, u16 userland_data)
{
// Setting DPL and GDT bits
userland_stack += 3;

View File

@ -3,6 +3,6 @@
#include <types.h>
void launch_process(u16 tss, int memory_start, int userland_stack, int userland_code, u16 userland_data);
void launch_process(u16 tss, int userland_stack, int userland_code, u16 userland_data);
#endif /* !LAUNCH_PROCESS_H */

View File

@ -124,7 +124,7 @@ int create_kernel_page(void)
DEBUG_INFO("PAGE_TABLE %d", &page_table[i * 1024]);
page_dir[i] = create_page_directory_entry((struct page_directory_param) {
.P = 1, .R_W = 1, .U = 0, .PWT = 0, .PCD = 0,
.A = 0, .PS = 0, .address = &page_table[i * 1024]});
.A = 0, .PS = 0, .address = (u32) &page_table[i * 1024]});
}
for (int i = NB_KERNEL_PAGE_DIR; i < 1024; i++)
@ -193,7 +193,7 @@ int create_new_userland_page(int uid)
DEBUG_INFO("PAGE_TABLE %d", &kernel_page_table[i * 1024]);
userland_page_dir[i] = create_page_directory_entry((struct page_directory_param) {
.P = 1, .R_W = 1, .U = 0, .PWT = 0, .PCD = 0,
.A = 0, .PS = 0, .address = &kernel_page_table[i * 1024]});
.A = 0, .PS = 0, .address = (u32) &kernel_page_table[i * 1024]});
}
for (int i = 0; i < 1024; i++)
@ -208,7 +208,7 @@ int create_new_userland_page(int uid)
userland_page_dir[NB_KERNEL_PAGE_DIR] = create_page_directory_entry((struct page_directory_param) {
.P = 1, .R_W = 1, .U = 0, .PWT = 0, .PCD = 0,
.A = 0, .PS = 0, .address = userland_data->userland_data[uid].page_table});
.A = 0, .PS = 0, .address = (u32) userland_data->userland_data[uid].page_table});
for (int i = NB_KERNEL_PAGE_DIR + 1; i < 1024; i++)
{
@ -216,6 +216,8 @@ int create_new_userland_page(int uid)
.P = 0, .R_W = 0, .U = 0, .PWT = 0, .PCD = 0,
.A = 0, .PS = 0, .address = 0});
}
return 0;
}
int allocate_new_page(int uid, int address)
@ -231,7 +233,7 @@ int allocate_new_page(int uid, int address)
// CPU does't use page table when decoding page table, so it need the physical address
int new_page_table_real = (int) userland_data->userland_data[uid].page_table[dir_address].address;
DEBUG_INFO("PAGE TABLE REAL ADDRESS %d", new_page_table_real << 12);
struct page_table_entry *new_page_table = USERLAND_BASE_ADDRESS + dir_address * 1024 * 4 + table_address * 4;
struct page_table_entry *new_page_table = (struct page_table_entry *) (USERLAND_BASE_ADDRESS + dir_address * 1024 * 4 + table_address * 4);
if (userland_page_dir[dir_address].address != 0 && new_page_table->address != 0)
clear_page(new_page_table->address);
@ -250,4 +252,6 @@ int allocate_new_page(int uid, int address)
.P = 1, .R_W = 1, .U = 1, .PWT = 0, .PCD = 0,
.A = 0, .D = 0, .PAT = 0, .G = 0,
.address = (avl_address >> 12)});
return 0;
}

View File

@ -17,6 +17,7 @@ struct page_table_entry {
} __attribute__((packed));
int create_kernel_page(void);
int create_new_userland_page(int uid);
int allocate_new_page(int uid, int address);
// extern struct page_directory_entry page_dir[1024];

View File

@ -20,6 +20,8 @@ int init_serial()
outb(PORT + 3, 0x03); // 8 bits, no parity, one stop bit
outb(PORT + 2, 0xC7); // Enable FIFO, clear them, with 14-byte threshold
outb(PORT + 4, 0x0B); // IRQs enabled, RTS/DSR set
return 0;
}
int write_serial_nb(int nb, int ln)
@ -86,7 +88,7 @@ int write_serial_char(char c)
int write_serial(char * s)
{
for (size_t i = 0; i < strlen(s); i++)
for (int i = 0; i < strlen(s); i++)
{
while ((inb(PORT + 5) & 0x20) == 0);
outb(PORT, s[i]);

14
src/tools.c Normal file
View File

@ -0,0 +1,14 @@
#include "tools.h"
void *memcpy(void *dest, const void *src, size_t n)
{
const char *s = src;
char *d = dest;
for (size_t i = 0; i < n; i++)
{
*d++ = *s++;
}
return dest;
}

8
src/tools.h Normal file
View File

@ -0,0 +1,8 @@
#ifndef TOOLS_H
#define TOOLS_H
#include <types.h>
void *memcpy(void *dest, const void *src, size_t n);
#endif /* !TOOLS_H */

View File

@ -2,9 +2,10 @@
#include "debug.h"
#include "paging.h"
#include "elf.h"
#include "launch_process.h"
struct userlands_data *userland_data = 0x3020000;
struct userlands_data *userland_data = (struct userlands_data *) 0x3020000;
int create_process(int uid, char *data_start)
{
@ -41,5 +42,7 @@ int switch_to_process(int uid)
mov %%eax, %%cr3" : "+r" (process_page_dir_adress));
// TODO : once data by process has been implemented, load the right one
launch_process(0x28, 0x6000000, 0x20, 0x18, 0x20);
launch_process(0x28, 0x20, 0x18, 0x20);
return 0;
}