101153d2bSBin MengSiFive HiFive Unleashed (``sifive_u``) 201153d2bSBin Meng====================================== 301153d2bSBin Meng 401153d2bSBin MengSiFive HiFive Unleashed Development Board is the ultimate RISC-V development 501153d2bSBin Mengboard featuring the Freedom U540 multi-core RISC-V processor. 601153d2bSBin Meng 701153d2bSBin MengSupported devices 801153d2bSBin Meng----------------- 901153d2bSBin Meng 1001153d2bSBin MengThe ``sifive_u`` machine supports the following devices: 1101153d2bSBin Meng 1201153d2bSBin Meng* 1 E51 / E31 core 1301153d2bSBin Meng* Up to 4 U54 / U34 cores 14d3745751SBin Meng* Core Local Interruptor (CLINT) 1501153d2bSBin Meng* Platform-Level Interrupt Controller (PLIC) 1601153d2bSBin Meng* Power, Reset, Clock, Interrupt (PRCI) 1701153d2bSBin Meng* L2 Loosely Integrated Memory (L2-LIM) 1801153d2bSBin Meng* DDR memory controller 1901153d2bSBin Meng* 2 UARTs 2001153d2bSBin Meng* 1 GEM Ethernet controller 2101153d2bSBin Meng* 1 GPIO controller 2201153d2bSBin Meng* 1 One-Time Programmable (OTP) memory with stored serial number 2301153d2bSBin Meng* 1 DMA controller 2401153d2bSBin Meng* 2 QSPI controllers 2501153d2bSBin Meng* 1 ISSI 25WP256 flash 2601153d2bSBin Meng* 1 SD card in SPI mode 27ea6eaa06SAlistair Francis* PWM0 and PWM1 2801153d2bSBin Meng 2901153d2bSBin MengPlease note the real world HiFive Unleashed board has a fixed configuration of 3001153d2bSBin Meng1 E51 core and 4 U54 core combination and the RISC-V core boots in 64-bit mode. 3101153d2bSBin MengWith QEMU, one can create a machine with 1 E51 core and up to 4 U54 cores. It 3201153d2bSBin Mengis also possible to create a 32-bit variant with the same peripherals except 3301153d2bSBin Mengthat the RISC-V cores are replaced by the 32-bit ones (E31 and U34), to help 3401153d2bSBin Mengtesting of 32-bit guest software. 3501153d2bSBin Meng 3601153d2bSBin MengHardware configuration information 3701153d2bSBin Meng---------------------------------- 3801153d2bSBin Meng 3901153d2bSBin MengThe ``sifive_u`` machine automatically generates a device tree blob ("dtb") 400147af69SBin Mengwhich it passes to the guest, if there is no ``-dtb`` option. This provides 410147af69SBin Menginformation about the addresses, interrupt lines and other configuration of 420147af69SBin Mengthe various devices in the system. Guest software should discover the devices 430147af69SBin Mengthat are present in the generated DTB instead of using a DTB for the real 440147af69SBin Menghardware, as some of the devices are not modeled by QEMU and trying to access 450147af69SBin Mengthese devices may cause unexpected behavior. 460147af69SBin Meng 470147af69SBin MengIf users want to provide their own DTB, they can use the ``-dtb`` option. 480147af69SBin MengThese DTBs should have the following requirements: 490147af69SBin Meng 500147af69SBin Meng* The /cpus node should contain at least one subnode for E51 and the number 510147af69SBin Meng of subnodes should match QEMU's ``-smp`` option 520147af69SBin Meng* The /memory reg size should match QEMU’s selected ram_size via ``-m`` 530147af69SBin Meng* Should contain a node for the CLINT device with a compatible string 540147af69SBin Meng "riscv,clint0" if using with OpenSBI BIOS images 5501153d2bSBin Meng 5601153d2bSBin MengBoot options 5701153d2bSBin Meng------------ 5801153d2bSBin Meng 5901153d2bSBin MengThe ``sifive_u`` machine can start using the standard -kernel functionality 6001153d2bSBin Mengfor loading a Linux kernel, a VxWorks kernel, a modified U-Boot bootloader 6101153d2bSBin Meng(S-mode) or ELF executable with the default OpenSBI firmware image as the 6201153d2bSBin Meng-bios. It also supports booting the unmodified U-Boot bootloader using the 6301153d2bSBin Mengstandard -bios functionality. 6401153d2bSBin Meng 6501153d2bSBin MengMachine-specific options 6601153d2bSBin Meng------------------------ 6701153d2bSBin Meng 6801153d2bSBin MengThe following machine-specific options are supported: 6901153d2bSBin Meng 7001153d2bSBin Meng- serial=nnn 7101153d2bSBin Meng 7201153d2bSBin Meng The board serial number. When not given, the default serial number 1 is used. 7301153d2bSBin Meng 7401153d2bSBin Meng SiFive reserves the first 1 KiB of the 16 KiB OTP memory for internal use. 7501153d2bSBin Meng The current usage is only used to store the serial number of the board at 7601153d2bSBin Meng offset 0xfc. U-Boot reads the serial number from the OTP memory, and uses 7701153d2bSBin Meng it to generate a unique MAC address to be programmed to the on-chip GEM 7801153d2bSBin Meng Ethernet controller. When multiple QEMU ``sifive_u`` machines are created 7901153d2bSBin Meng and connected to the same subnet, they all have the same MAC address hence 8001153d2bSBin Meng it creates an unusable network. In such scenario, user should give different 8101153d2bSBin Meng values to serial= when creating different ``sifive_u`` machines. 8201153d2bSBin Meng 8301153d2bSBin Meng- start-in-flash 8401153d2bSBin Meng 8501153d2bSBin Meng When given, QEMU's ROM codes jump to QSPI memory-mapped flash directly. 8601153d2bSBin Meng Otherwise QEMU will jump to DRAM or L2LIM depending on the msel= value. 8701153d2bSBin Meng When not given, it defaults to direct DRAM booting. 8801153d2bSBin Meng 8901153d2bSBin Meng- msel=[6|11] 9001153d2bSBin Meng 9101153d2bSBin Meng Mode Select (MSEL[3:0]) pins value, used to control where to boot from. 9201153d2bSBin Meng 9301153d2bSBin Meng The FU540 SoC supports booting from several sources, which are controlled 9401153d2bSBin Meng using the Mode Select pins on the chip. Typically, the boot process runs 9501153d2bSBin Meng through several stages before it begins execution of user-provided programs. 9601153d2bSBin Meng These stages typically include the following: 9701153d2bSBin Meng 9801153d2bSBin Meng 1. Zeroth Stage Boot Loader (ZSBL), which is contained in an on-chip mask 9901153d2bSBin Meng ROM and provided by QEMU. Note QEMU implemented ROM codes are not the 10001153d2bSBin Meng same as what is programmed in the hardware. The QEMU one is a simplified 10101153d2bSBin Meng version, but it provides the same functionality as the hardware. 10201153d2bSBin Meng 2. First Stage Boot Loader (FSBL), which brings up PLLs and DDR memory. 10301153d2bSBin Meng This is U-Boot SPL. 10401153d2bSBin Meng 3. Second Stage Boot Loader (SSBL), which further initializes additional 10501153d2bSBin Meng peripherals as needed. This is U-Boot proper combined with an OpenSBI 10601153d2bSBin Meng fw_dynamic firmware image. 10701153d2bSBin Meng 10801153d2bSBin Meng msel=6 means FSBL and SSBL are both on the QSPI flash. msel=11 means FSBL 10901153d2bSBin Meng and SSBL are both on the SD card. 11001153d2bSBin Meng 11101153d2bSBin MengRunning Linux kernel 11201153d2bSBin Meng-------------------- 11301153d2bSBin Meng 11401153d2bSBin MengLinux mainline v5.10 release is tested at the time of writing. To build a 11501153d2bSBin MengLinux mainline kernel that can be booted by the ``sifive_u`` machine in 11601153d2bSBin Meng64-bit mode, simply configure the kernel using the defconfig configuration: 11701153d2bSBin Meng 11801153d2bSBin Meng.. code-block:: bash 11901153d2bSBin Meng 12001153d2bSBin Meng $ export ARCH=riscv 12101153d2bSBin Meng $ export CROSS_COMPILE=riscv64-linux- 12201153d2bSBin Meng $ make defconfig 12301153d2bSBin Meng $ make 12401153d2bSBin Meng 12501153d2bSBin MengTo boot the newly built Linux kernel in QEMU with the ``sifive_u`` machine: 12601153d2bSBin Meng 12701153d2bSBin Meng.. code-block:: bash 12801153d2bSBin Meng 12901153d2bSBin Meng $ qemu-system-riscv64 -M sifive_u -smp 5 -m 2G \ 13001153d2bSBin Meng -display none -serial stdio \ 13101153d2bSBin Meng -kernel arch/riscv/boot/Image \ 13201153d2bSBin Meng -initrd /path/to/rootfs.ext4 \ 13301153d2bSBin Meng -append "root=/dev/ram" 13401153d2bSBin Meng 1350147af69SBin MengAlternatively, we can use a custom DTB to boot the machine by inserting a CLINT 1360147af69SBin Mengnode in fu540-c000.dtsi in the Linux kernel, 1370147af69SBin Meng 1380147af69SBin Meng.. code-block:: none 1390147af69SBin Meng 1400147af69SBin Meng clint: clint@2000000 { 1410147af69SBin Meng compatible = "riscv,clint0"; 1420147af69SBin Meng interrupts-extended = <&cpu0_intc 3 &cpu0_intc 7 1430147af69SBin Meng &cpu1_intc 3 &cpu1_intc 7 1440147af69SBin Meng &cpu2_intc 3 &cpu2_intc 7 1450147af69SBin Meng &cpu3_intc 3 &cpu3_intc 7 1460147af69SBin Meng &cpu4_intc 3 &cpu4_intc 7>; 1470147af69SBin Meng reg = <0x00 0x2000000 0x00 0x10000>; 1480147af69SBin Meng }; 1490147af69SBin Meng 1500147af69SBin Mengwith the following command line options: 1510147af69SBin Meng 1520147af69SBin Meng.. code-block:: bash 1530147af69SBin Meng 1540147af69SBin Meng $ qemu-system-riscv64 -M sifive_u -smp 5 -m 8G \ 1550147af69SBin Meng -display none -serial stdio \ 1560147af69SBin Meng -kernel arch/riscv/boot/Image \ 1570147af69SBin Meng -dtb arch/riscv/boot/dts/sifive/hifive-unleashed-a00.dtb \ 1580147af69SBin Meng -initrd /path/to/rootfs.ext4 \ 1590147af69SBin Meng -append "root=/dev/ram" 1600147af69SBin Meng 16101153d2bSBin MengTo build a Linux mainline kernel that can be booted by the ``sifive_u`` machine 16201153d2bSBin Mengin 32-bit mode, use the rv32_defconfig configuration. A patch is required to 16301153d2bSBin Mengfix the 32-bit boot issue for Linux kernel v5.10. 16401153d2bSBin Meng 16501153d2bSBin Meng.. code-block:: bash 16601153d2bSBin Meng 16701153d2bSBin Meng $ export ARCH=riscv 16801153d2bSBin Meng $ export CROSS_COMPILE=riscv64-linux- 16901153d2bSBin Meng $ curl https://patchwork.kernel.org/project/linux-riscv/patch/20201219001356.2887782-1-atish.patra@wdc.com/mbox/ > riscv.patch 17001153d2bSBin Meng $ git am riscv.patch 17101153d2bSBin Meng $ make rv32_defconfig 17201153d2bSBin Meng $ make 17301153d2bSBin Meng 17401153d2bSBin MengReplace ``qemu-system-riscv64`` with ``qemu-system-riscv32`` in the command 17501153d2bSBin Mengline above to boot the 32-bit Linux kernel. A rootfs image containing 32-bit 17601153d2bSBin Mengapplications shall be used in order for kernel to boot to user space. 17701153d2bSBin Meng 17801153d2bSBin MengRunning VxWorks kernel 17901153d2bSBin Meng---------------------- 18001153d2bSBin Meng 18101153d2bSBin MengVxWorks 7 SR0650 release is tested at the time of writing. To build a 64-bit 18201153d2bSBin MengVxWorks mainline kernel that can be booted by the ``sifive_u`` machine, simply 18301153d2bSBin Mengcreate a VxWorks source build project based on the sifive_generic BSP, and a 18401153d2bSBin MengVxWorks image project to generate the bootable VxWorks image, by following the 18501153d2bSBin MengBSP documentation instructions. 18601153d2bSBin Meng 18701153d2bSBin MengA pre-built 64-bit VxWorks 7 image for HiFive Unleashed board is available as 18801153d2bSBin Mengpart of the VxWorks SDK for testing as well. Instructions to download the SDK: 18901153d2bSBin Meng 19001153d2bSBin Meng.. code-block:: bash 19101153d2bSBin Meng 19201153d2bSBin Meng $ wget https://labs.windriver.com/downloads/wrsdk-vxworks7-sifive-hifive-1.01.tar.bz2 19301153d2bSBin Meng $ tar xvf wrsdk-vxworks7-sifive-hifive-1.01.tar.bz2 19401153d2bSBin Meng $ ls bsps/sifive_generic_1_0_0_0/uboot/uVxWorks 19501153d2bSBin Meng 19601153d2bSBin MengTo boot the VxWorks kernel in QEMU with the ``sifive_u`` machine, use: 19701153d2bSBin Meng 19801153d2bSBin Meng.. code-block:: bash 19901153d2bSBin Meng 20001153d2bSBin Meng $ qemu-system-riscv64 -M sifive_u -smp 5 -m 2G \ 20101153d2bSBin Meng -display none -serial stdio \ 20201153d2bSBin Meng -nic tap,ifname=tap0,script=no,downscript=no \ 20301153d2bSBin Meng -kernel /path/to/vxWorks \ 20401153d2bSBin Meng -append "gem(0,0)host:vxWorks h=192.168.200.1 e=192.168.200.2:ffffff00 u=target pw=vxTarget f=0x01" 20501153d2bSBin Meng 20601153d2bSBin MengIt is also possible to test 32-bit VxWorks on the ``sifive_u`` machine. Create 20701153d2bSBin Menga 32-bit project to build the 32-bit VxWorks image, and use exact the same 20801153d2bSBin Mengcommand line options with ``qemu-system-riscv32``. 20901153d2bSBin Meng 21001153d2bSBin MengRunning U-Boot 21101153d2bSBin Meng-------------- 21201153d2bSBin Meng 213*e0299f71SBin MengU-Boot mainline v2024.01 release is tested at the time of writing. To build a 21401153d2bSBin MengU-Boot mainline bootloader that can be booted by the ``sifive_u`` machine, use 215758c07c9SBin Mengthe sifive_unleashed_defconfig with similar commands as described above for 216758c07c9SBin MengLinux: 21701153d2bSBin Meng 21801153d2bSBin Meng.. code-block:: bash 21901153d2bSBin Meng 22001153d2bSBin Meng $ export CROSS_COMPILE=riscv64-linux- 22101153d2bSBin Meng $ export OPENSBI=/path/to/opensbi-riscv64-generic-fw_dynamic.bin 222758c07c9SBin Meng $ make sifive_unleashed_defconfig 22301153d2bSBin Meng 22401153d2bSBin MengYou will get spl/u-boot-spl.bin and u-boot.itb file in the build tree. 22501153d2bSBin Meng 22601153d2bSBin MengTo start U-Boot using the ``sifive_u`` machine, prepare an SPI flash image, or 22701153d2bSBin MengSD card image that is properly partitioned and populated with correct contents. 22801153d2bSBin Menggenimage_ can be used to generate these images. 22901153d2bSBin Meng 23001153d2bSBin MengA sample configuration file for a 128 MiB SD card image is: 23101153d2bSBin Meng 23201153d2bSBin Meng.. code-block:: bash 23301153d2bSBin Meng 23401153d2bSBin Meng $ cat genimage_sdcard.cfg 23501153d2bSBin Meng image sdcard.img { 23601153d2bSBin Meng size = 128M 23701153d2bSBin Meng 23801153d2bSBin Meng hdimage { 23901153d2bSBin Meng gpt = true 24001153d2bSBin Meng } 24101153d2bSBin Meng 24201153d2bSBin Meng partition u-boot-spl { 24301153d2bSBin Meng image = "u-boot-spl.bin" 24401153d2bSBin Meng offset = 17K 24501153d2bSBin Meng partition-type-uuid = 5B193300-FC78-40CD-8002-E86C45580B47 24601153d2bSBin Meng } 24701153d2bSBin Meng 24801153d2bSBin Meng partition u-boot { 24901153d2bSBin Meng image = "u-boot.itb" 25001153d2bSBin Meng offset = 1041K 25101153d2bSBin Meng partition-type-uuid = 2E54B353-1271-4842-806F-E436D6AF6985 25201153d2bSBin Meng } 25301153d2bSBin Meng } 25401153d2bSBin Meng 25501153d2bSBin MengSPI flash image has slightly different partition offsets, and the size has to 25601153d2bSBin Mengbe 32 MiB to match the ISSI 25WP256 flash on the real board: 25701153d2bSBin Meng 25801153d2bSBin Meng.. code-block:: bash 25901153d2bSBin Meng 26001153d2bSBin Meng $ cat genimage_spi-nor.cfg 26101153d2bSBin Meng image spi-nor.img { 26201153d2bSBin Meng size = 32M 26301153d2bSBin Meng 26401153d2bSBin Meng hdimage { 26501153d2bSBin Meng gpt = true 26601153d2bSBin Meng } 26701153d2bSBin Meng 26801153d2bSBin Meng partition u-boot-spl { 26901153d2bSBin Meng image = "u-boot-spl.bin" 27001153d2bSBin Meng offset = 20K 27101153d2bSBin Meng partition-type-uuid = 5B193300-FC78-40CD-8002-E86C45580B47 27201153d2bSBin Meng } 27301153d2bSBin Meng 27401153d2bSBin Meng partition u-boot { 27501153d2bSBin Meng image = "u-boot.itb" 27601153d2bSBin Meng offset = 1044K 27701153d2bSBin Meng partition-type-uuid = 2E54B353-1271-4842-806F-E436D6AF6985 27801153d2bSBin Meng } 27901153d2bSBin Meng } 28001153d2bSBin Meng 28101153d2bSBin MengAssume U-Boot binaries are put in the same directory as the config file, 28201153d2bSBin Mengwe can generate the image by: 28301153d2bSBin Meng 28401153d2bSBin Meng.. code-block:: bash 28501153d2bSBin Meng 28601153d2bSBin Meng $ genimage --config genimage_<boot_src>.cfg --inputpath . 28701153d2bSBin Meng 28801153d2bSBin MengBoot U-Boot from SD card, by specifying msel=11 and pass the SD card image 28901153d2bSBin Mengto QEMU ``sifive_u`` machine: 29001153d2bSBin Meng 29101153d2bSBin Meng.. code-block:: bash 29201153d2bSBin Meng 29301153d2bSBin Meng $ qemu-system-riscv64 -M sifive_u,msel=11 -smp 5 -m 8G \ 29401153d2bSBin Meng -display none -serial stdio \ 29501153d2bSBin Meng -bios /path/to/u-boot-spl.bin \ 29601153d2bSBin Meng -drive file=/path/to/sdcard.img,if=sd 29701153d2bSBin Meng 29801153d2bSBin MengChanging msel= value to 6, allows booting U-Boot from the SPI flash: 29901153d2bSBin Meng 30001153d2bSBin Meng.. code-block:: bash 30101153d2bSBin Meng 30201153d2bSBin Meng $ qemu-system-riscv64 -M sifive_u,msel=6 -smp 5 -m 8G \ 30301153d2bSBin Meng -display none -serial stdio \ 30401153d2bSBin Meng -bios /path/to/u-boot-spl.bin \ 30501153d2bSBin Meng -drive file=/path/to/spi-nor.img,if=mtd 30601153d2bSBin Meng 30701153d2bSBin MengNote when testing U-Boot, QEMU automatically generated device tree blob is 30801153d2bSBin Mengnot used because U-Boot itself embeds device tree blobs for U-Boot SPL and 30901153d2bSBin MengU-Boot proper. Hence the number of cores and size of memory have to match 31001153d2bSBin Mengthe real hardware, ie: 5 cores (-smp 5) and 8 GiB memory (-m 8G). 31101153d2bSBin Meng 31201153d2bSBin MengAbove use case is to run upstream U-Boot for the SiFive HiFive Unleashed 31301153d2bSBin Mengboard on QEMU ``sifive_u`` machine out of the box. This allows users to 31401153d2bSBin Mengdevelop and test the recommended RISC-V boot flow with a real world use 31501153d2bSBin Mengcase: ZSBL (in QEMU) loads U-Boot SPL from SD card or SPI flash to L2LIM, 31601153d2bSBin Mengthen U-Boot SPL loads the combined payload image of OpenSBI fw_dynamic 317758c07c9SBin Mengfirmware and U-Boot proper. 318758c07c9SBin Meng 319758c07c9SBin MengHowever sometimes we want to have a quick test of booting U-Boot on QEMU 320758c07c9SBin Mengwithout the needs of preparing the SPI flash or SD card images, an alternate 321758c07c9SBin Mengway can be used, which is to create a U-Boot S-mode image by modifying the 322758c07c9SBin Mengconfiguration of U-Boot: 32301153d2bSBin Meng 32401153d2bSBin Meng.. code-block:: bash 32501153d2bSBin Meng 326758c07c9SBin Meng $ export CROSS_COMPILE=riscv64-linux- 327758c07c9SBin Meng $ make sifive_unleashed_defconfig 328*e0299f71SBin Meng $ ./scripts/config --enable OF_BOARD 329*e0299f71SBin Meng $ ./scripts/config --disable BINMAN_FDT 330*e0299f71SBin Meng $ ./scripts/config --disable SPL 331*e0299f71SBin Meng $ make olddefconfig 33201153d2bSBin Meng 333758c07c9SBin MengThis changes U-Boot to use the QEMU generated device tree blob, and bypass 334758c07c9SBin Mengrunning the U-Boot SPL stage. 33501153d2bSBin Meng 33601153d2bSBin MengBoot the 64-bit U-Boot S-mode image directly: 33701153d2bSBin Meng 33801153d2bSBin Meng.. code-block:: bash 33901153d2bSBin Meng 34001153d2bSBin Meng $ qemu-system-riscv64 -M sifive_u -smp 5 -m 2G \ 34101153d2bSBin Meng -display none -serial stdio \ 34201153d2bSBin Meng -kernel /path/to/u-boot.bin 34301153d2bSBin Meng 34401153d2bSBin MengIt's possible to create a 32-bit U-Boot S-mode image as well. 34501153d2bSBin Meng 34601153d2bSBin Meng.. code-block:: bash 34701153d2bSBin Meng 34801153d2bSBin Meng $ export CROSS_COMPILE=riscv64-linux- 349758c07c9SBin Meng $ make sifive_unleashed_defconfig 350*e0299f71SBin Meng $ ./scripts/config --disable ARCH_RV64I 351*e0299f71SBin Meng $ ./scripts/config --enable ARCH_RV32I 352*e0299f71SBin Meng $ ./scripts/config --set-val TEXT_BASE 0x80400000 353*e0299f71SBin Meng $ ./scripts/config --enable OF_BOARD 354*e0299f71SBin Meng $ ./scripts/config --disable BINMAN_FDT 355*e0299f71SBin Meng $ ./scripts/config --disable SPL 356*e0299f71SBin Meng $ make olddefconfig 35701153d2bSBin Meng 35801153d2bSBin MengUse the same command line options to boot the 32-bit U-Boot S-mode image: 35901153d2bSBin Meng 36001153d2bSBin Meng.. code-block:: bash 36101153d2bSBin Meng 36201153d2bSBin Meng $ qemu-system-riscv32 -M sifive_u -smp 5 -m 2G \ 36301153d2bSBin Meng -display none -serial stdio \ 36401153d2bSBin Meng -kernel /path/to/u-boot.bin 36501153d2bSBin Meng 36601153d2bSBin Meng.. _genimage: https://github.com/pengutronix/genimage 367