Skip to content

Add AArch64 UEFI support (NVIDIA Jetson Orin)#818

Open
dgarske wants to merge 3 commits into
wolfSSL:masterfrom
dgarske:aarch64_efi
Open

Add AArch64 UEFI support (NVIDIA Jetson Orin)#818
dgarske wants to merge 3 commits into
wolfSSL:masterfrom
dgarske:aarch64_efi

Conversation

@dgarske

@dgarske dgarske commented Jul 7, 2026

Copy link
Copy Markdown
Member

Add aarch64_efi target: wolfBoot as an AArch64 UEFI application (+ root-of-trust, FIPS, Tegra234 groundwork)

Summary

Adds a generic AArch64 UEFI-application target to wolfBoot -- the direct sibling of the existing x86_64_efi target. wolfBoot builds as wolfboot.efi (a PE/COFF EFI application), is launched by platform UEFI firmware, cryptographically verifies the next-stage image, and boots it through UEFI LoadImage/StartImage. Validated end-to-end on the NVIDIA Jetson Orin Nano, booting all the way to an Ubuntu 22.04 login prompt.

The branch also lands the first roadmap steps beyond the base target: UEFI Secure Boot enrollment tooling (so the firmware verifies wolfBoot), a FIPS-ready algorithm configuration, and a bare-metal Tegra234 skeleton as groundwork for lower-level driver work. Each is an independent, self-contained commit.

Commits on this branch

  1. Add aarch64_efi target -- the UEFI-application target and its Orin validation (below), the CI script exec-bit fix, the UEFI Secure Boot signing tool (sign-efi-secureboot.sh) with enrollment/fuse docs, and FIPS-approved algorithm guidance (docs/FIPS.md).
  2. Tegra234 bare-metal skeleton -- UART + generic-timer HAL and a compile-only CI job.

Base target features

  • New aarch64_efi target -- the AArch64 counterpart of x86_64_efi. It uses only UEFI Boot Services (no SoC-specific registers), so a single wolfboot.efi runs on any AArch64 UEFI platform rather than being tied to one board.
  • Verified boot after UEFI -- reads the kernel image from the EFI Simple File System, verifies it with wolfCrypt (validated with ED25519/SHA256; the standard wolfBoot SIGN/HASH options apply), and hands control to it via LoadImage/StartImage. A/B image selection uses the RAM updater.
  • gnu-efi build integration -- pei-aarch64-little PE output, gnu-efi CRT0 entry, and EFI console Print for log output. A helper script builds the AArch64 gnu-efi runtime from source (tools/scripts/build-gnu-efi-aarch64.sh), pinned to a released gnu-efi tag (4.0.4) so the runtime CRT0/linker-script/libs are reproducible and auditable.
  • Hardware-free iteration -- tools/scripts/aarch64-efi-qemu.sh runs wolfboot.efi under QEMU + AAVMF, including a --gdb mode for source-level debugging.
  • Continuous integration -- a compile-only aarch64_efi_test job builds the AArch64 gnu-efi runtime and then wolfboot.efi on every push, mirroring the existing x86_64_efi job.
  • Validated on real hardware -- NVIDIA Jetson Orin Nano (Tegra234): boots from the SD via UEFI removable-media auto-boot (\EFI\BOOT\BOOTAA64.EFI), verifies the ED25519 signature, and boots the payload through to Linux userspace.

Root of trust: UEFI Secure Boot (new)

Closes the remaining code-signing gap so the chain is continuous: firmware -> wolfboot.efi -> kernel.

  • tools/scripts/sign-efi-secureboot.sh generates PK/KEK/db keys, sbsigns wolfboot.efi, and emits the signed variable updates (.auth) for enrollment. Verified locally: the signed image passes sbverify and the unsigned original is rejected. (Requires sbsigntool, efitools, openssl.)
  • docs/Targets.md gains an "Enrolling wolfBoot into UEFI Secure Boot" subsection (enrollment order, QEMU/AAVMF pre-test) and a document-only NVIDIA PKC/SBK fuse-provisioning subsection (no fuses are burned; the board stays in dev/unfused mode).

FIPS-ready configuration (new)

  • The aarch64_efi config documents the FIPS-approved selection (set SIGN=ECC384, HASH=SHA384, SPMATH=1) instead of the default ED25519/SHA256 (ED25519 is not FIPS approved).
  • docs/FIPS.md states the distinction plainly: this selects approved algorithms, but wolfBoot's build compiles individual wolfCrypt sources and is not itself the CMVP-validated module boundary. It scopes what a genuinely validated build additionally requires.

Tegra234 bare-metal skeleton (new, groundwork)

Groundwork for the "Path B" firmware-replacement direction; not a validated boot path (the validated Orin path remains the UEFI application above).

  • hal/tegra234.c implements the two lowest-level drivers to build on -- Tegra234 UARTA (NS16550) console and the ARMv8 generic timer -- plus the standard HAL stubs, on top of the shared AArch64 startup (src/boot_aarch64_start.S via the simple-startup path).
  • Builds wolfboot.bin (RAM boot, no factory.bin), mirroring raspi3; links the full verify path. A compile-only tegra234_test CI job is added.
  • The DRAM memory map (hal/tegra234.ld) and the earlier-stage clock/pinmux assumptions are marked PROVISIONAL, to be finalized on hardware alongside the Path B handoff recon.

