From c16b3e39cf8b0a6ea5e43812bc4187bf7867343d Mon Sep 17 00:00:00 2001 From: Baptiste Wicht Date: Tue, 28 Jan 2014 20:48:31 +0100 Subject: [PATCH] Handle state of processes --- kernel/include/process.hpp | 9 +++++++++ kernel/src/scheduler.cpp | 22 +++++++++++++++++----- 2 files changed, 26 insertions(+), 5 deletions(-) diff --git a/kernel/include/process.hpp b/kernel/include/process.hpp index 945e8af0..a1d0d52d 100644 --- a/kernel/include/process.hpp +++ b/kernel/include/process.hpp @@ -16,6 +16,13 @@ namespace scheduler { +enum class process_state : char { + NEW = 0, + READY = 1, + RUNNING = 2, + BLOCKED = 3 +}; + struct segment_t { size_t physical; size_t size; @@ -24,6 +31,8 @@ struct segment_t { struct process_t { size_t pid; + process_state state; + bool system; size_t physical_cr3; diff --git a/kernel/src/scheduler.cpp b/kernel/src/scheduler.cpp index 4eb68983..10046c61 100644 --- a/kernel/src/scheduler.cpp +++ b/kernel/src/scheduler.cpp @@ -36,8 +36,7 @@ size_t idle_stack[64]; size_t idle_kernel_stack[4096]; //TODO Perhaps not good void create_idle_task(){ - scheduler::process_t idle_process; - idle_process.pid = next_pid++; + auto idle_process = scheduler::new_process(); idle_process.system = true; idle_process.physical_cr3 = paging::get_physical_pml4t(); idle_process.paging_size = 0; @@ -53,8 +52,7 @@ void create_idle_task(){ 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); + queue_process(std::move(idle_process)); } void switch_to_process(const interrupt::syscall_regs& regs, size_t index){ @@ -64,6 +62,8 @@ void switch_to_process(const interrupt::syscall_regs& regs, size_t index){ auto& process = processes[current_index]; + process.state = scheduler::process_state::RUNNING; + gdt::tss.rsp0_low = process.kernel_rsp & 0xFFFFFFFF; gdt::tss.rsp0_high = process.kernel_rsp >> 32; @@ -103,7 +103,13 @@ void switch_to_process(const interrupt::syscall_regs& regs, size_t index){ } size_t select_next_process(){ - return (current_index + 1) % processes.size(); + auto next = (current_index + 1) % processes.size(); + + while(processes[next].state != scheduler::process_state::READY){ + next = (next + 1) % processes.size(); + } + + return next; } void save_context(const interrupt::syscall_regs& regs){ @@ -126,6 +132,7 @@ void scheduler::start(){ current_index = 0; rounds[current_index] = TURNOVER; + processes[current_index].state = process_state::RUNNING; //Wait for the next interrupt while(true){ @@ -157,6 +164,8 @@ void scheduler::reschedule(const interrupt::syscall_regs& regs){ if(rounds[current_index] == TURNOVER){ rounds[current_index] = 0; + processes[current_index].state = process_state::READY; + auto index = select_next_process(); //If it is the same, no need to go to the switching process @@ -179,6 +188,7 @@ scheduler::process_t scheduler::new_process(){ p.system = false; p.pid = next_pid++; + p.state = process_state::NEW; return std::move(p); } @@ -186,4 +196,6 @@ scheduler::process_t scheduler::new_process(){ void scheduler::queue_process(process_t&& p){ processes.push_back(std::forward(p)); rounds.push_back(0); + + p.state = process_state::READY; }