Move kcmdline parsing out of OSTD

This commit is contained in:
Zhang Junyang
2024-12-31 14:29:49 +08:00
committed by Tate, Hongliang Tian
parent 397ce9652f
commit 5ea366bced
5 changed files with 20 additions and 27 deletions

View File

@ -18,8 +18,6 @@ use alloc::{
vec::Vec, vec::Vec,
}; };
use crate::early_println;
#[derive(PartialEq, Debug)] #[derive(PartialEq, Debug)]
struct InitprocArgs { struct InitprocArgs {
path: Option<String>, path: Option<String>,
@ -116,7 +114,7 @@ impl From<&str> for KCmdlineArg {
1 => (arg_pattern[0], None), 1 => (arg_pattern[0], None),
2 => (arg_pattern[0], Some(arg_pattern[1])), 2 => (arg_pattern[0], Some(arg_pattern[1])),
_ => { _ => {
early_println!( log::warn!(
"[KCmdline] Unable to parse kernel argument {}, skip for now", "[KCmdline] Unable to parse kernel argument {}, skip for now",
arg arg
); );
@ -129,7 +127,7 @@ impl From<&str> for KCmdlineArg {
1 => (None, entry_pattern[0]), 1 => (None, entry_pattern[0]),
2 => (Some(entry_pattern[0]), entry_pattern[1]), 2 => (Some(entry_pattern[0]), entry_pattern[1]),
_ => { _ => {
early_println!( log::warn!(
"[KCmdline] Unable to parse entry {} in argument {}, skip for now", "[KCmdline] Unable to parse entry {} in argument {}, skip for now",
entry, entry,
arg arg

View File

@ -30,6 +30,7 @@
#![feature(trait_upcasting)] #![feature(trait_upcasting)]
#![register_tool(component_access_control)] #![register_tool(component_access_control)]
use kcmdline::KCmdlineArg;
use ostd::{ use ostd::{
arch::qemu::{exit_qemu, QemuExitCode}, arch::qemu::{exit_qemu, QemuExitCode},
boot::boot_info, boot::boot_info,
@ -59,6 +60,7 @@ pub mod error;
pub mod events; pub mod events;
pub mod fs; pub mod fs;
pub mod ipc; pub mod ipc;
pub mod kcmdline;
pub mod net; pub mod net;
pub mod prelude; pub mod prelude;
mod process; mod process;
@ -141,7 +143,7 @@ fn init_thread() {
print_banner(); print_banner();
let karg = &boot_info().kernel_cmdline; let karg: KCmdlineArg = boot_info().kernel_cmdline.as_str().into();
let initproc = Process::spawn_user_process( let initproc = Process::spawn_user_process(
karg.get_initproc_path().unwrap(), karg.get_initproc_path().unwrap(),

View File

@ -40,14 +40,10 @@ fn parse_kernel_commandline(mb1_info: &MultibootLegacyInfo) -> &str {
if mb1_info.cmdline != 0 { if mb1_info.cmdline != 0 {
// SAFETY: the command line is C-style zero-terminated string. // SAFETY: the command line is C-style zero-terminated string.
unsafe { unsafe {
let cstr = paddr_to_vaddr(mb1_info.cmdline as usize) as *const u8; let cstr = paddr_to_vaddr(mb1_info.cmdline as usize) as *const i8;
let mut len = 0; let cstr = core::ffi::CStr::from_ptr(cstr);
while cstr.add(len).read() != 0 {
len += 1;
}
cmdline = core::str::from_utf8(core::slice::from_raw_parts(cstr, len)) cmdline = cstr.to_str().unwrap();
.expect("cmdline is not a utf-8 string");
} }
} }
cmdline cmdline

View File

@ -6,7 +6,6 @@
//! 2. the routine booting into the actual kernel; //! 2. the routine booting into the actual kernel;
//! 3. the routine booting the other processors in the SMP context. //! 3. the routine booting the other processors in the SMP context.
pub mod kcmdline;
pub mod memory_region; pub mod memory_region;
pub mod smp; pub mod smp;
@ -15,7 +14,6 @@ use alloc::{
vec::Vec, vec::Vec,
}; };
use kcmdline::KCmdlineArg;
use memory_region::{MemoryRegion, MemoryRegionArray}; use memory_region::{MemoryRegion, MemoryRegionArray};
use spin::Once; use spin::Once;
@ -24,7 +22,7 @@ pub struct BootInfo {
/// The name of the bootloader. /// The name of the bootloader.
pub bootloader_name: String, pub bootloader_name: String,
/// The kernel command line arguments. /// The kernel command line arguments.
pub kernel_cmdline: KCmdlineArg, pub kernel_cmdline: String,
/// The initial ramfs raw bytes. /// The initial ramfs raw bytes.
pub initramfs: Option<&'static [u8]>, pub initramfs: Option<&'static [u8]>,
/// The framebuffer arguments. /// The framebuffer arguments.
@ -100,7 +98,7 @@ pub(crate) fn init() {
INFO.call_once(|| BootInfo { INFO.call_once(|| BootInfo {
bootloader_name: boot_time_info.bootloader_name.to_string(), bootloader_name: boot_time_info.bootloader_name.to_string(),
kernel_cmdline: boot_time_info.kernel_cmdline.into(), kernel_cmdline: boot_time_info.kernel_cmdline.to_string(),
initramfs: boot_time_info.initramfs, initramfs: boot_time_info.initramfs,
framebuffer_arg: boot_time_info.framebuffer_arg, framebuffer_arg: boot_time_info.framebuffer_arg,
memory_regions: boot_time_info.memory_regions.to_vec(), memory_regions: boot_time_info.memory_regions.to_vec(),

View File

@ -12,7 +12,7 @@ use core::str::FromStr;
use log::{LevelFilter, Metadata, Record}; use log::{LevelFilter, Metadata, Record};
use spin::Once; use spin::Once;
use crate::boot::{boot_info, kcmdline::ModuleArg}; use crate::boot::BOOT_TIME_INFO;
static LOGGER: Logger = Logger::new(); static LOGGER: Logger = Logger::new();
@ -82,16 +82,15 @@ pub(crate) fn init() {
} }
fn get_log_level() -> Option<LevelFilter> { fn get_log_level() -> Option<LevelFilter> {
let module_args = boot_info().kernel_cmdline.get_module_args("ostd")?; let kcmdline = BOOT_TIME_INFO.get().unwrap().kernel_cmdline;
// Although OSTD is agnostic of the parsing of the kernel command line,
// the logger assumes that it follows the Linux kernel command line format.
// We search for the `ostd.log_level=ARGUMENT` pattern in string.
let value = kcmdline
.split(' ')
.find(|arg| arg.starts_with("ostd.log_level="))
.map(|arg| arg.split('=').last().unwrap_or_default())?;
let value = {
let value = module_args.iter().find_map(|arg| match arg {
ModuleArg::KeyVal(name, value) if name.as_bytes() == "log_level".as_bytes() => {
Some(value)
}
_ => None,
})?;
value.as_c_str().to_str().ok()?
};
LevelFilter::from_str(value).ok() LevelFilter::from_str(value).ok()
} }