Electronics Design AU
Raspberry Pi

How Do You Configure NVMe/PCIe Boot on a Raspberry Pi 5 or CM4/CM5?

Last updated 9 July 2026 · 6 min read

Direct Answer

The Raspberry Pi 5's PCIe interface (also present on the CM4 and CM5 via their module connectors) is disabled by default and must be explicitly enabled before an NVMe SSD attached through an M.2 HAT or carrier board can be used, let alone booted from. The practical sequence is: update the Raspberry Pi bootloader EEPROM to a version that supports NVMe boot (`sudo rpi-eeprom-update -a`), enable the PCIe interface with a `dtparam=pciex1` line in `config.txt`, add `PCIE_PROBE=1` if the specific HAT does not implement the official HAT+ identification EEPROM the Pi otherwise checks for, and set the bootloader's `BOOT_ORDER` to try the NVMe device before (or instead of) the SD card. Because the interface is disabled by default and the exact configuration keys have changed across firmware releases, always confirm the current syntax against Raspberry Pi's own bootloader configuration documentation for the OS and firmware version actually in use.

Detailed Explanation

NVMe and PCIe are named repeatedly across this site's Raspberry Pi coverage — as a Pi 5 storage option, a CM4 carrier-board interface, and a comparison-table bullet — but the actual bring-up steps (bootloader update, config.txt settings, boot order) have never been covered as their own topic. This page covers that configuration directly, for the Pi 5, CM4, and CM5, all of which share the same underlying PCIe interface and bootloader boot-order mechanism.

Why PCIe/NVMe Boot Needs Explicit Configuration

Earlier Raspberry Pi models booted only from a microSD card (and, on the CM4, optionally from onboard eMMC). The Pi 5 introduced a PCIe Gen 2 x1 lane, exposed as a dedicated FPC connector for the official M.2 HAT+, and the CM4/CM5 expose the equivalent lane through their module edge connector for a carrier board to route to an M.2 slot. This PCIe interface is disabled at power-on by default and is not automatically part of the boot search — both facts exist because the Raspberry Pi Foundation validated the interface's signal integrity and boot behaviour for its own reference hardware, and enabling it unconditionally for every board (including third-party HATs it never tested) would risk instability the Foundation can't control for. Enabling and configuring NVMe boot is therefore a deliberate, multi-step process rather than a single toggle.

The Bootloader EEPROM and BOOT_ORDER

The Raspberry Pi 5, CM4, and CM5 use a bootloader stored in an on-board EEPROM (distinct from the OS itself) that determines the sequence of devices the board tries to boot from. NVMe boot support was added to this bootloader after the Pi 5's initial release, so the first practical step on an older unit is updating it:

sudo rpi-eeprom-update -a
sudo reboot

The bootloader's BOOT_ORDER setting, viewable and editable with rpi-eeprom-config, is a hex value where each digit represents a boot device to try, read in sequence — commonly including codes for SD card, USB mass storage, network boot, NVMe, and a "retry forever" terminator. The exact device codes and default order are defined by Raspberry Pi's own bootloader documentation and have been extended as new boot sources were added, so treat any specific example value as illustrative rather than authoritative — always check the current rpi-eeprom-config output and Raspberry Pi's bootloader documentation for the firmware version installed on the specific unit, rather than copying a boot-order value from an older guide.

Enabling PCIe in config.txt

The PCIe interface itself is enabled separately from the boot order, via config.txt (located in the firmware/boot partition):

[all]
dtparam=pciex1

Some third-party M.2 HATs additionally require PCIE_PROBE=1 in the same file if they don't implement the official Raspberry Pi HAT+ identification EEPROM the firmware otherwise checks for before probing the bus — without it, the Pi's firmware may not attempt to detect a connected device at all, which looks identical to a wiring or hardware fault but is actually a configuration gap. Running the PCIe lane at its full Gen 3 signalling rate (rather than the officially supported Gen 2) is possible via an additional dtparam=pciex1_gen=3 setting on some firmware versions, but this is an unsupported overclock outside the Pi 5's validated operating envelope — it should not be used in a product design without independent signal-integrity validation on the specific board and cable/connector in use.

