mirror of
https://github.com/wichtounet/thor-os.git
synced 2025-09-17 08:37:17 -04:00
Merge branch 'develop' of github.com:wichtounet/thor-os into develop
Conflicts: cpp.mk
This commit is contained in:
commit
3fb29dab1c
10
Makefile
10
Makefile
@ -20,6 +20,12 @@ programs/hello/a.out: force_look
|
||||
programs/long/a.out: force_look
|
||||
cd programs/long; ${MAKE} a.out
|
||||
|
||||
programs/longone/a.out: force_look
|
||||
cd programs/longone; ${MAKE} a.out
|
||||
|
||||
programs/longtwo/a.out: force_look
|
||||
cd programs/longtwo; ${MAKE} a.out
|
||||
|
||||
programs/loop/a.out: force_look
|
||||
cd programs/loop; ${MAKE} a.out
|
||||
|
||||
@ -27,7 +33,7 @@ hdd.img:
|
||||
dd if=/dev/zero of=hdd.img bs=516096c count=1000
|
||||
(echo n; echo p; echo 1; echo ""; echo ""; echo t; echo c; echo a; echo 1; echo w;) | sudo fdisk -u -C1000 -S63 -H16 hdd.img
|
||||
|
||||
thor.flp: hdd.img bootloader/stage1.bin bootloader/stage2.bin kernel/kernel.bin programs/one/a.out programs/hello/a.out programs/long/a.out programs/loop/a.out
|
||||
thor.flp: hdd.img bootloader/stage1.bin bootloader/stage2.bin kernel/kernel.bin programs/one/a.out programs/hello/a.out programs/long/a.out programs/loop/a.out programs/longone/a.out programs/longtwo/a.out
|
||||
mkdir -p mnt/fake/
|
||||
dd if=bootloader/stage1.bin of=hdd.img conv=notrunc
|
||||
dd if=bootloader/stage2.bin of=hdd.img seek=1 conv=notrunc
|
||||
@ -38,6 +44,8 @@ thor.flp: hdd.img bootloader/stage1.bin bootloader/stage2.bin kernel/kernel.bin
|
||||
sudo /bin/cp programs/one/a.out mnt/fake/one
|
||||
sudo /bin/cp programs/hello/a.out mnt/fake/hello
|
||||
sudo /bin/cp programs/long/a.out mnt/fake/long
|
||||
sudo /bin/cp programs/longone/a.out mnt/fake/longone
|
||||
sudo /bin/cp programs/longtwo/a.out mnt/fake/longtwo
|
||||
sudo /bin/cp programs/loop/a.out mnt/fake/loop
|
||||
sleep 0.1
|
||||
sudo /bin/umount mnt/fake/
|
||||
|
2
cpp.mk
2
cpp.mk
@ -12,6 +12,6 @@ CPP_FLAGS_32=$(COMMON_CPP_FLAGS) $(CPP_FLAGS_LOW) -mpreferred-stack-boundary=4
|
||||
CPP_FLAGS_64=$(COMMON_CPP_FLAGS) -mno-sse3 -mno-sse4 -mno-sse4.1 -mno-sse4.2
|
||||
|
||||
COMMON_LINK_FLAGS=-lgcc
|
||||
PROGRAM_LINK_FLAGS=-z max-page-size=0x1000 $(COMMON_LINK_FLAGS) -T ../linker.ld
|
||||
PROGRAM_LINK_FLAGS=$(COMMON_LINK_FLAGS) -z max-page-size=0x1000 -T ../linker.ld
|
||||
|
||||
PROGRAM_FLAGS=-I../../userlib/include/
|
||||
|
@ -12,6 +12,7 @@
|
||||
#include "stl/vector.hpp"
|
||||
|
||||
#include "paging.hpp"
|
||||
#include "interrupts.hpp"
|
||||
|
||||
namespace scheduler {
|
||||
|
||||
@ -25,19 +26,16 @@ struct process_t {
|
||||
|
||||
bool system;
|
||||
|
||||
size_t code_selector;
|
||||
size_t data_selector;
|
||||
|
||||
size_t physical_cr3;
|
||||
size_t paging_size;
|
||||
|
||||
size_t physical_user_stack;
|
||||
size_t physical_kernel_stack;
|
||||
|
||||
size_t rip;
|
||||
size_t user_rsp;
|
||||
size_t kernel_rsp;
|
||||
|
||||
interrupt::syscall_regs regs;
|
||||
|
||||
std::vector<segment_t> segments;
|
||||
std::vector<size_t> physical_paging;
|
||||
};
|
||||
|
@ -16,7 +16,7 @@ namespace scheduler {
|
||||
void init();
|
||||
void start();
|
||||
|
||||
void kill_current_process();
|
||||
void kill_current_process(const interrupt::syscall_regs& regs);
|
||||
|
||||
void reschedule(const interrupt::syscall_regs& regs);
|
||||
|
||||
|
@ -200,15 +200,25 @@ void init_head(){
|
||||
malloc_head->prev_ref() = malloc_head;
|
||||
}
|
||||
|
||||
void expand_heap(malloc_header_chunk* current){
|
||||
void expand_heap(malloc_header_chunk* current, size_t bytes = 0){
|
||||
auto blocks = MIN_BLOCKS;
|
||||
|
||||
if(bytes){
|
||||
auto necessary_blocks = ((bytes + META_SIZE) / BLOCK_SIZE) + 1;
|
||||
|
||||
if(necessary_blocks > blocks){
|
||||
blocks = necessary_blocks;
|
||||
}
|
||||
}
|
||||
|
||||
//Allocate a new block of memory
|
||||
uint64_t* block = allocate_block(MIN_BLOCKS);
|
||||
uint64_t* block = allocate_block(blocks);
|
||||
|
||||
//Transform it into a malloc chunk
|
||||
auto header = reinterpret_cast<malloc_header_chunk*>(block);
|
||||
|
||||
//Update the sizes
|
||||
header->size() = MIN_BLOCKS * BLOCK_SIZE - META_SIZE;
|
||||
header->size() = blocks * BLOCK_SIZE - META_SIZE;
|
||||
header->footer()->size() = header->size();
|
||||
|
||||
//Insert the new block into the free list
|
||||
@ -301,7 +311,7 @@ void* malloc::k_malloc(uint64_t bytes){
|
||||
if(current == malloc_head){
|
||||
//There are no blocks big enough to hold this request
|
||||
//So expand the heap
|
||||
expand_heap(current);
|
||||
expand_heap(current, bytes);
|
||||
} else if(current->size() >= bytes){
|
||||
//This block is big enough
|
||||
|
||||
|
@ -45,19 +45,19 @@ void create_idle_task(){
|
||||
idle_process.physical_user_stack = 0;
|
||||
idle_process.physical_kernel_stack = 0;
|
||||
|
||||
idle_process.rip = reinterpret_cast<size_t>(&idle_task);
|
||||
idle_process.user_rsp = reinterpret_cast<size_t>(&idle_stack[63]);
|
||||
idle_process.regs.rflags = 0x200;
|
||||
idle_process.regs.rip = reinterpret_cast<size_t>(&idle_task);
|
||||
idle_process.regs.rsp = reinterpret_cast<size_t>(&idle_stack[63]);
|
||||
idle_process.kernel_rsp = reinterpret_cast<size_t>(&idle_kernel_stack[4095]);
|
||||
|
||||
idle_process.code_selector = gdt::LONG_SELECTOR;
|
||||
idle_process.data_selector = gdt::DATA_SELECTOR;
|
||||
idle_process.regs.cs = gdt::LONG_SELECTOR;
|
||||
idle_process.regs.ds = gdt::DATA_SELECTOR;
|
||||
|
||||
processes.push_back(std::move(idle_process));
|
||||
rounds.push_back(0);
|
||||
}
|
||||
|
||||
void switch_to_process(size_t index) __attribute__((noreturn));
|
||||
void switch_to_process(size_t index){
|
||||
void switch_to_process(const interrupt::syscall_regs& regs, size_t index){
|
||||
current_index = index;
|
||||
|
||||
k_printf("Switched to %u\n", index);
|
||||
@ -67,7 +67,29 @@ void switch_to_process(size_t index){
|
||||
gdt::tss.rsp0_low = process.kernel_rsp & 0xFFFFFFFF;
|
||||
gdt::tss.rsp0_high = process.kernel_rsp >> 32;
|
||||
|
||||
asm volatile("mov rax, %0; mov ds, ax; mov es, ax; mov fs, ax; mov gs, ax;"
|
||||
auto stack_pointer = reinterpret_cast<uint64_t*>(regs.placeholder);
|
||||
|
||||
*(stack_pointer + 4) = process.regs.ds;
|
||||
*(stack_pointer + 3) = process.regs.rsp;
|
||||
*(stack_pointer + 2) = process.regs.rflags;
|
||||
*(stack_pointer + 1) = process.regs.cs;
|
||||
*(stack_pointer + 0) = process.regs.rip;
|
||||
*(stack_pointer - 3) = process.regs.r12;
|
||||
*(stack_pointer - 4) = process.regs.r11;
|
||||
*(stack_pointer - 5) = process.regs.r10;
|
||||
*(stack_pointer - 6) = process.regs.r9;
|
||||
*(stack_pointer - 7) = process.regs.r8;
|
||||
*(stack_pointer - 8) = process.regs.rdi;
|
||||
*(stack_pointer - 9) = process.regs.rsi;
|
||||
*(stack_pointer - 10) = process.regs.rdx;
|
||||
*(stack_pointer - 11) = process.regs.rcx;
|
||||
*(stack_pointer - 12) = process.regs.rbx;
|
||||
*(stack_pointer - 13) = process.regs.rax;
|
||||
*(stack_pointer - 14) = process.regs.ds;
|
||||
|
||||
asm volatile("mov cr3, %0" : : "r" (process.physical_cr3) : "memory");
|
||||
|
||||
/*asm volatile("mov rax, %0; mov ds, ax; mov es, ax; mov fs, ax; mov gs, ax;"
|
||||
: //No outputs
|
||||
: "r" (process.data_selector)
|
||||
: "rax");
|
||||
@ -77,9 +99,7 @@ void switch_to_process(size_t index){
|
||||
asm volatile("push %0; push %1; pushfq; pop rax; or rax, 0x200; push rax; push %2; push %3; iretq"
|
||||
: //No outputs
|
||||
: "r" (process.data_selector), "r" (process.user_rsp), "r" (process.code_selector), "r" (process.rip)
|
||||
: "rax", "memory");
|
||||
|
||||
__builtin_unreachable();
|
||||
: "rax", "memory");*/
|
||||
}
|
||||
|
||||
size_t select_next_process(){
|
||||
@ -89,8 +109,7 @@ size_t select_next_process(){
|
||||
void save_context(const interrupt::syscall_regs& regs){
|
||||
auto& process = processes[current_index];
|
||||
|
||||
process.user_rsp = regs.rsp;
|
||||
process.rip = regs.rip;
|
||||
process.regs = regs;
|
||||
}
|
||||
|
||||
} //end of anonymous namespace
|
||||
@ -105,10 +124,16 @@ void scheduler::start(){
|
||||
|
||||
started = true;
|
||||
|
||||
switch_to_process(processes.size() - 1);
|
||||
current_index = 0;
|
||||
rounds[current_index] = TURNOVER;
|
||||
|
||||
//Wait for the next interrupt
|
||||
while(true){
|
||||
asm volatile ("nop; nop; nop; nop");
|
||||
}
|
||||
}
|
||||
|
||||
void scheduler::kill_current_process(){
|
||||
void scheduler::kill_current_process(const interrupt::syscall_regs& regs){
|
||||
k_printf("Kill %u\n", current_index);
|
||||
|
||||
processes.erase(current_index);
|
||||
@ -121,7 +146,7 @@ void scheduler::kill_current_process(){
|
||||
|
||||
//Select the next process and switch to it
|
||||
auto index = select_next_process();
|
||||
switch_to_process(index);
|
||||
switch_to_process(regs, index);
|
||||
}
|
||||
|
||||
void scheduler::reschedule(const interrupt::syscall_regs& regs){
|
||||
@ -141,7 +166,7 @@ void scheduler::reschedule(const interrupt::syscall_regs& regs){
|
||||
|
||||
save_context(regs);
|
||||
|
||||
switch_to_process(index);
|
||||
switch_to_process(regs, index);
|
||||
} else {
|
||||
++rounds[current_index];
|
||||
}
|
||||
|
@ -809,7 +809,7 @@ bool create_paging(char* buffer, scheduler::process_t& process){
|
||||
|
||||
//2.1 Allocate user stack
|
||||
allocate_user_memory(process, scheduler::user_stack_start, scheduler::user_stack_size, process.physical_user_stack);
|
||||
process.user_rsp = scheduler::user_rsp;
|
||||
process.regs.rsp = scheduler::user_rsp;
|
||||
|
||||
//2.2 Allocate all user segments
|
||||
|
||||
@ -865,22 +865,8 @@ bool create_paging(char* buffer, scheduler::process_t& process){
|
||||
return true;
|
||||
}
|
||||
|
||||
void exec_command(const std::vector<std::string>& params){
|
||||
if(params.size() < 2){
|
||||
k_print_line("exec: Need the name of the executable to read");
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
if(!disks::mounted_partition() || !disks::mounted_disk()){
|
||||
k_print_line("Nothing is mounted");
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
scheduler::init();
|
||||
|
||||
auto content = read_elf_file(params[1], "exec");
|
||||
void queue_process(const std::string& file){
|
||||
auto content = read_elf_file(file, "exec");
|
||||
|
||||
if(!content){
|
||||
return;
|
||||
@ -896,12 +882,34 @@ void exec_command(const std::vector<std::string>& params){
|
||||
return;
|
||||
}
|
||||
|
||||
process.rip = header->e_entry;
|
||||
process.regs.rip = header->e_entry;
|
||||
|
||||
process.code_selector = gdt::USER_CODE_SELECTOR + 3;
|
||||
process.data_selector = gdt::USER_DATA_SELECTOR + 3;
|
||||
process.regs.cs = gdt::USER_CODE_SELECTOR + 3;
|
||||
process.regs.ds = gdt::USER_DATA_SELECTOR + 3;
|
||||
|
||||
process.regs.rflags = 0x200;
|
||||
|
||||
scheduler::queue_process(std::move(process));
|
||||
}
|
||||
|
||||
void exec_command(const std::vector<std::string>& params){
|
||||
if(params.size() < 2){
|
||||
k_print_line("exec: Need the name of the executable to read");
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
if(!disks::mounted_partition() || !disks::mounted_disk()){
|
||||
k_print_line("Nothing is mounted");
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
scheduler::init();
|
||||
|
||||
for(size_t i = 1; i < params.size(); ++i){
|
||||
queue_process(params[i]);
|
||||
}
|
||||
|
||||
scheduler::start();
|
||||
}
|
||||
|
@ -42,7 +42,7 @@ void system_call_entry(const interrupt::syscall_regs& regs){
|
||||
break;
|
||||
|
||||
case 0x666:
|
||||
scheduler::kill_current_process();
|
||||
scheduler::kill_current_process(regs);
|
||||
break;
|
||||
|
||||
default:
|
||||
|
15
programs/longone/Makefile
Normal file
15
programs/longone/Makefile
Normal file
@ -0,0 +1,15 @@
|
||||
.PHONY: default clean
|
||||
|
||||
default: a.out
|
||||
|
||||
include ../../cpp.mk
|
||||
|
||||
%.cpp.o: src/%.cpp
|
||||
$(CC) $(PROGRAM_FLAGS) $(CPP_FLAGS_64) $(WARNING_FLAGS) -c $< -o $@
|
||||
|
||||
a.out: main.cpp.o
|
||||
$(CC) $(PROGRAM_LINK_FLAGS) $(CPP_FLAGS_64) -o a.out main.cpp.o
|
||||
|
||||
clean:
|
||||
rm *.cpp.o
|
||||
rm -rf a.out
|
30
programs/longone/src/main.cpp
Normal file
30
programs/longone/src/main.cpp
Normal file
@ -0,0 +1,30 @@
|
||||
//=======================================================================
|
||||
// Copyright Baptiste Wicht 2013-2014.
|
||||
// Distributed under the Boost Software License, Version 1.0.
|
||||
// (See accompanying file LICENSE_1_0.txt or copy at
|
||||
// http://www.boost.org/LICENSE_1_0.txt)
|
||||
//=======================================================================
|
||||
|
||||
#include <print.hpp>
|
||||
#include <system.hpp>
|
||||
|
||||
volatile uint64_t current = 45;
|
||||
|
||||
uint64_t fibonacci_slow(uint64_t s){
|
||||
if(s == 1 || s == 2){
|
||||
return current;
|
||||
}
|
||||
|
||||
return fibonacci_slow(s - 1) + fibonacci_slow(s - 2);
|
||||
}
|
||||
|
||||
auto message = "I'm one";
|
||||
|
||||
int main(){
|
||||
while(true){
|
||||
fibonacci_slow(current);
|
||||
print_line(message);
|
||||
}
|
||||
|
||||
exit(0);
|
||||
}
|
15
programs/longtwo/Makefile
Normal file
15
programs/longtwo/Makefile
Normal file
@ -0,0 +1,15 @@
|
||||
.PHONY: default clean
|
||||
|
||||
default: a.out
|
||||
|
||||
include ../../cpp.mk
|
||||
|
||||
%.cpp.o: src/%.cpp
|
||||
$(CC) $(PROGRAM_FLAGS) $(CPP_FLAGS_64) $(WARNING_FLAGS) -c $< -o $@
|
||||
|
||||
a.out: main.cpp.o
|
||||
$(CC) $(PROGRAM_LINK_FLAGS) $(CPP_FLAGS_64) -o a.out main.cpp.o
|
||||
|
||||
clean:
|
||||
rm *.cpp.o
|
||||
rm -rf a.out
|
30
programs/longtwo/src/main.cpp
Normal file
30
programs/longtwo/src/main.cpp
Normal file
@ -0,0 +1,30 @@
|
||||
//=======================================================================
|
||||
// Copyright Baptiste Wicht 2013-2014.
|
||||
// Distributed under the Boost Software License, Version 1.0.
|
||||
// (See accompanying file LICENSE_1_0.txt or copy at
|
||||
// http://www.boost.org/LICENSE_1_0.txt)
|
||||
//=======================================================================
|
||||
|
||||
#include <print.hpp>
|
||||
#include <system.hpp>
|
||||
|
||||
volatile uint64_t current = 45;
|
||||
|
||||
uint64_t fibonacci_slow(uint64_t s){
|
||||
if(s == 1 || s == 2){
|
||||
return current;
|
||||
}
|
||||
|
||||
return fibonacci_slow(s - 1) + fibonacci_slow(s - 2);
|
||||
}
|
||||
|
||||
auto message = "I'm two";
|
||||
|
||||
int main(){
|
||||
while(true){
|
||||
fibonacci_slow(current);
|
||||
print_line(message);
|
||||
}
|
||||
|
||||
exit(0);
|
||||
}
|
Loading…
x
Reference in New Issue
Block a user