@@ -1984,28 +1984,50 @@ qemu-system-aarch64 -M raspi3b -m 1024 -serial stdio -kernel wolfboot_linux_rasp
19841984
19851985## Xilinx Zynq UltraScale
19861986
1987- Xilinx UltraScale+ ZCU102 (Aarch64)
1987+ AMD Zynq UltraScale+ MPSoC ZCU102 Evaluation Kit - Quad-core ARM Cortex-A53 (plus dual Cortex-R5).
19881988
1989- See example .config file at ` config/examples/zynqmp.config ` .
1990-
1991- Example build options (.config):
1989+ wolfBoot replaces U-Boot in the ZynqMP boot flow:
19921990```
1993- TARGET=zynq
1994- ARCH=AARCH64
1995- SIGN=RSA4096
1996- HASH=SHA3
1991+ FSBL -> PMUFW -> BL31 (EL3) -> wolfBoot (EL2) -> Linux (EL1)
19971992```
19981993
1999- ### Building Zynq with Xilinx tools (Vitis IDE)
1994+ wolfBoot runs from DDR at ` 0x8000000 ` (128MB, EL2, non-secure) for both QSPI and SD card boot. All clock, MIO, and DDR initialization is handled by the FSBL/PMUFW before wolfBoot starts.
1995+
1996+ This target supports ** two boot paths** :
1997+ - ** QSPI boot** (primary, production-style): ` config/examples/zynqmp.config `
1998+ - ** SD card boot** (MBR, A/B images): ` config/examples/zynqmp_sdcard.config `
1999+
2000+ ### Prerequisites
2001+
2002+ 1 . ** Xilinx Vitis 2024.1 or newer**
2003+ - Set ` VITIS_PATH ` environment variable: ` export VITIS_PATH=/opt/Xilinx/Vitis/2024.1 `
2004+ 2 . ** Toolchain** : ` aarch64-none-elf-gcc `
2005+ 3 . ** Pre-built firmware** (FSBL, PMUFW, BL31):
2006+ ``` sh
2007+ git clone --branch xlnx_rel_v2024.2 https://github.com/Xilinx/soc-prebuilt-firmware.git
2008+ export PREBUILT_DIR=$( pwd) /../soc-prebuilt-firmware/zcu102-zynqmp
2009+ ```
2010+
2011+ ### Configuration Options
2012+
2013+ Key configuration options:
2014+
2015+ - ` ARCH=AARCH64 ` - ARM 64-bit architecture
2016+ - ` TARGET=zynq ` - ZynqMP platform target
2017+ - ` SIGN=RSA4096 ` - RSA 4096-bit signatures
2018+ - ` HASH=SHA3 ` - SHA3-384 hashing
2019+ - ` ELF=1 ` - ELF loading support
2020+
2021+ ### Building with Xilinx tools (Vitis IDE)
20002022
20012023See [ IDE/XilinxSDK/README.md] ( /IDE/XilinxSDK/README.md ) for using Xilinx IDE
20022024
2003- ### Building Zynq with gcc-aarch64-linux-gnu
2025+ ### Building with gcc-aarch64-linux-gnu
20042026
20052027Requires ` gcc-aarch64-linux-gnu ` package.
20062028Use ` make CROSS_COMPILE=aarch64-linux-gnu- `
20072029
2008- ### Building Zynq with QNX
2030+ ### Building with QNX
20092031
20102032``` sh
20112033source ~ /qnx700/qnxsdp-env.sh
@@ -2014,17 +2036,197 @@ make clean
20142036make CROSS_COMPILE=aarch64-unknown-nto-qnx7.0.0-
20152037```
20162038
2017- #### Testing Zynq with QEMU
2039+ ### QSPI Boot (default)
2040+
2041+ Use ` config/examples/zynqmp.config ` .
2042+
2043+ ``` sh
2044+ cp config/examples/zynqmp.config .config
2045+ make clean
2046+ make
2047+ ```
2048+
2049+ ** QSPI layout**
2050+ | Partition | Size | Address | Description |
2051+ | -------------| --------| -------------| --------------------------------|
2052+ | Bootloader | - | 0x8000000 | wolfBoot in DDR (loaded by FSBL) |
2053+ | Primary | 42MB | 0x800000 | Boot partition in QSPI |
2054+ | Update | 42MB | 0x3A00000 | Update partition in QSPI |
2055+ | Swap | - | 0x63E0000 | Swap area in QSPI |
2056+
2057+ ** Build BOOT.BIN for QSPI**
2058+
2059+ See [ IDE/XilinxSDK/README.md] ( /IDE/XilinxSDK/README.md ) for creating BOOT.BIN with the Xilinx IDE, or use the existing BIF file:
2060+
2061+ ``` sh
2062+ cp ${PREBUILT_DIR} /zynqmp_fsbl.elf .
2063+ cp ${PREBUILT_DIR} /pmufw.elf .
2064+ cp ${PREBUILT_DIR} /bl31.elf .
2065+
2066+ source ${VITIS_PATH} /settings64.sh
2067+ bootgen -arch zynqmp -image ./IDE/XilinxSDK/boot.bif -w -o BOOT.BIN
2068+ ```
2069+
2070+ ** Signing**
20182071
2072+ ``` sh
2073+ tools/keytools/sign --rsa4096 --sha3 /path/to/vmlinux.bin wolfboot_signing_private_key.der 1
20192074```
2075+
2076+ ** Testing with QEMU**
2077+
2078+ ``` sh
20202079qemu-system-aarch64 -machine xlnx-zcu102 -cpu cortex-a53 -serial stdio -display none \
20212080 -device loader,file=wolfboot.bin,cpu-num=0
2081+ ```
20222082
2083+ ### SD Card Boot (MBR + A/B)
2084+
2085+ Use ` config/examples/zynqmp_sdcard.config ` . This uses the Arasan SDHCI controller (SD1 - external SD card slot on ZCU102) and an ** MBR** partitioned SD card.
2086+
2087+ ** Partition layout**
2088+ | Partition | Name | Size | Type | Contents |
2089+ | -----------| --------| -----------| -------------------------------| -------------------------------------------|
2090+ | 1 | boot | 128MB | FAT32 LBA (0x0c), bootable | BOOT.BIN (FSBL + PMUFW + BL31 + wolfBoot) |
2091+ | 2 | OFP_A | 200MB | Linux (0x83) | Primary signed firmware image |
2092+ | 3 | OFP_B | 200MB | Linux (0x83) | Update signed firmware image |
2093+ | 4 | rootfs | remainder | Linux (0x83) | Linux root filesystem |
2094+
2095+ ** Build wolfBoot + sign test images**
2096+ ``` sh
2097+ cp config/examples/zynqmp_sdcard.config .config
2098+ make clean
2099+ make
2100+
2101+ make test-app/image.bin
2102+ IMAGE_HEADER_SIZE=1024 ./tools/keytools/sign --rsa4096 --sha3 test-app/image.elf wolfboot_signing_private_key.der 1
2103+ IMAGE_HEADER_SIZE=1024 ./tools/keytools/sign --rsa4096 --sha3 test-app/image.elf wolfboot_signing_private_key.der 2
20232104```
20242105
2025- #### Signing Zynq
2106+ ** Build BOOT.BIN for SD card**
2107+
2108+ Copy the pre-built firmware and generate BOOT.BIN:
2109+
2110+ ``` sh
2111+ cp ${PREBUILT_DIR} /zynqmp_fsbl.elf .
2112+ cp ${PREBUILT_DIR} /pmufw.elf .
2113+ cp ${PREBUILT_DIR} /bl31.elf .
2114+
2115+ source ${VITIS_PATH} /settings64.sh
2116+ bootgen -arch zynqmp -image ./tools/scripts/zynqmp_sd_boot.bif -w -o BOOT.BIN
2117+ ```
20262118
2027- ` tools/keytools/sign --rsa4096 --sha3 /srv/linux-rpi4/vmlinux.bin wolfboot_signing_private_key.der 1 `
2119+ The BIF file (` zynqmp_sd_boot.bif ` ) configures the boot chain:
2120+ - FSBL at A53-0 (bootloader)
2121+ - PMUFW at PMU
2122+ - BL31 at EL3 with TrustZone
2123+ - wolfBoot at EL2
2124+
2125+ ** Create SD image**
2126+ ``` sh
2127+ dd if=/dev/zero of=sdcard.img bs=1M count=1024
2128+ sfdisk sdcard.img << EOF
2129+ label: dos
2130+ unit: sectors
2131+
2132+ 1 : start=2048, size=128M, type=c, bootable
2133+ 2 : size=200M, type=83
2134+ 3 : size=200M, type=83
2135+ 4 : type=83
2136+ EOF
2137+
2138+ SECTOR2=$( sfdisk -d sdcard.img | awk ' /sdcard.img2/ {for (i=1;i<=NF;i++) if ($i ~ /start=/) {gsub(/start=|,/, "", $i); print $i}}' )
2139+ SECTOR3=$( sfdisk -d sdcard.img | awk ' /sdcard.img3/ {for (i=1;i<=NF;i++) if ($i ~ /start=/) {gsub(/start=|,/, "", $i); print $i}}' )
2140+ dd if=test-app/image_v1_signed.bin of=sdcard.img bs=512 seek=$SECTOR2 conv=notrunc
2141+ dd if=test-app/image_v2_signed.bin of=sdcard.img bs=512 seek=$SECTOR3 conv=notrunc
2142+ ```
2143+
2144+ ** Provision SD card**
2145+ ``` sh
2146+ sudo dd if=sdcard.img of=/dev/sdX bs=4M status=progress conv=fsync
2147+ sync
2148+ sudo mkfs.vfat -F 32 -n BOOT /dev/sdX1
2149+ sudo mount /dev/sdX1 /mnt
2150+ sudo cp BOOT.BIN /mnt/
2151+ sudo umount /mnt
2152+ sudo fdisk -l /dev/sdX
2153+ ```
2154+
2155+ Or just mount and copy the BOOT.BIN and "dd" the partitions
2156+
2157+ ``` sh
2158+ # Mount the FAT boot partition and copy just the updated BOOT.BIN
2159+ sudo mount /dev/sdX1 /mnt && sudo cp BOOT.BIN /mnt/ && sudo umount /mnt && sync
2160+
2161+ # Write the signed image to partition 2 (P:A) and partition 3 (P:B)
2162+ sudo dd if=test-app/image_v1_signed.bin of=/dev/sdX2 bs=4k
2163+ sudo dd if=test-app/image_v1_signed.bin of=/dev/sdX3 bs=4k
2164+ ```
2165+
2166+ ** Boot Mode**
2167+
2168+ Set the ZCU102 boot mode switches (SW6) for SD card boot:
2169+
2170+ | Boot Mode | MODE Pins 3:0 | SW6[ 4:1] |
2171+ | --------- | ------------- | -------------- |
2172+ | JTAG | 0 0 0 0 | on, on, on, on |
2173+ | QSPI32 | 0 0 1 0 | on, on, off,on |
2174+ | SD1 | 1 1 1 0 | off,off,off,on |
2175+
2176+ ** Debug**
2177+
2178+ Enable SDHCI debug output by uncommenting in the config:
2179+ ```
2180+ CFLAGS_EXTRA+=-DDEBUG_SDHCI
2181+ CFLAGS_EXTRA+=-DDEBUG_DISK
2182+ ```
2183+
2184+ ** Example Boot Output**
2185+
2186+ ```
2187+ wolfBoot Secure Boot
2188+ Current EL: 2
2189+ PMUFW Ver: 1.1
2190+ SDHCI: SDCard mode
2191+ Reading MBR...
2192+ Found MBR partition table
2193+ MBR part 1: type=0x0C, start=0x100000, size=128MB
2194+ MBR part 2: type=0x83, start=0x8100000, size=200MB
2195+ MBR part 3: type=0x83, start=0x14900000, size=200MB
2196+ MBR part 4: type=0x83, start=0x21100000, size=71MB
2197+ Total partitions on disk0: 4
2198+ Checking primary OS image in 0,1...
2199+ Checking secondary OS image in 0,2...
2200+ Versions, A:1 B:1
2201+ Load address 0x10000000
2202+ Attempting boot from P:A
2203+ Boot partition: 0x8038AA0 (sz 211096, ver 0x1, type 0x401)
2204+ Loading image from disk...done
2205+ Boot partition: 0x8038AA0 (sz 211096, ver 0x1, type 0x401)
2206+ Checking image integrity...done
2207+ Verifying image signature...done
2208+ Firmware Valid.
2209+ Loading elf at 0x10000000
2210+ Found valid elf64 (little endian)
2211+ Program Headers 1 (size 56)
2212+ Load 29888 bytes (offset 0x10000) to 0x10000000 (p 0x10000000)
2213+ Clear 17540 bytes at 0x10000000 (p 0x10000000)
2214+ Entry point 0x10000000
2215+ Booting at 10000000
2216+ do_boot: entry=0x10000000, EL=2
2217+ do_boot: dts=0x00000000
2218+
2219+
2220+ ===========================================
2221+ wolfBoot Test Application - AMD ZynqMP
2222+ ===========================================
2223+
2224+ Current EL: 2
2225+ Boot mode: Disk-based (MBR partitions)
2226+ Application running successfully!
2227+
2228+ Entering idle loop...
2229+ ```
20282230
20292231
20302232## Versal Gen 1 VMK180
@@ -2313,7 +2515,6 @@ make test-app/image.bin
23132515dd if=/dev/zero of=sdcard.img bs=1M count=1024
23142516sfdisk sdcard.img << EOF
23152517label: dos
2316- unit: sectors
23172518
231825191 : start=2048, size=128M, type=c, bootable
231925202 : size=200M, type=83
0 commit comments