riscv: probe sbi extensions (#511)

This commit is contained in:
LoGin 2024-02-07 17:15:17 +08:00 committed by GitHub
parent f2022a8a1c
commit cb23beb255
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
4 changed files with 118 additions and 5 deletions

View File

@ -63,7 +63,7 @@ x86_64 = "0.14.10"
# target为riscv64时使用下面的依赖
[target.'cfg(target_arch = "riscv64")'.dependencies]
riscv = { version = "0.11.0", features = [ "s-mode" ] }
sbi-rt = { git = "https://github.com/rustsbi/rustsbi" }
sbi-rt = { git = "https://git.mirrors.dragonos.org.cn/DragonOS-Community/rustsbi.git", rev = "80478bc417", features = ["legacy"] }
# 构建时依赖项

View File

@ -18,7 +18,115 @@
/// console_putstr(message);
/// ```
pub fn console_putstr(s: &[u8]) {
for c in s {
sbi_rt::console_write_byte(*c);
if SbiDriver::extensions().contains(SBIExtensions::CONSOLE) {
for c in s {
sbi_rt::console_write_byte(*c);
}
return;
} else {
for c in s {
#[allow(deprecated)]
sbi_rt::legacy::console_putchar(*c as usize);
}
}
}
bitflags! {
pub struct SBIExtensions: u64 {
/// RISC-V SBI Base extension.
const BASE = 1 << 0;
/// Timer programmer extension.
const TIME = 1 << 1;
/// Inter-processor Interrupt extension.
const SPI = 1 << 2;
/// Remote Fence extension.
const RFENCE = 1 << 3;
/// Hart State Monitor extension.
const HSM = 1 << 4;
/// System Reset extension.
const RESET = 1 << 5;
/// Performance Monitoring Unit extension.
const PMU = 1 << 6;
/// Debug Console extension.
const CONSOLE = 1 << 7;
/// System Suspend extension.
const SUSPEND = 1 << 8;
/// SBI CPPC extension.
const CPPC = 1 << 9;
/// Nested Acceleration extension.
const NACL = 1 << 10;
/// Steal-time Accounting extension.
const STA = 1 << 11;
}
}
static mut EXTENSIONS: SBIExtensions = SBIExtensions::empty();
#[derive(Debug)]
pub struct SbiDriver;
impl SbiDriver {
#[inline(never)]
pub fn early_init() {
unsafe {
EXTENSIONS = Self::probe_extensions();
}
}
/// 获取probe得到的SBI扩展信息。
pub fn extensions() -> &'static SBIExtensions {
unsafe { &EXTENSIONS }
}
fn probe_extensions() -> SBIExtensions {
let mut extensions = SBIExtensions::empty();
if sbi_rt::probe_extension(sbi_rt::Base).is_available() {
extensions |= SBIExtensions::BASE;
}
if sbi_rt::probe_extension(sbi_rt::Timer).is_available() {
extensions |= SBIExtensions::TIME;
}
if sbi_rt::probe_extension(sbi_rt::Ipi).is_available() {
extensions |= SBIExtensions::SPI;
}
if sbi_rt::probe_extension(sbi_rt::Fence).is_available() {
extensions |= SBIExtensions::RFENCE;
}
if sbi_rt::probe_extension(sbi_rt::Hsm).is_available() {
extensions |= SBIExtensions::HSM;
}
if sbi_rt::probe_extension(sbi_rt::Reset).is_available() {
extensions |= SBIExtensions::RESET;
}
if sbi_rt::probe_extension(sbi_rt::Pmu).is_available() {
extensions |= SBIExtensions::PMU;
}
if sbi_rt::probe_extension(sbi_rt::Console).is_available() {
extensions |= SBIExtensions::CONSOLE;
}
if sbi_rt::probe_extension(sbi_rt::Suspend).is_available() {
extensions |= SBIExtensions::SUSPEND;
}
if sbi_rt::probe_extension(sbi_rt::Cppc).is_available() {
extensions |= SBIExtensions::CPPC;
}
if sbi_rt::probe_extension(sbi_rt::Nacl).is_available() {
extensions |= SBIExtensions::NACL;
}
if sbi_rt::probe_extension(sbi_rt::Sta).is_available() {
extensions |= SBIExtensions::STA;
}
return extensions;
}
}

View File

@ -2,7 +2,7 @@ use fdt::node::FdtNode;
use system_error::SystemError;
use crate::{
arch::mm::init::mm_early_init,
arch::{driver::sbi::SbiDriver, mm::init::mm_early_init},
driver::{firmware::efi::init::efi_init, open_firmware::fdt::open_firmware_fdt_driver},
init::{boot_params, init::start_kernel},
kdebug, kinfo,
@ -10,6 +10,8 @@ use crate::{
print, println,
};
use super::driver::sbi::console_putstr;
#[derive(Debug)]
pub struct ArchBootParams {
/// 启动时的fdt物理地址
@ -76,9 +78,11 @@ unsafe fn parse_dtb() {
#[inline(never)]
pub fn early_setup_arch() -> Result<(), SystemError> {
let hartid = unsafe { BOOT_HARTID };
SbiDriver::early_init();
let hartid: usize = unsafe { BOOT_HARTID };
let fdt_paddr = unsafe { BOOT_FDT_PADDR };
boot_params().write().arch.fdt_paddr = fdt_paddr;
kinfo!(
"DragonOS kernel is running on hart {}, fdt address:{:?}",
hartid,

View File

@ -44,6 +44,7 @@ pub fn start_kernel() -> ! {
#[inline(never)]
fn do_start_kernel() {
init_before_mem_init();
early_setup_arch().expect("setup_arch failed");
unsafe { mm_init() };
scm_reinit().unwrap();