Giter Site home page Giter Site logo

rustsbi-qemu's Introduction

QEMU support from RustSBI

RustSBI is designed as a library to craft a bootable binary or ELF file. However, QEMU provides us a way to load ELF file and implement simple SBI directly, thus RustSBI provides a bootable ELF file for this platform.

Try it out!

To prepare for environment, you should have Rust compiler and QEMU installed. You may install Rust by rustup or using vendor provided rustc and cargo packages. To install QEMU, your may need to use package manager (e.g. apt, dnf etc.) from system distribution to get a proper QEMU software package.

After environment prepared, compile and run with:

cargo qemu

When running cargo qemu, the test kernel will build and run. Expected output should be:

[rustsbi] RustSBI version 0.4.0-alpha.1, adapting to RISC-V SBI v1.0.0
.______       __    __      _______.___________.  _______..______   __
|   _  \     |  |  |  |    /       |           | /       ||   _  \ |  |
|  |_)  |    |  |  |  |   |   (----`---|  |----`|   (----`|  |_)  ||  |
|      /     |  |  |  |    \   \       |  |      \   \    |   _  < |  |
|  |\  \----.|  `--'  |.----)   |      |  |  .----)   |   |  |_)  ||  |
| _| `._____| \______/ |_______/       |__|  |_______/    |______/ |__|
[rustsbi] Implementation     : RustSBI-QEMU Version 0.2.0-alpha.2
[rustsbi] Platform Name      : riscv-virtio,qemu
[rustsbi] Platform SMP       : 8
[rustsbi] Platform Memory    : 0x80000000..0x88000000
[rustsbi] Boot HART          : 6
[rustsbi] Device Tree Region : 0x87e00000..0x87e01a8e
[rustsbi] Firmware Address   : 0x80000000
[rustsbi] Supervisor Address : 0x80200000
[rustsbi] pmp01: 0x00000000..0x80000000 (-wr)
[rustsbi] pmp02: 0x80000000..0x80200000 (---)
[rustsbi] pmp03: 0x80200000..0x88000000 (xwr)
[rustsbi] pmp04: 0x88000000..0x00000000 (-wr)

 _____         _     _  __                    _
|_   _|__  ___| |_  | |/ /___ _ __ _ __   ___| |
  | |/ _ \/ __| __| | ' // _ \ '__| '_ \ / _ \ |
  | |  __/\__ \ |_  | . \  __/ |  | | | |  __/ |
  |_|\___||___/\__| |_|\_\___|_|  |_| |_|\___|_|
================================================
| boot hart id          |                    6 |
| smp                   |                    8 |
| timebase frequency    |          10000000 Hz |
| dtb physical address  |           0x87e00000 |
------------------------------------------------
[ INFO] Testing `Base`
[ INFO] sbi spec version = 2.0
[ INFO] sbi impl = RustSBI
[ INFO] sbi impl version = 0x400
[ INFO] sbi extensions = [Base, TIME, sPI, HSM, SRST]
[ INFO] mvendor id = 0x0
[ INFO] march id = 0x70200
[ INFO] mimp id = 0x70200
[ INFO] Sbi `Base` test pass
[ INFO] Testing `TIME`
[ INFO] read time register successfully, set timer +1s
[ INFO] timer interrupt delegate successfully
[ INFO] Sbi `TIME` test pass
[ INFO] Testing `sPI`
[ INFO] send ipi successfully
[ INFO] Sbi `sPI` test pass
[ INFO] Testing `HSM`
[ INFO] Testing harts: [0, 1, 2, 3]
[DEBUG] hart 0 started
[DEBUG] hart 0 suspended nonretentive
[DEBUG] hart 1 started
[DEBUG] hart 1 suspended nonretentive
[DEBUG] hart 2 started
[DEBUG] hart 2 suspended nonretentive
[DEBUG] hart 3 started
[DEBUG] hart 3 suspended nonretentive
[DEBUG] hart 0 resumed
[DEBUG] hart 0 suspended retentive
[DEBUG] hart 0 stopped
[DEBUG] hart 1 resumed
[DEBUG] hart 1 suspended retentive
[DEBUG] hart 1 stopped
[DEBUG] hart 2 resumed
[DEBUG] hart 2 suspended retentive
[DEBUG] hart 2 stopped
[DEBUG] hart 3 resumed
[DEBUG] hart 3 suspended retentive
[DEBUG] hart 3 stopped
[ INFO] Testing Pass: [0, 1, 2, 3]
[ INFO] Testing harts: [4, 5, 7]
[DEBUG] hart 4 started
[DEBUG] hart 4 suspended nonretentive
[DEBUG] hart 5 started
[DEBUG] hart 5 suspended nonretentive
[DEBUG] hart 7 started
[DEBUG] hart 7 suspended nonretentive
[DEBUG] hart 4 resumed
[DEBUG] hart 4 suspended retentive
[DEBUG] hart 4 stopped
[DEBUG] hart 5 resumed
[DEBUG] hart 5 suspended retentive
[DEBUG] hart 5 stopped
[DEBUG] hart 7 resumed
[DEBUG] hart 7 suspended retentive
[DEBUG] hart 7 stopped
[ INFO] Testing Pass: [4, 5, 7]
[ INFO] Sbi `HSM` test pass
[ INFO] Testing `DBCN`
Hello, world!
[ INFO] writing slice successfully
[ INFO] reading 0 bytes from console
[ INFO] Sbi `DBCN` test pass

Run test kernel

Requirements

You should have cargo-binutils installed.

cargo install cargo-binutils

Run

Run with:

cargo test

It will run RustSBI-QEMU with a test kernel. The test kernel will test all SBI functions, its command emulation and other features. If it succeeds, there would be output like:

running 1 test
    Finished dev [unoptimized + debuginfo] target(s) in 0.14s
   Compiling test-kernel v0.1.0 (D:\RustProjects\rustsbi-qemu\test-kernel)
    Finished dev [unoptimized + debuginfo] target(s) in 0.61s
test run_test_kernel ... ok

test result: ok. 1 passed; 0 failed; 0 ignored; 0 measured; 0 filtered out; finished in 2.31s

Notes

  1. What kind of kernel does this project support?

    The rustsbi-qemu project supports raw binary kernels for educational or competition use. This project itself is only a showcase example illustrating how implementations should use RustSBI, it does not include a Linux boot support. You may visit downstream bootloader projects for a Linux capable bootloader.

  2. How to enable hypervisor H extension on QEMU?

    You should use these following line of parameters:

        command.args(&["-cpu", "rv64,x-h=true"]);

    ... to enable H extension on QEMU software.

    The H extension is enabled by default when QEMU version >= 7.0.0.

  3. What is the minimum supported Rust version of this package?

    You should build RustSBI-QEMU on nightly at least rustc 1.66.0-nightly (a24a020e6 2022-10-18).

License

This project is licensed under Mulan PSL v2.

Copyright (c) 2021-2023 RustSBI Team
RustSBI-QEMU is licensed under Mulan PSL v2.
You can use this software according to the terms and conditions of the Mulan PSL v2.
You may obtain a copy of Mulan PSL v2 at:
         http://license.coscl.org.cn/MulanPSL2
THIS SOFTWARE IS PROVIDED ON AN "AS IS" BASIS, WITHOUT WARRANTIES OF ANY KIND,
EITHER EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO NON-INFRINGEMENT,
MERCHANTABILITY OR FIT FOR A PARTICULAR PURPOSE.
See the Mulan PSL v2 for more details.

rustsbi-qemu's People

Contributors

duskmoon314 avatar felixonmars avatar kuangjux avatar luojia65 avatar placebo27 avatar vaaandark avatar wyfcyx avatar ydrmaster avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar

rustsbi-qemu's Issues

或许可以考虑将test-kernel独立成一个新的项目?

注意到作为测试用例的test-kernel目前是作为该项目以及rustsbi-k210项目的一部分存在的。考虑到其作为测试用例而言对这两个sbi实现具有普适性,是否可以将test-kernel独立出来?这样还可以方便其他的SBI实现使用其作为测试用例。

是否期望和qemu自带的sbi行为一致?

我这边观察到的rustsbi的行为是,每一个hart都会启动进入系统内核,并且hartid不为0的hart才能接受到a1 (device tree)参数。相同的代码用qemu自带的sbi跑,只有hartid为0的hart启动进入内核,能接受到device tree,其他hart为Stopped状态。
是否应该期望两者行为一致,还是说这是一种feature?

使用cargo qemu进行build时报错

我在使用cargo qemu进行编译,显示了如下错误。
image
因此,我认为是rustsbi v0.2.0-alpha.8导致的编译错误。
这是我使用的toolchain 的情况:
image
奇怪的是,我在rustsbi的仓库下(https://github.com/rustsbi/rustsbi/)
对rustsbi的最新版本0.2.0-alpha.9进行编译不会报错。
image
并且编译rustsbi使用的toolchain和编译rustsbi-qemu时使用的toolchain相同:
image

看上去问题 的根源应该是最新版本的toolchain不太适配rustsbi v0.2.0-alpha.8导致的编译错误。

Legacy sbi_set_timer() behaves differently than new sbi_set_timer() on QEMU ?

Rustsbi version: at commit 269d1d32b4c0fd4900e6db1f070e7a2ce983dd14
QEMU version: 5.2.0

Minimalist test case:

int main() {
  w_stvec((uint64_t)kvec_asm); // i put some printf in interrupt handler
  s_sstatus(SSTATUS_SIE);
  s_sie(SIE_SSIE | SIE_STIE | SIE_SEIE);
  sbi_legacy_set_timer(r_time() + 30000000);
  // struct sbiret r = sbi_set_timer(r_time() + 30000000);
  // printf("%l, %l\n", r.error, r.value);
  while(1);
  return 0;
 }

When i use the legacy sbi_legacy_set_timer(), the code works as expected, outputs a lot.

When i use the new sbi_set_time(), it seems that timer interrupt was never triggered..

I have traced the code, the params were properly passed.

image
image

Is the difference an expected behavior?

Thanks ~~~

使用cargo qemu进行build时报错

我在使用cargo qemu进行编译,显示了如下错误。
➜ [/home/wynn/Desktop/codes/rustsbi-qemu] git:(main) cargo qemu Finished dev [unoptimized + debuginfo] target(s) in 0.03s Runningtarget/debug/xtask qemuxtask: mode: Debug Compiling rustsbi v0.2.0-alpha.8 error: cannot find macroasmin this scope --> /home/wynn/.cargo/registry/src/mirrors.ustc.edu.cn-61ef6e0cd06fb9b8/rustsbi-0.2.0-alpha.8/src/privileged.rs:30:15 | 30 | () => asm!(" | ^^^ | = note: consider importing this macro: core::arch::asm
因此,我认为是rustsbi v0.2.0-alpha.8导致的编译错误。
这是我使用的toolchain 的情况:
`➜ [/home/wynn/Desktop/codes/rustsbi-qemu] git:(main) rustup show
Default host: x86_64-unknown-linux-gnu
rustup home: /home/wynn/.rustup

installed toolchains

stable-x86_64-unknown-linux-gnu
nightly-2018-09-18-x86_64-unknown-linux-gnu
nightly-2019-07-15-x86_64-unknown-linux-gnu
nightly-2020-05-01-x86_64-unknown-linux-gnu
nightly-2020-06-04-x86_64-unknown-linux-gnu
nightly-2020-06-27-x86_64-unknown-linux-gnu
nightly-2021-10-15-x86_64-unknown-linux-gnu
nightly-x86_64-unknown-linux-gnu (default)

installed targets for active toolchain

riscv64imac-unknown-none-elf
x86_64-unknown-linux-gnu

active toolchain

nightly-x86_64-unknown-linux-gnu (overridden by '/home/wynn/Desktop/codes/rustsbi-qemu/rust-toolchain.toml')
rustc 1.59.0-nightly (475b00aa4 2021-12-24)`

奇怪的是,我在rustsbi的仓库下(https://github.com/rustsbi/rustsbi/)对rustsbi的最新版本0.2.0-alpha.9进行编译不会报错。
`
➜ [/home/wynn/Desktop/codes/rustsbi] git:(master) cargo build --target riscv64imac-unknown-none-elf

Compiling memchr v2.4.1
Compiling regex-syntax v0.6.25
Compiling lazy_static v1.4.0
Compiling nb v1.0.0
Compiling bit_field v0.10.1
Compiling void v1.0.2
Compiling bare-metal v1.0.0
Compiling nb v0.1.3
Compiling embedded-hal v0.2.6
Compiling aho-corasick v0.7.18
Compiling regex v1.5.4
Compiling riscv-target v0.1.2
Compiling riscv v0.7.0
Compiling rustsbi v0.2.0-alpha.9 (/home/wynn/Desktop/codes/rustsbi)
Finished dev [unoptimized + debuginfo] target(s) in 6.48s
并且编译rustsbi使用的toolchain和编译rustsbi-qemu时使用的toolchain相同:
➜ [/home/wynn/Desktop/codes/rustsbi] git:(master) rustup show
Default host: x86_64-unknown-linux-gnu
rustup home: /home/wynn/.rustup

installed toolchains

stable-x86_64-unknown-linux-gnu
nightly-2018-09-18-x86_64-unknown-linux-gnu
nightly-2019-07-15-x86_64-unknown-linux-gnu
nightly-2020-05-01-x86_64-unknown-linux-gnu
nightly-2020-06-04-x86_64-unknown-linux-gnu
nightly-2020-06-27-x86_64-unknown-linux-gnu
nightly-2021-10-15-x86_64-unknown-linux-gnu
nightly-x86_64-unknown-linux-gnu (default)

installed targets for active toolchain

riscv64imac-unknown-none-elf
x86_64-unknown-linux-gnu

active toolchain

nightly-x86_64-unknown-linux-gnu (default)
rustc 1.59.0-nightly (475b00aa4 2021-12-24)
`

A proper way to set pmp registers

Now rustsbi-qemu doesn't allow S mode software use devices provided by qemu because we havn't set pmp registers for them.

Noticed that qemu provides more than one board, and they have different MMIO. We need to discuss how to set pmp registers properly.

现在 rustsbi-qemu 不允许 S 态软件使用 qemu 提供的设备,因为我们没有为它们设置 pmp 寄存器。

注意到 qemu 提供了不止一种板子,而且它们有不同的 MMIO。我们需要讨论如何正确设置 pmp 寄存器。


If anyone who wonder how to use devices in qemu, here is an example of using uart0 (uart0_mmio base 0x10000000 lenth 0x100) in virt machine:

如果任何人想知道如何使用 qemu 的外设,下面是使用 virt 的 uart0 (uart0_mmio 基址 0x10000000 长度 0x100) 的一个例子:

fn set_pmp() {
    unsafe {
        asm!(
-            "li     {tmp}, ((0x08 << 16) | (0x1F << 8) | (0x1F << 0))", // 0 = NAPOT,ARWX; 1 = NAPOT,ARWX; 2 = TOR,A;
+            "li     {tmp}, ((0x08 << 24) | (0x1F << 16) | (0x1F << 8) | (0x1F << 0))", // 0 = NAPOT,ARWX; 1 = NAPOT,ARWX; 2 = TOR,A;
            "csrw   0x3A0, {tmp}",
            "li     {tmp}, ((0x0000000080000000 >> 2) | 0x3ffff)", // 0 = 0x0000000080000000-0x000000008001ffff
            "csrw   0x3B0, {tmp}",
            "li     {tmp}, ((0x0000000080200000 >> 2) | 0x1fffff)", // 1 = 0x0000000080200000-0x000000008021ffff
            "csrw   0x3B1, {tmp}",
+            "li     {tmp}, ((0x0000000010000000 >> 2) | 0x3f)",
+            "csrw   0x3B2, {tmp}",
            "sfence.vma",
            tmp = out(reg) _
        )
    };
}

It can't start test in Linux environment

It looks good in windows :

PS C:\Rust\rustsbi-qemu> cargo qemu
    Finished release [optimized] target(s) in 0.06s
     Running `target\release\xtask.exe qemu`
    Finished release [optimized] target(s) in 0.06s
    Finished release [optimized] target(s) in 0.06s
[rustsbi] RustSBI version 0.3.0-alpha.4, adapting to RISC-V SBI v1.0.0
.______       __    __      _______.___________.  _______..______   __
|   _  \     |  |  |  |    /       |           | /       ||   _  \ |  |
|  |_)  |    |  |  |  |   |   (----`---|  |----`|   (----`|  |_)  ||  |
|      /     |  |  |  |    \   \       |  |      \   \    |   _  < |  |
|  |\  \----.|  `--'  |.----)   |      |  |  .----)   |   |  |_)  ||  |
| _| `._____| \______/ |_______/       |__|  |_______/    |______/ |__|
[rustsbi] Implementation     : RustSBI-QEMU Version 0.2.0-alpha.2
[rustsbi] Platform Name      : riscv-virtio,qemu
[rustsbi] Platform SMP       : 8
[rustsbi] Platform Memory    : 0x80000000..0x88000000
[rustsbi] Boot HART          : 6
[rustsbi] Device Tree Region : 0x87e00000..0x87e01925
[rustsbi] Firmware Address   : 0x80000000
[rustsbi] Supervisor Address : 0x80200000
[rustsbi] pmp01: 0x00000000..0x80000000 (-wr)
[rustsbi] pmp02: 0x80000000..0x80200000 (---)
[rustsbi] pmp03: 0x80200000..0x88000000 (xwr)
[rustsbi] pmp04: 0x88000000..0x00000000 (-wr)
.....................

But when I try to run it in ubuntu22.04, an error was thrown out in the beginnig like this:

$:~/workspace/debug/rustsbi-qemu$ cargo qemu
    Finished release [optimized] target(s) in 0.01s
     Running `target/release/xtask qemu`
    Finished release [optimized] target(s) in 0.01s
    Finished release [optimized] target(s) in 0.01s
xtask: QEMU command not found. Does your system have QEMU installed and environment variable configured?
xtask: error: No such file or directory (os error 2)
$: ~

rustsbi and opensbi getchar differences

I found that opensbi and rustsbi have different getchar implemenation. Opensbi will return -1(or we can say 255) if it does not receive a char, but rustsbi will wait until getting char.

legacy::LEGACY_CONSOLE_GETCHAR => {
    ret.error = unsafe { UART.lock().assume_init_mut() }.receive() as _;
    ret.value = a1;
}

The above is the implementation of rustsbi, and I found the implementation of receive as shown below. So the implementations of opensbi and rustsbi are totally different.

pub fn receive(&mut self) -> u8 {
        let self_data = self.data.load(Ordering::Relaxed);
        unsafe {
            wait_for!(self.line_sts().contains(LineStsFlags::INPUT_FULL));
            self_data.read()
        }
    }

But the following sbi doc describes that we should return -1 when error. So what I want to ask is whether this is a difference or mistake.

5.3. Extension: Console Getchar (EID #0x02)
long sbi_console_getchar(void)
Read a byte from debug console.

The SBI call returns the byte on success, or -1 for failure.

Wrong PMP output and compatibility with rCore-Tutorial-v3 of rustsbi-qemu version 0.1.1

The Rustsbi binary was downloaded from https://github.com/rustsbi/rustsbi-qemu/releases/download/v0.1.1/rustsbi-qemu-release.zip.

$ qemu-system-riscv64 --version
QEMU emulator version 6.2.0
Copyright (c) 2003-2021 Fabrice Bellard and the QEMU Project developers
$ qemu-system-riscv64 -machine virt -nographic -bios ../bootloader/rustsbi-qemu.bin -smp 1
[rustsbi] RustSBI version 0.2.2, adapting to RISC-V SBI v1.0.0
[logo]
[rustsbi] Implementation: RustSBI-QEMU Version 0.1.1
[rustsbi-dtb] Hart count: cluster0 with 1 cores
[rustsbi] misa: RV64ACDFIMSU
[rustsbi] mideleg: ssoft, stimer, sext (0x222)
[rustsbi] medeleg: ima, ia, bkpt, la, sa, uecall, ipage, lpage, spage (0xb1ab)
[rustsbi] pmp0: 0x10000000 ..= 0x10001fff (rw-)
[rustsbi] pmp6: 0x2000000 ..= 0x200ffff (rw-)
[rustsbi] pmp12: 0xc000000 ..= 0xc3fffff (rw-)
[rustsbi] enter supervisor 0x80200000
$ qemu-system-riscv64 -machine virt -nographic -bios ../bootloader/rustsbi-qemu.bin -smp 8
[rustsbi] RustSBI version 0.2.2, adapting to RISC-V SBI v1.0.0
[logo]
[rustsbi] Implementation: RustSBI-QEMU Version 0.1.1
[rustsbi-dtb] Hart count: cluster0 with 8 cores
[rustsbi] misa: RV64ACDFIMSU
[rustsbi] mideleg: ssoft, stimer, sext (0x222)
[rustsbi] medeleg: ima, ia, bkpt, la, sa, uecall, ipage, lpage, spage (0xb1ab)
[rustsbi] pmp0: 0x10000000 ..= 0x10001fff (rw-)
[rustsbi] pmp6: 0x2000000 ..= 0x200ffff (rw-)
[rustsbi] pmp12: 0xc000000 ..= 0xc3fffff (rw-)
[rustsbi] enter supervisor 0x80200000

The PMP output was not correct. Actually, the expected output is:

[rustsbi] pmp0: 0x10000000 ..= 0x10001fff (rw-)
[rustsbi] pmp1: 0x2000000 ..= 0x200ffff (rw-)
[rustsbi] pmp2: 0xc000000 ..= 0xc3fffff (rw-)
[rustsbi] pmp3: 0x80000000 ..= 0x8fffffff (rwx)

It was very weird that when I tested using cargo qemu under the rustsbi-qemu root directory, the output was correct. I did not know what happened.


Another question is that rCore-Tutorial-v3 cannot work normally using rustsbi-qemu version 0.1.1 if the tutorial is built in debug mode. However, it works under release mode. Therefore, I decide not to upgrade rustsbi for a while...

HSM和IPI、RFENCE扩展共存的问题

目前rustsbi-qemu在收到M态软件中断时,只会判断上一个HSM命令,如果不存在就直接 panic ,导致S态软件无论是通过SBI s-IPI扩展还是直接访问Clint都无法使用IPI功能(除非是ACLINT)。

一个最直接的hack就是发现没有HSM命令时,把软件中断直接转发给S态;不过这样可能处理不了rfence扩展,应该得再加一套或者两套命令接口。

在Ubuntu物理机和WSL 上行为不一致

您好!
我正在尝试跑通rcore。
按照 http://rcore-os.cn/rCore-Tutorial-Book-v3/chapter0/5setup-devel-env.html 里的描述,可以正常在WSL和物理机上跑通rcore。
然而,我注意到有一个rcore的实验指导,专门为了做实验的同学设计的,这里面的代码和tutorial稍有不同,我尝试跑通实验指导三:虚拟内存的时候的时候,出现了以下奇怪的情况:

物理机+opensbi(qemu参数改为default): 正常运行!
物理机+rustsbi2.2.0: 运行失败! 具体来说,在虚拟内存开启之后(mm::init()之后),println宏无法打印变量的值,此时PC不知道跑哪去了,再也没有输出了!
WSL+opensbi: 所有章节的rcore都运行失败!(rcore指的是实验指导的rcore,不是tutorial的rcore)
WSL+rustsbi: 没有虚拟内存的章节的rcore可以正常运行,但是开启了虚拟内存章节的rcore运行失败!

rustsbi下字符显示异常

image

可以看到对于某些字符重复发送导致格式异常和乱码
同样在opensbi下无此问题
下附opensbi图
image

在qemu下出现乱码问题

image

可以看到对于某些字符重复发送导致格式异常和乱码
同样在opensbi下无此问题
下附opensbi图
image

关于非法指令的转发行为

在现有的处理中:

mstatus::set_spp(SPP::Supervisor);

仅仅设置SPP为S态似乎有些草率。比如在xv6中,若是在用户态触发了非法指令异常,那么在异常处理函数中会判断该异常是否来自于用户态:

if((r_sstatus() & SSTATUS_SPP) != 0){
  panic("usertrap: not from user mode");
}

若按上述设置,那么将会触发panic,这对于debug来说颇具误导性...

比较合适的设置方法应该是根据现有的MPP来设置SPP:

// 设置中断位
if ctx.mstatus.mpp() == MPP::User {
    mstatus::set_spp(SPP::User);
} else {
    mstatus::set_spp(SPP::Supervisor);
}
    
mstatus::set_mpp(MPP::Supervisor);

The newer version of dtc stops qemu-system-riscv64 properly executing RustSBI

I'm currently using qemu 7.0.0 for risc-v system emulation. However, the current version of device tree compiler might caught problem. If we use git clone to get the qemu source and compile it, the qemu does not work properly as it gets stuck in a loop before jumping to the kernel. The execution trace of this loop shows below. It causes RustABI in an infinite loop around address 0x80001b00:

(gdb) si
0x0000000080001b00 in ?? ()
(gdb) si
0x0000000080001b04 in ?? ()
(gdb) si
0x0000000080001b08 in ?? ()
(gdb) si
0x0000000080001b0c in ?? ()
(gdb) si
0x0000000080001b10 in ?? ()
(gdb) si
0x0000000080004394 in ?? ()
(gdb) si
0x0000000080001b14 in ?? ()
(gdb) si
0x0000000080001b18 in ?? ()
(gdb) si
0x0000000080001b00 in ?? ()
(gdb) x/10i $pc
=> 0x80001b00:	fence	w,unknown
   0x80001b04:	lb	a0,8(s1)
   0x80001b08:	fence	r,rw
   0x80001b0c:	auipc	ra,0x3
   0x80001b10:	jalr	-1912(ra)
   0x80001b14:	zext.b	a0,a0
   0x80001b18:	blez	a0,0x80001b00
   0x80001b1c:	bne	a0,s0,0x80001b26
   0x80001b20:	fence	w,unknown
   0x80001b24:	j	0x80001b04
(gdb)

I infer this problem is caused by dtc submodule is because if we download source code tar file of qemu 7.0.0 on official website, which include all of the component at that time including the full copy of old version dtc, qemu will work as expected. The only difference between the git clone version and .tar file of qemu 7.0.0 is the submodules (including dtc and a building system). I have tried many kinds of platform and it yields the same result.

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.