Notable fix (base target)

For a UEFI-application target the keystore must not be placed in the dedicated .keystore linker section: the gnu-efi PE does not load that section, so PubKeys reads back as zeros and key lookup fails (and faults on stricter firmware). keygen.c emits the keystore as plain const data for aarch64_efi, matching how x86_64_efi already handles it.

Files

New: hal/aarch64_efi.c, hal/aarch64_efi.ld, src/boot_aarch64_efi.c, config/examples/aarch64_efi.config, config/examples/tegra234.config, hal/tegra234.c, hal/tegra234.h, hal/tegra234.ld, test-app/app_tegra234.c, docs/FIPS.md, tools/scripts/build-gnu-efi-aarch64.sh, tools/scripts/aarch64-efi-qemu.sh, tools/scripts/sign-efi-secureboot.sh. Edits: arch.mk, Makefile, tools/keytools/keygen.c, src/boot_aarch64_start.S, docs/Targets.md, docs/README.md, .gitignore, .github/workflows/test-configs.yml, .github/workflows/test-build.yml.

Build and run

./tools/scripts/build-gnu-efi-aarch64.sh          # one-time: AArch64 gnu-efi
cp config/examples/aarch64_efi.config .config
make                                              # -> wolfboot.efi
# sign a payload, place wolfboot.efi + kernel.img on a FAT ESP, launch from UEFI
./tools/scripts/aarch64-efi-qemu.sh               # optional: run in QEMU

FIPS-ready variant: edit .config to set SIGN=ECC384 HASH=SHA384 SPMATH=1, then make keysclean && make (sign with --ecc384 --sha384).

Tegra234 skeleton: cp config/examples/tegra234.config .config && make wolfboot.bin CROSS_COMPILE=aarch64-linux-gnu-.

See docs/Targets.md (NVIDIA Jetson Orin section) for the full validated L4T recipe and Secure Boot enrollment steps.

Validation

  • QEMU (qemu-system-aarch64 + AAVMF): launch -> read kernel.img -> ED25519 verify PASS -> LoadImage/StartImage -> the real L4T kernel EFI stub runs.
  • Jetson Orin Nano: Verifying signature...done -> boots the signed L4T kernel -> mounts the SD rootfs -> Ubuntu 22.04.5 login prompt, auto-launched from the SD.
  • Build coverage: aarch64_efi (default and FIPS ECC384/SHA384 algorithms) and tegra234 build clean; x86_64_efi and raspi3 unregressed. The Secure Boot tool round-trips (sign -> sbverify PASS; unsigned -> rejected).

@dgarske dgarske self-assigned this Jul 7, 2026
Copilot AI review requested due to automatic review settings July 7, 2026 17:05

Copilot AI left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

This pull request adds a new aarch64_efi target so wolfBoot can run as an AArch64 UEFI application (validated on NVIDIA Jetson Orin), loading/verifying kernel.img/update.img from the ESP and booting via UEFI LoadImage/StartImage.

Changes:

  • Add a new AArch64 UEFI HAL (hal/aarch64_efi.c) plus boot glue (src/boot_aarch64_efi.c) and linker-script stub.
  • Extend the build system to support an AArch64 PE/COFF wolfboot.efi output and a new example config.
  • Add helper scripts and documentation for building gnu-efi for AArch64 and running under QEMU/Jetson deployment.

Reviewed changes

Copilot reviewed 10 out of 11 changed files in this pull request and generated 6 comments.

Show a summary per file
File Description
tools/scripts/build-gnu-efi-aarch64.sh Helper to clone/build/install gnu-efi (AArch64) into the repo tree
tools/scripts/aarch64-efi-qemu.sh Convenience runner for wolfboot.efi under QEMU + AAVMF
tools/keytools/keygen.c Extends keystore section handling for the new UEFI target macro
src/boot_aarch64_efi.c Adds UEFI-target do_boot() glue for AArch64
Makefile Makes the wolfboot.efi objcopy output format configurable per target
hal/aarch64_efi.ld Empty placeholder linker script (gnu-efi script used instead)
hal/aarch64_efi.c New AArch64 UEFI HAL: ESP file loading, verification, LoadImage/StartImage handoff
docs/Targets.md Adds aarch64_efi target documentation (Jetson Orin + QEMU workflow)
config/examples/aarch64_efi.config Example configuration for aarch64_efi
arch.mk Adds aarch64_efi target build flags, gnu-efi paths, and linking rules
.gitignore Ignores gnu-efi build artifacts and staging dirs for the new target

💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.

Comment thread hal/aarch64_efi.c
Comment thread src/boot_aarch64_efi.c Outdated
Comment thread hal/aarch64_efi.c Outdated
Comment thread hal/aarch64_efi.c
Comment thread tools/scripts/build-gnu-efi-aarch64.sh Outdated
Comment thread arch.mk
@dgarske dgarske requested a review from Copilot July 8, 2026 00:05

