Skip to content

Commit

Permalink
[rust] resolve deadlock on multiple Stdin/Stdout references
Browse files Browse the repository at this point in the history
Use &'static Mutex type other than MutexGuard for Stdin/Stdout inner field

Signed-off-by: Zhouqi Jiang <luojia@hust.edu.cn>
  • Loading branch information
luojia65 committed Oct 5, 2024
1 parent ab68370 commit 8170d62
Show file tree
Hide file tree
Showing 2 changed files with 12 additions and 13 deletions.
4 changes: 2 additions & 2 deletions board/100ask-d1-h-rs/src/main.rs
Original file line number Diff line number Diff line change
Expand Up @@ -63,8 +63,8 @@ fn main(p: Peripherals, _c: Clocks) {
}
}

fn command_bootargs<'a>(cli: &mut CliHandle<'a, Stdout, Infallible>) {
ufmt::uwrite!(cli.writer(), "TODO Bootargs").ok();
fn command_bootargs<'a>(_cli: &mut CliHandle<'a, Stdout, Infallible>) {
println!("TODO Bootargs");
}

fn command_reload<'a>(cli: &mut CliHandle<'a, Stdout, Infallible>) {
Expand Down
21 changes: 10 additions & 11 deletions rust/src/stdio.rs
Original file line number Diff line number Diff line change
Expand Up @@ -36,7 +36,7 @@ pub fn _print(args: core::fmt::Arguments) {

/// A handle to the global standard output stream of the current runtime.
pub struct Stdout {
inner: spin::MutexGuard<'static, Option<SyterKitStdoutInner>>,
inner: &'static spin::Mutex<Option<SyterKitStdoutInner>>,
}

impl embedded_io::ErrorType for Stdout {
Expand All @@ -46,14 +46,16 @@ impl embedded_io::ErrorType for Stdout {
impl embedded_io::Write for Stdout {
#[inline]
fn write(&mut self, buf: &[u8]) -> Result<usize, Self::Error> {
if let Some(stdout) = &mut *self.inner {
let mut lock = self.inner.lock();
if let Some(stdout) = &mut *lock {
stdout.inner.write_all(buf).ok();
}
Ok(buf.len())
}
#[inline]
fn flush(&mut self) -> Result<(), Self::Error> {
if let Some(stdout) = &mut *self.inner {
let mut lock = self.inner.lock();
if let Some(stdout) = &mut *lock {
stdout.inner.flush().ok();
}
Ok(())
Expand All @@ -62,7 +64,7 @@ impl embedded_io::Write for Stdout {

/// A handle to the standard input stream of a runtime.
pub struct Stdin {
inner: spin::MutexGuard<'static, Option<SyterKitStdinInner>>,
inner: &'static spin::Mutex<Option<SyterKitStdinInner>>,
}

impl embedded_io::ErrorType for Stdin {
Expand All @@ -72,7 +74,8 @@ impl embedded_io::ErrorType for Stdin {
impl embedded_io::Read for Stdin {
#[inline]
fn read(&mut self, buf: &mut [u8]) -> Result<usize, Self::Error> {
if let Some(stdin) = &mut *self.inner {
let mut lock = self.inner.lock();
if let Some(stdin) = &mut *lock {
stdin.inner.read(buf).ok();
}
Ok(buf.len())
Expand All @@ -82,15 +85,11 @@ impl embedded_io::Read for Stdin {
/// Constructs a new handle to the standard output of the current environment.
#[inline]
pub fn stdout() -> Stdout {
Stdout {
inner: STDOUT.lock(),
}
Stdout { inner: &STDOUT }
}

/// Constructs a new handle to the standard input of the current environment.
#[inline]
pub fn stdin() -> Stdin {
Stdin {
inner: STDIN.lock(),
}
Stdin { inner: &STDIN }
}

0 comments on commit 8170d62

Please sign in to comment.