xref: /qemu/docs/system/riscv/sifive_u.rst (revision 34eac35f893664eb8545b98142e23d9954722766)
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