Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[feat] replace deprecated sbi_rt legacy console operations in riscv #195

Merged
merged 6 commits into from
Oct 29, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
10 changes: 8 additions & 2 deletions api/arceos_api/src/imp/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -19,8 +19,14 @@ cfg_display! {
mod stdio {
use core::fmt;

pub fn ax_console_read_byte() -> Option<u8> {
axhal::console::getchar().map(|c| if c == b'\r' { b'\n' } else { c })
pub fn ax_console_read_bytes(buf: &mut [u8]) -> crate::AxResult<usize> {
let len = axhal::console::read_bytes(buf);
for c in &mut buf[..len] {
if *c == b'\r' {
*c = b'\n';
}
}
Ok(len)
}

pub fn ax_console_write_bytes(buf: &[u8]) -> crate::AxResult<usize> {
Expand Down
4 changes: 2 additions & 2 deletions api/arceos_api/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -106,8 +106,8 @@ pub mod mem {
pub mod stdio {
use core::fmt;
define_api! {
/// Reads a byte from the console, or returns [`None`] if no input is available.
pub fn ax_console_read_byte() -> Option<u8>;
/// Reads a slice of bytes from the console, returns the number of bytes written.
pub fn ax_console_read_bytes(buf: &mut [u8]) -> crate::AxResult<usize>;
/// Writes a slice of bytes to the console, returns the number of bytes written.
pub fn ax_console_write_bytes(buf: &[u8]) -> crate::AxResult<usize>;
/// Writes a formatted string to the console.
Expand Down
17 changes: 11 additions & 6 deletions api/arceos_posix_api/src/imp/stdio.rs
Original file line number Diff line number Diff line change
Expand Up @@ -5,8 +5,14 @@ use axsync::Mutex;
#[cfg(feature = "fd")]
use {alloc::sync::Arc, axerrno::LinuxError, axerrno::LinuxResult, axio::PollState};

fn console_read_bytes() -> Option<u8> {
axhal::console::getchar().map(|c| if c == b'\r' { b'\n' } else { c })
fn console_read_bytes(buf: &mut [u8]) -> AxResult<usize> {
let len = axhal::console::read_bytes(buf);
for c in &mut buf[..len] {
if *c == b'\r' {
*c = b'\n';
}
}
Ok(len)
}

fn console_write_bytes(buf: &[u8]) -> AxResult<usize> {
Expand All @@ -22,12 +28,11 @@ impl Read for StdinRaw {
fn read(&mut self, buf: &mut [u8]) -> AxResult<usize> {
let mut read_len = 0;
while read_len < buf.len() {
if let Some(c) = console_read_bytes() {
buf[read_len] = c;
read_len += 1;
} else {
let len = console_read_bytes(buf[read_len..].as_mut())?;
if len == 0 {
break;
}
read_len += len;
}
Ok(read_len)
}
Expand Down
7 changes: 0 additions & 7 deletions modules/axhal/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -60,13 +60,6 @@ pub mod paging;
/// Console input and output.
pub mod console {
pub use super::platform::console::*;

/// Write a slice of bytes to the console.
pub fn write_bytes(bytes: &[u8]) {
for c in bytes {
putchar(*c);
}
}
}

/// Miscellaneous operation, e.g. terminate the system.
Expand Down
24 changes: 23 additions & 1 deletion modules/axhal/src/platform/aarch64_bsta1000b/dw_apb_uart.rs
Original file line number Diff line number Diff line change
Expand Up @@ -22,10 +22,32 @@ pub fn putchar(c: u8) {
}

/// Reads a byte from the console, or returns [`None`] if no input is available.
pub fn getchar() -> Option<u8> {
fn getchar() -> Option<u8> {
UART.lock().getchar()
}

/// Write a slice of bytes to the console.
pub fn write_bytes(bytes: &[u8]) {
equation314 marked this conversation as resolved.
Show resolved Hide resolved
for c in bytes {
putchar(*c);
}
}

/// Reads bytes from the console into the given mutable slice.
/// Returns the number of bytes read.
pub fn read_bytes(bytes: &mut [u8]) -> usize {
let mut read_len = 0;
while read_len < bytes.len() {
if let Some(c) = getchar() {
bytes[read_len] = c;
} else {
break;
}
read_len += 1;
}
read_len
}

/// UART simply initialize
pub fn init_early() {
UART.lock().init();
Expand Down
24 changes: 23 additions & 1 deletion modules/axhal/src/platform/aarch64_common/pl011.rs
Original file line number Diff line number Diff line change
Expand Up @@ -24,10 +24,32 @@ pub fn putchar(c: u8) {
}

/// Reads a byte from the console, or returns [`None`] if no input is available.
pub fn getchar() -> Option<u8> {
fn getchar() -> Option<u8> {
UART.lock().getchar()
}

/// Write a slice of bytes to the console.
pub fn write_bytes(bytes: &[u8]) {
for c in bytes {
putchar(*c);
}
}

/// Reads bytes from the console into the given mutable slice.
/// Returns the number of bytes read.
pub fn read_bytes(bytes: &mut [u8]) -> usize {
let mut read_len = 0;
while read_len < bytes.len() {
if let Some(c) = getchar() {
bytes[read_len] = c;
} else {
break;
}
read_len += 1;
}
read_len
}

/// Initialize the UART
pub fn init_early() {
UART.lock().init();
Expand Down
9 changes: 5 additions & 4 deletions modules/axhal/src/platform/dummy/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -2,13 +2,14 @@
#![allow(dead_code)]

pub mod console {
/// Writes a byte to the console.
pub fn putchar(c: u8) {
/// Writes bytes to the console from input u8 slice.
equation314 marked this conversation as resolved.
Show resolved Hide resolved
pub fn write_bytes(_bytes: &[u8]) {
unimplemented!()
}

/// Reads a byte from the console, or returns [`None`] if no input is available.
pub fn getchar() -> Option<u8> {
/// Reads bytes from the console into the given mutable slice.
/// Returns the number of bytes read.
pub fn read_bytes(_bytes: &mut [u8]) -> usize {
unimplemented!()
}
}
Expand Down
49 changes: 41 additions & 8 deletions modules/axhal/src/platform/riscv64_qemu_virt/console.rs
Original file line number Diff line number Diff line change
@@ -1,14 +1,47 @@
use memory_addr::VirtAddr;

use crate::mem::virt_to_phys;

/// The maximum number of bytes that can be read at once.
const MAX_RW_SIZE: usize = 256;

/// Writes a byte to the console.
pub fn putchar(c: u8) {
#[allow(deprecated)]
sbi_rt::legacy::console_putchar(c as usize);
sbi_rt::console_write_byte(c);
}

/// Reads a byte from the console, or returns [`None`] if no input is available.
pub fn getchar() -> Option<u8> {
#[allow(deprecated)]
match sbi_rt::legacy::console_getchar() as isize {
-1 => None,
c => Some(c as u8),
/// Tries to write bytes to the console from input u8 slice.
/// Returns the number of bytes written.
fn try_write_bytes(bytes: &[u8]) -> usize {
sbi_rt::console_write(sbi_rt::Physical::new(
// A maximum of 256 bytes can be written at a time
// to prevent SBI from disabling IRQs for too long.
bytes.len().min(MAX_RW_SIZE),
virt_to_phys(VirtAddr::from_ptr_of(bytes.as_ptr())).as_usize(),
0,
))
.value
}

/// Writes bytes to the console from input u8 slice.
pub fn write_bytes(bytes: &[u8]) {
let mut write_len = 0;
while write_len < bytes.len() {
let len = try_write_bytes(&bytes[write_len..]);
if len == 0 {
break;
}
write_len += len;
}
}

/// Reads bytes from the console into the given mutable slice.
/// Returns the number of bytes read.
pub fn read_bytes(bytes: &mut [u8]) -> usize {
sbi_rt::console_read(sbi_rt::Physical::new(
equation314 marked this conversation as resolved.
Show resolved Hide resolved
bytes.len().min(MAX_RW_SIZE),
virt_to_phys(VirtAddr::from_mut_ptr_of(bytes.as_mut_ptr())).as_usize(),
0,
))
.value
}
26 changes: 24 additions & 2 deletions modules/axhal/src/platform/x86_pc/uart16550.rs
Original file line number Diff line number Diff line change
Expand Up @@ -84,7 +84,7 @@ impl Uart16550 {
}

/// Writes a byte to the console.
pub fn putchar(c: u8) {
fn putchar(c: u8) {
let mut uart = COM1.lock();
match c {
b'\n' => {
Expand All @@ -96,10 +96,32 @@ pub fn putchar(c: u8) {
}

/// Reads a byte from the console, or returns [`None`] if no input is available.
pub fn getchar() -> Option<u8> {
fn getchar() -> Option<u8> {
COM1.lock().getchar()
}

/// Write a slice of bytes to the console.
pub fn write_bytes(bytes: &[u8]) {
for c in bytes {
putchar(*c);
}
}

/// Reads bytes from the console into the given mutable slice.
/// Returns the number of bytes read.
pub fn read_bytes(bytes: &mut [u8]) -> usize {
let mut read_len = 0;
while read_len < bytes.len() {
if let Some(c) = getchar() {
bytes[read_len] = c;
} else {
break;
}
read_len += 1;
}
read_len
}

pub(super) fn init() {
COM1.lock().init(115200);
}
7 changes: 3 additions & 4 deletions ulib/axstd/src/io/stdio.rs
Original file line number Diff line number Diff line change
Expand Up @@ -12,12 +12,11 @@ impl Read for StdinRaw {
fn read(&mut self, buf: &mut [u8]) -> io::Result<usize> {
let mut read_len = 0;
while read_len < buf.len() {
if let Some(c) = arceos_api::stdio::ax_console_read_byte() {
buf[read_len] = c;
read_len += 1;
} else {
let len = arceos_api::stdio::ax_console_read_bytes(buf[read_len..].as_mut())?;
if len == 0 {
break;
}
read_len += len;
}
Ok(read_len)
}
Expand Down
Loading