Design Considerations

  • Update the bootloader before assuming NVMe boot doesn't work. A unit still running the EEPROM version it shipped with may simply lack NVMe boot support entirely — confirm the installed bootloader version and update it before troubleshooting anything else.
  • Budget power for the SSD, not just the Pi. The Raspberry Pi 5's higher-rated official power supply (5V/5A) already reflects the board's own increased demands; an NVMe SSD adds further current draw, particularly during write bursts, and some third-party HATs deliberately add their own regulator or separate power input to avoid loading the Pi's 5V rail. Check the specific drive's and HAT's power requirements against the actual supply budget in the finished product rather than assuming headroom exists.
  • Route the PCIe lane with controlled impedance on a custom carrier board. As already noted for the CM4 in Should You Use the Raspberry Pi CM4 in a Product?, PCIe traces require controlled-impedance routing; treating them as ordinary signal traces on a custom carrier board risks signal integrity failures that only show up as unreliable NVMe detection or boot failures, not an obvious hardware fault.
  • Keep firmware/OS documentation current in a long-lived product. Bootloader configuration keys and default boot-order device codes have changed across Raspberry Pi firmware releases since NVMe support was introduced — a product's build and provisioning documentation should record the exact firmware version validated for it, since assuming a config.txt setting from an early guide still applies to a much later firmware release is a common source of confusing field failures.

Common Mistakes

  • Assuming any NVMe M.2 HAT works out of the box. Without dtparam=pciex1 (and, for many third-party boards, PCIE_PROBE=1), the Pi's firmware never attempts to detect the drive at all — this presents identically to a dead or miswired SSD and wastes debugging time on the wrong layer.
  • Skipping the bootloader EEPROM update. NVMe boot support did not exist in the Pi 5's initial-release bootloader; a unit that has never had rpi-eeprom-update run may be unable to boot from NVMe no matter how correctly config.txt and BOOT_ORDER are set.
  • Enabling PCIe Gen 3 signalling in a production design without validation. The Gen 3 override is outside the officially supported operating envelope for the Pi 5's PCIe interface; using it in a shipped product without independent signal-integrity testing on the actual board and connector risks intermittent, hard-to-reproduce data corruption rather than a clean failure.
  • Underestimating the SSD's contribution to total system power draw. A design validated only with the Pi idling, then loaded with a power-hungry NVMe drive under sustained write traffic in the field, can brown out or reset under load in a way that never showed up during bring-up testing.

For Raspberry Pi–based products that need reliable storage, boot configuration, and firmware validated end to end, Zeus Design's firmware team supports embedded Linux product development from hardware through to field-ready firmware.

Frequently Asked Questions

Why won't my Raspberry Pi 5 detect a third-party NVMe HAT even after enabling PCIe?
Many third-party M.2/NVMe HATs for the Pi 5 do not implement the official HAT+ identification EEPROM that the Pi's firmware checks for by default before it will probe the PCIe bus for a connected device — this is a deliberate safety/compliance gate, not a bug, because the Pi 5's PCIe interface was validated with specific signal integrity margins in mind and not every third-party board meets the same layout requirements. Adding `PCIE_PROBE=1` to config.txt forces the firmware to probe for a PCIe device regardless of whether it detects a HAT+ identification EEPROM, which is the typical fix for a HAT that is otherwise electrically compatible but doesn't carry that identification. Confirm this setting name and behaviour against current Raspberry Pi documentation, since bootloader configuration options have changed across firmware releases.
Can I run an NVMe SSD from the Raspberry Pi 5's official power supply?
It depends on the specific SSD's power draw and the HAT's own power delivery design. The Raspberry Pi 5's official power supply is rated at 5V/5A (25W) specifically because the board itself, combined with an actively cooled CPU and typical peripherals, needs more headroom than earlier Pi models — adding an NVMe SSD (which can draw a meaningful current spike during writes, particularly on higher-performance drives) further reduces the remaining power budget. Some third-party M.2 HATs include their own dedicated regulator or a separate power input specifically to avoid loading the Pi's own 5V rail; check the HAT's documentation for its power architecture and choose a drive within the combined system's actual power budget rather than assuming any NVMe SSD will work from the Pi's own supply.
Does the CM4 support the same NVMe boot configuration as the Pi 5?
The underlying PCIe interface and bootloader EEPROM boot-order mechanism are shared across the Raspberry Pi 5, CM4, and CM5, since they all use the same Raspberry Pi bootloader architecture — but the CM4 exposes its single PCIe Gen 2 x1 lane through the compute module's edge connector rather than a dedicated M.2 HAT slot, so NVMe support depends entirely on whether the specific carrier board routes that lane to an M.2 connector, as covered in Should You Use the Raspberry Pi CM4 in a Product? The config.txt and rpi-eeprom-config steps are the same in principle; the hardware path to get the PCIe lane onto a physical M.2 connector is carrier-board-specific.

References

Related Questions

Related Forum Discussions