Copilot AI left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

Copilot reviewed 12 out of 13 changed files in this pull request and generated 11 comments.

Comment thread hal/aarch64_efi.c
Comment thread hal/aarch64_efi.c
Comment thread hal/aarch64_efi.c
Comment thread hal/aarch64_efi.c
Comment thread hal/aarch64_efi.c
Comment thread hal/aarch64_efi.c
Comment thread hal/aarch64_efi.c
Comment thread hal/aarch64_efi.c
Comment thread hal/aarch64_efi.c
Comment thread src/boot_aarch64_efi.c
dgarske added 2 commits July 10, 2026 14:25
AArch64 UEFI-application target (sibling of x86_64_efi): builds wolfboot.efi, verifies the next-stage image with wolfCrypt, and boots via UEFI LoadImage/StartImage. Validated on the Jetson Orin Nano through to the Ubuntu login. Includes gnu-efi build and QEMU scripts, CI, a UEFI Secure Boot signing tool (sign-efi-secureboot.sh) with enrollment/fuse docs, and FIPS-approved algorithm guidance (docs/FIPS.md).
UART + ARMv8 generic timer HAL on the shared AArch64 startup; builds wolfboot.bin (RAM boot, like raspi3). Groundwork for the Path B firmware-replacement direction; adds a compile-only CI job.
Adds MEASURED_BOOT_TCG2: wolfBoot extends the verified kernel into the platform firmware TPM (PCR MEASURED_PCR_A) via EFI_TCG2_PROTOCOL HashLogExtendEvent before handoff, no wolfTPM transport. Validated on the NVIDIA Orin Nano fTPM (TPM present, SHA-256+SHA-384 banks, measured into PCR 9).
@dgarske dgarske requested a review from Copilot July 11, 2026 00:29
@dgarske dgarske marked this pull request as ready for review July 11, 2026 00:39

Copilot AI left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

Copilot reviewed 22 out of 23 changed files in this pull request and generated 8 comments.

Comment thread hal/aarch64_efi.c
Comment on lines +250 to +256
mem_path_device->Header.Type = EFI_DEVICE_PATH_PROTOCOL_HW_TYPE;
mem_path_device->Header.SubType = EFI_DEVICE_PATH_PROTOCOL_MEM_SUBTYPE;
mem_path_device->MemoryType = EfiLoaderData;
mem_path_device->StartingAddress = (EFI_PHYSICAL_ADDRESS)boot_addr;
mem_path_device->EndingAddress = (EFI_PHYSICAL_ADDRESS)((uint8_t*)boot_addr+*size);
SetDevicePathNodeLength(&mem_path_device->Header,
sizeof(MEMMAP_DEVICE_PATH));
Comment thread hal/aarch64_efi.c
Comment on lines +378 to +388
wolfBoot_printf("Opening file: %s, size: %u\n", filename, *sz);
status = uefi_call_wrapper(BS->AllocatePages,
4,
AllocateAnyPages,
EfiLoaderData,
(*sz/PAGE_SIZE) + 1, _addr);
if (status != EFI_SUCCESS) {
wolfBoot_printf("can't get memory at specified address %d\n", status);
uefi_call_wrapper(file->Close, 1, file);
return status;
}
Comment thread hal/aarch64_efi.c
*sz = (uint32_t)readsz;
uefi_call_wrapper(file->Close, 1, file); /* done with the file */
if (status != EFI_SUCCESS) {
wolfBoot_printf("can't read kernel image %d\n", status);
Comment thread hal/aarch64_efi.c
Comment on lines +274 to +277
if (status != EFI_SUCCESS) {
wolfBoot_printf("can't load kernel image from memory\n");
panic();
}
Comment thread hal/aarch64_efi.c
Comment on lines +297 to +300
if (status != EFI_SUCCESS) {
wolfBoot_printf("can't load kernel image from memory\n");
panic();
}
Comment thread src/boot_aarch64_efi.c
Comment on lines +42 to +47
extern void RAMFUNCTION aarch64_efi_do_boot(uint32_t *boot_addr);

void RAMFUNCTION do_boot(const uint32_t *app_offset)
{
aarch64_efi_do_boot((uint32_t *)app_offset);
}
Comment on lines +20 to +25
set -e

SCRIPT_DIR="$(cd "$(dirname "$0")" && pwd)"
ROOT="$(cd "$SCRIPT_DIR/../.." && pwd)"

KEYDIR="${KEYDIR:-$ROOT/tools/efi-secureboot-keys}"
Comment on lines +362 to +369
tegra234_test:
uses: ./.github/workflows/test-build.yml
with:
arch: aarch64
# Tegra234 bare-metal skeleton: build the bootloader only (RAM boot,
# no factory.bin), mirroring raspi3.
config-file: ./config/examples/tegra234.config
make-args: wolfboot.bin CROSS_COMPILE=aarch64-linux-gnu-
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants