use mutex instead of static mut spinlocks

This commit is contained in:
Garen Tyler 2023-10-30 19:51:08 -06:00
parent d46c341aaf
commit 6d9a0a34e1
Signed by: garentyler
GPG Key ID: D7A048C454CB7054
4 changed files with 29 additions and 38 deletions

View File

@ -2,8 +2,7 @@
#![allow(non_upper_case_globals)] #![allow(non_upper_case_globals)]
use crate::{ use crate::{
console::consoleintr, proc::wakeup, queue::Queue, sync::mutex::Mutex, console::consoleintr, proc::wakeup, queue::Queue, sync::mutex::Mutex, trap::InterruptBlocker,
trap::InterruptBlocker,
}; };
use core::ptr::addr_of; use core::ptr::addr_of;
@ -111,7 +110,7 @@ impl Uart {
pub fn write_byte(&self, b: u8) { pub fn write_byte(&self, b: u8) {
let _ = InterruptBlocker::new(); let _ = InterruptBlocker::new();
if unsafe { crate::PANICKED } { if *crate::PANICKED.lock_spinning() {
loop { loop {
core::hint::spin_loop(); core::hint::spin_loop();
} }
@ -134,7 +133,7 @@ impl Uart {
pub fn write_byte_buffered(&self, b: u8) { pub fn write_byte_buffered(&self, b: u8) {
let mut buf = self.buffer.lock_spinning(); let mut buf = self.buffer.lock_spinning();
if unsafe { crate::PANICKED } { if *crate::PANICKED.lock_spinning() {
loop { loop {
core::hint::spin_loop(); core::hint::spin_loop();
} }

View File

@ -21,13 +21,13 @@ pub mod sync;
pub mod syscall; pub mod syscall;
pub mod trap; pub mod trap;
use crate::proc::cpuid; use crate::{proc::cpuid, sync::mutex::Mutex};
use core::ffi::{c_char, CStr}; use core::ffi::{c_char, CStr};
pub(crate) use crate::console::printf::{print, println}; pub(crate) use crate::console::printf::{print, println};
pub static mut STARTED: bool = false; pub static mut STARTED: bool = false;
pub static mut PANICKED: bool = false; pub static PANICKED: Mutex<bool> = Mutex::new(false);
/// Maximum number of processes /// Maximum number of processes
pub const NPROC: usize = 64; pub const NPROC: usize = 64;
@ -65,7 +65,6 @@ pub unsafe extern "C" fn main() -> ! {
mem::virtual_memory::kvminit(); mem::virtual_memory::kvminit();
mem::virtual_memory::kvminithart(); mem::virtual_memory::kvminithart();
proc::procinit(); proc::procinit();
trap::trapinit();
trap::trapinithart(); trap::trapinithart();
riscv::plic::plicinit(); riscv::plic::plicinit();
riscv::plic::plicinithart(); riscv::plic::plicinithart();
@ -113,7 +112,7 @@ fn panic_wrapper(panic_info: &core::panic::PanicInfo) -> ! {
println!("╚═╝ ╚═════╝ ╚═════╝╚═╝ ╚═╝╚═╝╚═╝"); println!("╚═╝ ╚═════╝ ╚═════╝╚═╝ ╚═╝╚═╝╚═╝");
unsafe { unsafe {
crate::PANICKED = true; *crate::PANICKED.lock_spinning() = true;
// Quit QEMU for convenience. // Quit QEMU for convenience.
crate::syscall::Syscall::Shutdown.call(); crate::syscall::Syscall::Shutdown.call();
} }

View File

@ -1,15 +1,17 @@
use crate::{ use crate::{
mem::virtual_memory::{copyin, copyinstr},
println, println,
proc::{self, myproc, sleep_lock}, proc::{self, myproc},
riscv::{memlayout::QEMU_POWER, Pagetable}, riscv::memlayout::QEMU_POWER,
string::strlen, string::strlen,
trap::CLOCK_TICKS,
};
use core::{
mem::size_of,
ptr::{addr_of, addr_of_mut},
}; };
use core::{mem::size_of, ptr::addr_of_mut};
extern "C" { extern "C" {
fn copyin(pagetable: Pagetable, dst: *mut u8, srcva: u64, len: u64) -> i32;
fn copyinstr(pagetable: Pagetable, dst: *mut u8, srcva: u64, len: u64) -> i32;
// fn syscall();
fn sys_pipe() -> u64; fn sys_pipe() -> u64;
fn sys_read() -> u64; fn sys_read() -> u64;
fn sys_exec() -> u64; fn sys_exec() -> u64;
@ -87,26 +89,22 @@ impl Syscall {
} }
} }
Syscall::Sleep => { Syscall::Sleep => {
use crate::trap::{ticks, tickslock};
let mut n = 0i32; let mut n = 0i32;
argint(0, addr_of_mut!(n)); argint(0, addr_of_mut!(n));
let _guard = tickslock.lock(); let mut ticks = CLOCK_TICKS.lock_spinning();
while ticks < ticks + n as u32 {
while *ticks < *ticks + n as usize {
if proc::killed(myproc()) > 0 { if proc::killed(myproc()) > 0 {
tickslock.unlock();
return -1i64 as u64; return -1i64 as u64;
} }
sleep_lock(addr_of_mut!(ticks).cast(), addr_of_mut!(tickslock).cast()) // Sleep until the value changes.
ticks.sleep(addr_of!(CLOCK_TICKS).cast_mut().cast());
} }
0 0
} }
// Returns how many clock tick interrupts have occured since start. // Returns how many clock tick interrupts have occured since start.
Syscall::Uptime => { Syscall::Uptime => *CLOCK_TICKS.lock_spinning() as u64,
let _guard = crate::trap::tickslock.lock();
crate::trap::ticks as u64
}
Syscall::Open => sys_open(), Syscall::Open => sys_open(),
Syscall::Write => sys_write(), Syscall::Write => sys_write(),
Syscall::Mknod => sys_mknod(), Syscall::Mknod => sys_mknod(),

View File

@ -2,10 +2,10 @@ use crate::{
println, println,
proc::{cpuid, exit, killed, mycpu, myproc, r#yield, setkilled, wakeup, ProcState}, proc::{cpuid, exit, killed, mycpu, myproc, r#yield, setkilled, wakeup, ProcState},
riscv::*, riscv::*,
sync::spinlock::Spinlock, sync::mutex::Mutex,
syscall::syscall, syscall::syscall,
}; };
use core::ptr::{addr_of, addr_of_mut}; use core::ptr::addr_of;
extern "C" { extern "C" {
pub fn kernelvec(); pub fn kernelvec();
@ -19,15 +19,7 @@ extern "C" {
pub static mut userret: [u8; 0]; pub static mut userret: [u8; 0];
} }
#[no_mangle] pub static CLOCK_TICKS: Mutex<usize> = Mutex::new(0);
pub static mut tickslock: Spinlock = Spinlock::new();
#[no_mangle]
pub static mut ticks: u32 = 0;
#[no_mangle]
pub unsafe extern "C" fn trapinit() {
tickslock = Spinlock::new();
}
/// Set up to take exceptions and traps while in the kernel. /// Set up to take exceptions and traps while in the kernel.
#[no_mangle] #[no_mangle]
@ -37,9 +29,12 @@ pub unsafe extern "C" fn trapinithart() {
#[no_mangle] #[no_mangle]
pub unsafe extern "C" fn clockintr() { pub unsafe extern "C" fn clockintr() {
let _guard = tickslock.lock(); let mut ticks = CLOCK_TICKS.lock_spinning();
ticks += 1;
wakeup(addr_of_mut!(ticks).cast()); *ticks += 1;
unsafe {
wakeup(addr_of!(CLOCK_TICKS).cast_mut().cast());
}
} }
/// Check if it's an external interrupt or software interrupt and handle it. /// Check if it's an external interrupt or software interrupt and handle it.