Show HN: Run xv6-riscv(64Bit,MMU) with RP2350
I have successfully run a 64-bit version of xv6-riscv—which includes an MMU—on the Raspberry Pi Pico 2W.
No PSRAM is attached.
I built a software emulator and ran it on the Hazard3 core.
(It should likely also run on the Cortex core.)
2 points
Running xv6-riscv64 on RaspberryPi Pico2 (Software Emulator)
Hello everyone,
I built a software emulator on RP2350 and succeeded in starting 64bit xv6 with almost no modification.
Demo:
Booting demo
In order to run with the limited RAM of 520KB, we adopted an interpreter method. (I would like to do JIT someday, but caching is a problem.)
It will reach the Shell in about 1 minute.
The changes for xv6 are PHYSTOP, umalloc.c (64KB to 4KB) and memlayout.h.
Works with MMU.
Please give me your opinions and impressions.
Github:
kamisori-daijin/pico-rv64-emu
xv6 fork: kamisori-daijin/xv6-riscv
1 point · 10 comments
RP2350でRV64のソフトウエアエミュレーターを動かし、64bitのxv6をほぼ無改造で動かした件
動いてしまった
xv6-riscv64がほとんど無改造でRP2350上で動いた。
ちなみにPSRAMなしです。無改造のRaspberry Pi Pico 2wです。
デモ:
xv6-fork: kamisori-daijin/xv6-riscv
Emulator: kamisori-daijin/pico-rv64-emu
動くこと
lsとcatの動作は確認しています。
usertestsはメモリ不足で動かずと言ったところです。
xv6の変更箇所
param.hと、memlayout.hと、umalloc.cを変更しました。
xv6のプロセス数などの減量と、PHYSTOPを縮小し、一度に確保されるRAMの単位を64KBから4KBに削りました。
Emulatorについて
Geminiに書かせました。
一命令ずつFetchするインタープリター方式で、メモリは520KB以内に収まります。
欲望:PSRAMを載せればusertestできるのになー
そして、ログを消したらUARTが早すぎて文字化けし、ウェイトを入れたら今度はOSがフリーズしました。
UARTの割込み調整や、TXピンの調整で苦戦しました。
肝心の速度
約1分ぐらいでShellに到達すると言った感じです。
早いのか遅いのかよくわかりませんが(多分遅い)64BitのOSをエミュレーションしてる割には速いような気もします。
展望
いつかPSRAMを追加して、画面出力もできるようにしたいと思います。
まとめ
省メモリで64bitのOSが動くことを検証できたのは非常に良かったです。
皆さんのご意見、ご意見をお寄せください。
Booting xv6-riscv64 on a Raspberry Pi Pico 2 (RP2350) with Software Emulator!
Hello everyone!
I have ported xv6-riscv64 to the RP2350 (Raspberry Pi Pico 2)!
The system boots completely, reaching the init process and launching the shshell. Interactive shell utilities like ls run smoothly via the UART console, with no stalls or memory panics.
I have managed to run a 64-bit OS on the RP2350, which features 520 KB of SRAM.
Demo:
reddit.com
Architecture and Features
- CPU Emulation: Supports RV64I + RV64C (compressed instructions) + RV64M (multiplication/division instructions), with full support for Machine (M), Supervisor (S), and User (U) modes.
- Sv39 MMU: Fully implements three-level page table translation, including access permission checks (PTE_R, PTE_W, PTE_X, PTE_U).
- RAM Allocation: 416 KB is reserved for the guest OS; the remaining SRAM is used for the emulator runtime, stack, and sector cache.
Peripherals:
16550 UART: Emulates RX/TX interrupts (including IER/LSR status handling) and connects to the Pico’s USB CDC/serial functionality.
- CLINT & PLIC: Manages timers and external interrupts for process scheduling and device I/O.
- VirtIO Block Device: Emulates disk I/O using a 128-sector cache in memory.
Key Technical Challenges and Solutions
Overcoming the 416 KB RAM Limit (Addressing OOM):
In the default umalloc.c for xv6, the morecore() function is designed to request 64 KB (4096 units) of memory each time it is called.
In a guest environment with only 416 KB of memory, executing fork() followed by exec("ls") would immediately exhaust available memory, resulting in a NULL return value and a "Store Page Fault" at address 0x0. By adjusting the morecore() allocation unit to 4 KB (256 units per page), the memory exhaustion issue was completely resolved.
The code is available on GitHub: kamisori-daijin/pico-rv64-emu
xv6 fork: kamisori-daijin/xv6-riscv
I would love to hear your thoughts, feedback, or any ideas for further optimizations!
1 point · 10 comments
Booting xv6-riscv64 on a Raspberry Pi Pico 2 (RP2350) with Software Emulator!
Hello everyone!
I have ported xv6-riscv64 to the RP2350 (Raspberry Pi Pico 2)!
The system boots completely, reaching the init process and launching the shshell. Interactive shell utilities like ls run smoothly via the UART console, with no stalls or memory panics.
I have managed to run a 64-bit OS on the RP2350, which features 520 KB of SRAM.
Demo:
reddit.com
Architecture and Features
- CPU Emulation: Supports RV64I + RV64C (compressed instructions) + RV64M (multiplication/division instructions), with full support for Machine (M), Supervisor (S), and User (U) modes.
- Sv39 MMU: Fully implements three-level page table translation, including access permission checks (PTE_R, PTE_W, PTE_X, PTE_U).
- RAM Allocation: 416 KB is reserved for the guest OS; the remaining SRAM is used for the emulator runtime, stack, and sector cache.
Peripherals:
16550 UART: Emulates RX/TX interrupts (including IER/LSR status handling) and connects to the Pico’s USB CDC/serial functionality.
- CLINT & PLIC: Manages timers and external interrupts for process scheduling and device I/O.
- VirtIO Block Device: Emulates disk I/O using a 128-sector cache in memory.
Key Technical Challenges and Solutions
Overcoming the 416 KB RAM Limit (Addressing OOM):
In the default umalloc.c for xv6, the morecore() function is designed to request 64 KB (4096 units) of memory each time it is called.
In a guest environment with only 416 KB of memory, executing fork() followed by exec("ls") would immediately exhaust available memory, resulting in a NULL return value and a "Store Page Fault" at address 0x0. By adjusting the morecore() allocation unit to 4 KB (256 units per page), the memory exhaustion issue was completely resolved.
The code is available on GitHub: kamisori-daijin/pico-rv64-emu
xv6 fork: kamisori-daijin/xv6-riscv
I would love to hear your thoughts, feedback, or any ideas for further optimizations!
7 points
Booting xv6-riscv64 on a Raspberry Pi Pico 2 (RP2350) with Software Emulator!
Hello everyone!
I have ported xv6-riscv64 to the RP2350 (Raspberry Pi Pico 2)!
The system boots completely, reaching the init process and launching the shshell. Interactive shell utilities like ls run smoothly via the UART console, with no stalls or memory panics.
I have managed to run a 64-bit OS on the RP2350, which features 520 KB of SRAM.
demo:
demo boot
Architecture and Features
- CPU Emulation: Supports RV64I + RV64C (compressed instructions) + RV64M (multiplication/division instructions), with full support for Machine (M), Supervisor (S), and User (U) modes.
- Sv39 MMU: Fully implements three-level page table translation, including access permission checks (PTE_R, PTE_W, PTE_X, PTE_U).
- RAM Allocation: 416 KB is reserved for the guest OS; the remaining SRAM is used for the emulator runtime, stack, and sector cache.
Peripherals:
16550 UART: Emulates RX/TX interrupts (including IER/LSR status handling) and connects to the Pico’s USB CDC/serial functionality.
- CLINT & PLIC: Manages timers and external interrupts for process scheduling and device I/O.
- VirtIO Block Device: Emulates disk I/O using a 128-sector cache in memory.
Key Technical Challenges and Solutions
Overcoming the 416 KB RAM Limit (Addressing OOM):
In the default umalloc.c for xv6, the morecore() function is designed to request 64 KB (4096 units) of memory each time it is called.
In a guest environment with only 416 KB of memory, executing fork() followed by exec("ls") would immediately exhaust available memory, resulting in a NULL return value and a "Store Page Fault" at address 0x0. By adjusting the morecore() allocation unit to 4 KB (256 units per page), the memory exhaustion issue was completely resolved.
The code is available on GitHub: kamisori-daijin/pico-rv64-emu
xv6 fork: kamisori-daijin/xv6-riscv
I would love to hear your thoughts, feedback, or any ideas for further optimizations!
7 points · 3 comments
Mentions
Show HN: Run xv6-riscv(64Bit,MMU) with RP2350 I have successfully run a 64-bit version of xv6-riscv—which includes an MMU—on the Raspberry Pi Pico 2W. No PSRAM is attached. I built a software emulator and ran it on the Hazard3 core. (It should likely also run on the Cortex core.)
Running xv6-riscv64 on RaspberryPi Pico2 (Software Emulator) Hello everyone, I built a software emulator on RP2350 and succeeded in starting 64bit xv6 with almost no modification. Demo: Booting demo In order to run with the limited RAM of 520KB, we adopted an interpreter method. (I would like to do JIT someday, but caching is a problem.) It will reach the Shell in about 1 minute. The changes for xv6 are PHYSTOP, umalloc.c (64KB to 4KB) and memlayout.h. Works with MMU. Please give me your opinions and impressions. Github: kamisori-daijin/pico-rv64-emu xv6 fork: kamisori-daijin/xv6-riscv
RP2350でRV64のソフトウエアエミュレーターを動かし、64bitのxv6をほぼ無改造で動かした件 動いてしまった xv6-riscv64がほとんど無改造でRP2350上で動いた。 ちなみにPSRAMなしです。無改造のRaspberry Pi Pico 2wです。 デモ: xv6-fork: kamisori-daijin/xv6-riscv Emulator: kamisori-daijin/pico-rv64-emu 動くこと lsとcatの動作は確認しています。 usertestsはメモリ不足で動かずと言ったところです。 xv6の変更箇所 param.hと、memlayout.hと、umalloc.cを変更しました。 xv6のプロセス数などの減量と、PHYSTOPを縮小し、一度に確保されるRAMの単位を64KBから4KBに削りました。 Emulatorについて Geminiに書かせました。 一命令ずつFetchするインタープリター方式で、メモリは520KB以内に収まります。 欲望:PSRAMを載せればusertestできるのになー そして、ログを消したらUARTが早すぎて文字化けし、ウェイトを入れたら今度はOSがフリーズしました。 UARTの割込み調整や、TXピンの調整で苦戦しました。 肝心の速度 約1分ぐらいでShellに到達すると言った感じです。 早いのか遅いのかよくわかりませんが(多分遅い)64BitのOSをエミュレーションしてる割には速いような気もします。 展望 いつかPSRAMを追加して、画面出力もできるようにしたいと思います。 まとめ 省メモリで64bitのOSが動くことを検証できたのは非常に良かったです。 皆さんのご意見、ご意見をお寄せください。
Booting xv6-riscv64 on a Raspberry Pi Pico 2 (RP2350) with Software Emulator! Hello everyone! I have ported xv6-riscv64 to the RP2350 (Raspberry Pi Pico 2)! The system boots completely, reaching the init process and launching the shshell. Interactive shell utilities like ls run smoothly via the UART console, with no stalls or memory panics. I have managed to run a 64-bit OS on the RP2350, which features 520 KB of SRAM. Demo: reddit.com Architecture and Features - CPU Emulation: Supports RV64I + RV64C (compressed instructions) + RV64M (multiplication/division instructions), with full support for Machine (M), Supervisor (S), and User (U) modes. - Sv39 MMU: Fully implements three-level page table translation, including access permission checks (PTE_R, PTE_W, PTE_X, PTE_U). - RAM Allocation: 416 KB is reserved for the guest OS; the remaining SRAM is used for the emulator runtime, stack, and sector cache. Peripherals: 16550 UART: Emulates RX/TX interrupts (including IER/LSR status handling) and connects to the Pico’s USB CDC/serial functionality. - CLINT & PLIC: Manages timers and external interrupts for process scheduling and device I/O. - VirtIO Block Device: Emulates disk I/O using a 128-sector cache in memory. Key Technical Challenges and Solutions Overcoming the 416 KB RAM Limit (Addressing OOM): In the default umalloc.c for xv6, the morecore() function is designed to request 64 KB (4096 units) of memory each time it is called. In a guest environment with only 416 KB of memory, executing fork() followed by exec("ls") would immediately exhaust available memory, resulting in a NULL return value and a "Store Page Fault" at address 0x0. By adjusting the morecore() allocation unit to 4 KB (256 units per page), the memory exhaustion issue was completely resolved. The code is available on GitHub: kamisori-daijin/pico-rv64-emu xv6 fork: kamisori-daijin/xv6-riscv I would love to hear your thoughts, feedback, or any ideas for further optimizations!
Booting xv6-riscv64 on a Raspberry Pi Pico 2 (RP2350) with Software Emulator! Hello everyone! I have ported xv6-riscv64 to the RP2350 (Raspberry Pi Pico 2)! The system boots completely, reaching the init process and launching the shshell. Interactive shell utilities like ls run smoothly via the UART console, with no stalls or memory panics. I have managed to run a 64-bit OS on the RP2350, which features 520 KB of SRAM. Demo: reddit.com Architecture and Features - CPU Emulation: Supports RV64I + RV64C (compressed instructions) + RV64M (multiplication/division instructions), with full support for Machine (M), Supervisor (S), and User (U) modes. - Sv39 MMU: Fully implements three-level page table translation, including access permission checks (PTE_R, PTE_W, PTE_X, PTE_U). - RAM Allocation: 416 KB is reserved for the guest OS; the remaining SRAM is used for the emulator runtime, stack, and sector cache. Peripherals: 16550 UART: Emulates RX/TX interrupts (including IER/LSR status handling) and connects to the Pico’s USB CDC/serial functionality. - CLINT & PLIC: Manages timers and external interrupts for process scheduling and device I/O. - VirtIO Block Device: Emulates disk I/O using a 128-sector cache in memory. Key Technical Challenges and Solutions Overcoming the 416 KB RAM Limit (Addressing OOM): In the default umalloc.c for xv6, the morecore() function is designed to request 64 KB (4096 units) of memory each time it is called. In a guest environment with only 416 KB of memory, executing fork() followed by exec("ls") would immediately exhaust available memory, resulting in a NULL return value and a "Store Page Fault" at address 0x0. By adjusting the morecore() allocation unit to 4 KB (256 units per page), the memory exhaustion issue was completely resolved. The code is available on GitHub: kamisori-daijin/pico-rv64-emu xv6 fork: kamisori-daijin/xv6-riscv I would love to hear your thoughts, feedback, or any ideas for further optimizations!
Booting xv6-riscv64 on a Raspberry Pi Pico 2 (RP2350) with Software Emulator! Hello everyone! I have ported xv6-riscv64 to the RP2350 (Raspberry Pi Pico 2)! The system boots completely, reaching the init process and launching the shshell. Interactive shell utilities like ls run smoothly via the UART console, with no stalls or memory panics. I have managed to run a 64-bit OS on the RP2350, which features 520 KB of SRAM. demo: demo boot Architecture and Features - CPU Emulation: Supports RV64I + RV64C (compressed instructions) + RV64M (multiplication/division instructions), with full support for Machine (M), Supervisor (S), and User (U) modes. - Sv39 MMU: Fully implements three-level page table translation, including access permission checks (PTE_R, PTE_W, PTE_X, PTE_U). - RAM Allocation: 416 KB is reserved for the guest OS; the remaining SRAM is used for the emulator runtime, stack, and sector cache. Peripherals: 16550 UART: Emulates RX/TX interrupts (including IER/LSR status handling) and connects to the Pico’s USB CDC/serial functionality. - CLINT & PLIC: Manages timers and external interrupts for process scheduling and device I/O. - VirtIO Block Device: Emulates disk I/O using a 128-sector cache in memory. Key Technical Challenges and Solutions Overcoming the 416 KB RAM Limit (Addressing OOM): In the default umalloc.c for xv6, the morecore() function is designed to request 64 KB (4096 units) of memory each time it is called. In a guest environment with only 416 KB of memory, executing fork() followed by exec("ls") would immediately exhaust available memory, resulting in a NULL return value and a "Store Page Fault" at address 0x0. By adjusting the morecore() allocation unit to 4 KB (256 units per page), the memory exhaustion issue was completely resolved. The code is available on GitHub: kamisori-daijin/pico-rv64-emu xv6 fork: kamisori-daijin/xv6-riscv I would love to hear your thoughts, feedback, or any ideas for further optimizations!