mirror of
https://github.com/wichtounet/thor-os.git
synced 2025-09-16 07:57:13 -04:00
Fix race condition in wait_for_termination
If preempted, it was possible for a process to be waiting forever
This commit is contained in:
parent
1c3af14f35
commit
27dc7e25a0
@ -26,6 +26,7 @@
|
|||||||
#include "mutex.hpp"
|
#include "mutex.hpp"
|
||||||
#include "kernel_utils.hpp"
|
#include "kernel_utils.hpp"
|
||||||
#include "logging.hpp"
|
#include "logging.hpp"
|
||||||
|
#include "int_lock.hpp"
|
||||||
|
|
||||||
//Provided by task_switch.s
|
//Provided by task_switch.s
|
||||||
extern "C" {
|
extern "C" {
|
||||||
@ -690,23 +691,35 @@ void scheduler::sbrk(size_t inc){
|
|||||||
}
|
}
|
||||||
|
|
||||||
void scheduler::await_termination(pid_t pid){
|
void scheduler::await_termination(pid_t pid){
|
||||||
|
int_lock lock;
|
||||||
|
|
||||||
while(true){
|
while(true){
|
||||||
|
lock.acquire();
|
||||||
|
|
||||||
bool found = false;
|
bool found = false;
|
||||||
for(auto& process : pcb){
|
for(auto& process : pcb){
|
||||||
if(process.process.ppid == current_pid && process.process.pid == pid){
|
if(process.process.ppid == current_pid && process.process.pid == pid){
|
||||||
if(process.state == process_state::KILLED){
|
if(process.state == process_state::KILLED){
|
||||||
|
lock.release();
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
found = true;
|
found = true;
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// The process may have already been cleaned, we can simply return
|
||||||
if(!found){
|
if(!found){
|
||||||
|
lock.release();
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
logging::logf(logging::log_level::DEBUG, "Process %u waits for %u\n", current_pid, pid);
|
||||||
|
|
||||||
pcb[current_pid].state = process_state::WAITING;
|
pcb[current_pid].state = process_state::WAITING;
|
||||||
|
|
||||||
|
lock.release();
|
||||||
reschedule();
|
reschedule();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -726,6 +739,7 @@ void scheduler::kill_current_process(){
|
|||||||
unblock_process(gc_pid);
|
unblock_process(gc_pid);
|
||||||
|
|
||||||
pcb[current_pid].state = scheduler::process_state::KILLED;
|
pcb[current_pid].state = scheduler::process_state::KILLED;
|
||||||
|
logging::logf(logging::log_level::DEBUG, "Found%u\n", static_cast<uint8_t>(pcb[current_pid].state));
|
||||||
|
|
||||||
//Run another process
|
//Run another process
|
||||||
reschedule();
|
reschedule();
|
||||||
|
Loading…
x
Reference in New Issue
Block a user