Getting Dirty with the Jetson Orin Nano Super Developer Kit
Overview:
This post details a runbook for flashing the Super Developer Kit with JetPack 6.2 (microSD) and then upgrading to JetPack 7.2 (NVMe via ISO). It also covers USB networking to a Mac, and getting the Intel 8265 WiFi Adapter working in both configurations
Background:
I broke the Realtek WiFi Adapter installing my Dev Kit in an enclosure, and installed the WaveShare (Intel 8265) as a replacement. The Intel 8265 has native support in recent JetPack releases, but the required CONFIG_IWLWIFI build option was not included in the JetPack 7.2 build.
Hardware:
Jetson Orin Nano Developer Kit, Intel Dual Band Wireless-AC 8265 (Waveshare
AC8265) in the M.2 Key-E slot, replacing the stock Realtek RTL8822CE.
Host machine: macOS.
Version glossary
One Jetson carries several unrelated version numbers. Confusing these costs time.
| Layer | 6.2 system | 7.2 system |
|---|---|---|
| JetPack (SDK bundle) | 6.2 | 7.2 |
| Jetson Linux / L4T (BSP) | 36.x | 39.2 |
| Linux kernel | 5.15 | 6.8.12-1021-tegra |
| Ubuntu | 22.04 | 24.04 |
| UEFI / QSPI firmware | 36.4.4 | r39 generation |
Firmware versions track L4T, not JetPack or the kernel.
1. Flashing JetPack 6.2 to microSD, with firmware updates
The microSD slot is on the underside of the module, not the carrier board. It is easy to miss under the heatsink assembly.
1.1 Check UEFI firmware first
Do not skip this. Power on, tap Esc repeatedly at the NVIDIA splash to enter UEFI setup; the firmware version is near the top. From a running system:
sudo nvbootctrl dump-slots-info
- 36.x or newer → skip to 1.3
- older than 36.0 → do 1.2 first
1.2 Firmware bridge (only if firmware < 36.0)
Factory firmware cannot boot JetPack 6.x, and the 6.x image cannot fix that itself — the
SoC boots from QSPI-NOR before it can read the SD card. JetPack 5.1.3 is the bridge.
- Download the JetPack 5.1.3 SD image (
JP513-orin-nano-sd-card-image_b29.zip) - Write to microSD with Balena Etcher, boot, complete first-boot setup, connect to network
- Reboot and let the firmware update run. Do not cut power during the progress bar.
- Power off, remove the 5.1.3 card
Install the QSPI updater and reboot again:
sudo nvbootctrl dump-slots-info # confirm current version
sudo apt update
sudo apt install nvidia-l4t-jetson-orin-nano-qspi-updater
sudo reboot
Confirm the bootloader update was scheduled:
sudo systemctl status nv-l4t-bootloader-config
1.3 Write and boot JetPack 6.2
- Download the Orin Nano SD card image from the JetPack 6.2.1 page
- Write it to a 64 GB+ UHS-1 microSD with Etcher — write the image, do not copy the file
- Insert into the module slot, connect DisplayPort, keyboard, then the 19 V supply
- Complete first-boot setup (EULA, locale, user account)
1.4 Post-install firmware update
JetPack 6.x may schedule a further UEFI update after first boot:
sudo systemctl status nv-l4t-bootloader-config
sudo reboot # if an update was scheduled; do not interrupt
1.5 Unlock full performance
sudo nvpmodel -q # list modes
sudo nvpmodel -m 0 # MAXN SUPER
2. Internet over USB-C for JetPack 6.2
The Jetson's USB-C port runs a device-mode gadget exposing a serial console, anL4T-README mass-storage volume, and a USB Ethernet interface. macOS does not support
RNDIS; it binds the CDC-ECM function.
This is a debugging bridge, not infrastructure. Ethernet or working Wi-Fi is better.
2.1 Mac side
Reset any stale sharing configuration first:
sudo defaults read /Library/Preferences/SystemConfiguration/com.apple.nat # inspect
sudo cp /Library/Preferences/SystemConfiguration/com.apple.nat.plist ~/nat.plist.bak
sudo rm /Library/Preferences/SystemConfiguration/com.apple.nat.plist
sudo reboot
Never delete preferences.plist — that resets all networking on the Mac.
With the Jetson booted and USB-C connected:
networksetup -listallhardwareports | grep -A2 -i tegra
You should see Linux for Tegra with a device name (e.g. en7). Then in
System Settings → General → Sharing → Internet Sharing:
- Share from: Wi-Fi
- To computers using: check "Linux for Tegra" ← the step that is easy to miss
- Toggle Internet Sharing on
Verify it actually took:
ifconfig bridge100 # note inet, and check the member list
sysctl net.inet.ip.forwarding # must be 1
sudo pfctl -s nat # needs sudo; should show a NAT rule
The member list must include your Tegra interface. If it only lists vmenet0, macOS is
sharing to a VM interface and nothing will reach the Jetson.
2.2 Jetson side
Match the Jetson to whatever subnet bridge100 reports (commonly 192.168.2.1):
ip -br addr show l4tbr0
sudo ip addr add 192.168.2.100/24 dev l4tbr0
sudo ip route replace default via 192.168.2.1 dev l4tbr0
echo "nameserver 1.1.1.1" | sudo tee /etc/resolv.conf
ping -c3 1.1.1.1
None of this survives a reboot.
2.3 Diagnostics that actually discriminate
ip route get 1.1.1.1 # shows chosen interface, gateway, and source address
ip neigh show 192.168.2.1 # REACHABLE = layer 2 fine; INCOMPLETE = ARP failing
On the Mac, watch the wire while pinging from the Jetson:
sudo tcpdump -i en7 -n arp
- ARP requests appear → Jetson transmits fine, Mac isn't replying (Mac-side problem)
- Nothing appears → frames never leave the Jetson (Jetson-side problem)
2.4 Known traps
- Mac self-assigns
169.254.x.x— DHCP failed. The Jetson runs a DHCP server on192.168.55.0/24while macOS wants to serve its own subnet on the same wire. They fight.
Set both ends statically instead. pingto the Mac fails but routing works — macOS drops inbound ICMP with the firewall
or stealth mode on. Don't judge the link by pings to the gateway.- Link-local only by default — without Internet Sharing you get a shell, not internet.
- Serial console fallback —
ls /dev/cu.usbmodem*thenscreen /dev/cu.usbmodem... 115200
(exit Ctrl-A, K, Y). Only exists once Linux has booted; it will never show UEFI or GRUB.
3. Intel 8265 on JetPack 6.2 via backport-iwlwifi
NVIDIA's 5.15 kernel does not ship iwlwifi. The DKMS backport supplies it.
sudo apt update
sudo apt install backport-iwlwifi-dkms
dkms status # want "installed", not just "added" or "built"
Load and verify:
sudo modprobe iwlwifi
sudo dmesg | grep -i iwlwifi
lspci -k | grep -A3 -i network # want "Kernel driver in use: iwlwifi"
ip -br link # wlP1p1s0 appears
Expected healthy dmesg output:
module verification failed: signature and/or required key missing - tainting kernel
Loading modules backported from iwlwifi
Detected Intel(R) Dual Band Wireless AC 8265
wlP1p1s0: renamed from wlan0
The taint warning is cosmetic — out-of-tree modules aren't signed by the kernel's key.
If firmware is missing (Direct firmware load ... failed):
ls /lib/firmware/iwlwifi-8265*
sudo apt install linux-firmware
sudo modprobe -r iwlwifi && sudo modprobe iwlwifi
Bring it up:
rfkill list
sudo rfkill unblock all
sudo nmcli radio wifi on # often "disabled" by default, and it persists
nmcli device status # if "unmanaged": nmcli device set <if> managed yes
nmcli device wifi list
sudo nmcli device wifi connect "SSID" password "password"
A wireless interface showing DOWN in ip -br link is normal — NetworkManager brings it up on connect.
4. Flashing JetPack 7.2 from ISO to NVMe
There is no SD card image for Orin Nano in 7.2. The unified ISO on a USB stick is the
only first-party path, and it installs to NVMe.
Requires: a 2280 or 2230 NVMe SSD in an M.2 Key-M slot, a 16 GB+ USB stick, and ~25 GB free
on the Mac.
4.1 Prepare
https://developer.nvidia.com/downloads/embedded/L4T/r39_Release_v2.0/iso/jetsoninstaller-r39.2.0-2026-06-01-23-53-13-arm64.iso
Write it to the USB stick with Etcher — a raw image write, not a file copy.
4.2 Set the display hand-off mode (previously-used devices)
Required when the board has been set up before, otherwise the installer or the OOBE service
hangs with a black screen.
- Power on, tap
Escto enter UEFI setup - Device Manager → NVIDIA Configuration → Boot Configuration
- SOC Display Hand-Off Mode →
Auto(default isNever) - SOC Display Hand-Off Method →
simplefb(efifbhangs the 7.2 OOBE path) F10,y,Escto top, Reset
Both settings matter. The installer resets Hand-Off to Never when it finishes, which is
correct for normal use.
4.3 Install
- Insert the USB stick in a Type-A port, power on,
Esc, Boot Manager, select the stick - Press
Yat the QSPI capsule update prompt. This is the critical step:- It is the first screen, with roughly a 20-second timeout
- Have a keyboard plugged directly into a Type-A port (not a hub) before powering on
- Press
Yimmediately — read it later, photograph the screen if needed - It runs twice with a progress bar. Do not cut power.
- Skipping this leaves firmware at 36.x, and a complete 7.2 install on NVMe will not
boot — you get a black screen with a non-blinking cursor, no kernel, no USB gadget
- At the GRUB menu, select the storage target (Install on NVMe)
- Wait ~10 minutes; it appears frozen partway through, which is normal
- Remove the USB stick before it reboots, or it boots the installer again
- Complete
oem-config
4.4 Verify
sudo nvbootctrl dump-slots-info # should no longer read 36.4.4
uname -r # 6.8.12-1021-tegra
4.5 Diagnosing a black screen after install
| Symptom | Meaning |
|---|---|
| Boots the 6.2 SD card fine | Display, cable, monitor, firmware all healthy |
/dev/cu.usbmodem* appears on the Mac |
Linux reached userspace — display-only problem |
No cu.usbmodem* ever appears |
Failure before userspace — not a display problem |
| Non-blinking cursor, top-left | UEFI initialized the display, then nothing wrote to it |
Inspect the NVMe from the working 6.2 system:
lsblk
sudo fdisk -l /dev/nvme0n1 # look for an EFI System partition
sudo mount /dev/nvme0n1p1 /mnt && du -sh /mnt
A rootfs of several GB means the install completed and the problem is firmware or boot
order, not a bad install.
5. Internet over USB-C for JetPack 7.2
Mac side is identical to §2.1. The Jetson side differs and this is the key finding:
On r39.2, the l4tbr0 bridge does not pass traffic to the ECM function that macOS binds to.
Symptoms: correct addressing on both ends, net.inet.ip.forwarding = 1, the Tegra interface
correctly bridged on the Mac — and ip neigh still reporting INCOMPLETE.
5.1 Check the gadget's slave interfaces
ip -br link # l4tbr0, usb0, usb1
bridge link show
usb0 is RNDIS (Windows), usb1 is CDC-ECM (macOS/Linux). usb1 is frequently DOWN.
sudo ip link set usb1 up
5.2 Bypass the bridge (this is what works)
sudo ip link set usb1 nomaster
sudo ip addr add 192.168.2.100/24 dev usb1
sudo ip link set usb1 up
sudo ip route replace default via 192.168.2.1 dev usb1
ping -c3 192.168.2.1
Substitute whatever ifconfig bridge100 reports on the Mac. Then:
echo "nameserver 1.1.1.1" | sudo tee /etc/resolv.conf
ping -c3 1.1.1.1
sudo apt update
Not persistent across reboots.
5.3 Captive portals
apt hash-sum mismatches on a portal network are the portal serving HTML in place of
package indexes — not an attack. apt's integrity checking working as designed.
curl -sI http://ports.ubuntu.com/ | head -5 # 302 → portal is intercepting
head -c 300 /var/lib/apt/lists/*_Packages # <!DOCTYPE html> confirms it
After authenticating:
sudo apt clean && sudo rm -rf /var/lib/apt/lists/* && sudo apt update
To log in, install a browser while USB internet still works, then switch networks:
which firefox || sudo apt install firefox
sudo nmcli device wifi connect "SSID" # no password for an open portal network
ip route | grep default # Wi-Fi must be the only default route
nmcli networking connectivity check # "portal" = associated, login pending
Firefox: Ctrl+L, http://neverssl.com (plain http — https breaks the redirect), Tab
between fields, Enter. GNOME often pops up its own portal window, which is easier.
w3m works for simple forms but fails on JavaScript-driven portals.
6. Building iwlwifi for JetPack 7.2 (kernel 6.8)
6.1 Why the backport doesn't work
backport-iwlwifi-dkms declares OBSOLETE_BY="6.7.0" in its dkms.conf. DKMS refuses to
build it on any kernel ≥ 6.7, so on 6.8 it registers as added and stops. EditingBUILD_EXCLUSIVE_CONFIG doesn't help — OBSOLETE_BY is the actual gate.
That's correct behaviour: upstream 6.8 already contains a current iwlwifi. NVIDIA simply
didn't set CONFIG_IWLWIFI when building their kernel. It's a config omission, not a
missing driver — so build it from NVIDIA's own source.
Clean up the dead end:
sudo dkms remove backport-iwlwifi/11510 --all
sudo apt remove backport-iwlwifi-dkms
6.2 Prerequisites
Build on the Jetson, natively. macOS cannot build Linux kernel modules.
sudo apt install build-essential bc bison flex libssl-dev libelf-dev dwarves rsync zstd
6.3 Get the kernel source
cd ~
wget -c https://developer.nvidia.com/downloads/embedded/L4T/r39_Release_v2.0/sources/public_sources.tbz2
tar xf public_sources.tbz2
cd Linux_for_Tegra/source
tar xf kernel_src.tbz2
Find the kernel root — the directory with the top-level kernel Makefile:
find . -maxdepth 4 -name Makefile -exec grep -l "^PATCHLEVEL = 8" {} \;
cd there. ls should show arch block certs crypto drivers fs include init kernel lib,
not flash.sh or bootloader/.
6.4 Configure
zcat /proc/config.gz > .config # or cp /lib/modules/$(uname -r)/build/.config .config
Enable Intel wireless and disable module signing:
scripts/config --module IWLWIFI
scripts/config --module IWLMVM
scripts/config --enable WLAN_VENDOR_INTEL
scripts/config --enable IWLWIFI_OPMODE_MODULAR
scripts/config --disable MODULE_SIG_ALL
scripts/config --disable MODULE_SIG
make olddefconfig
grep -E "^CONFIG_IWLWIFI|^CONFIG_IWLMVM|MODULE_SIG_ALL" .config
make olddefconfig can silently drop options whose dependencies aren't met — always verify
after. If it prompts interactively: IWLDVM → N (that's for older 5000/6000-series
cards), IWLMVM → m. In Kconfig prompts N=no, m=module, y=built-in; the capitalised
letter is the default.
6.5 Supply Module.symvers
make modules_prepare does not generate Module.symvers. Without it, modpost reports
every core symbol as undefined (krealloc undefined!, try_module_get undefined!). Copy it
from the installed headers:
cp /lib/modules/$(uname -r)/build/Module.symvers .
6.6 Build
make modules_prepare
make M=drivers/net/wireless/intel/iwlwifi LOCALVERSION=-1021-tegra modules
LOCALVERSION is required. The source tree produces vermagic 6.8.12 while the running
kernel is 6.8.12-1021-tegra; a mismatch means the module will not load. Verify:
make kernelrelease # must print 6.8.12-1021-tegra
modinfo drivers/net/wireless/intel/iwlwifi/iwlwifi.ko | grep vermagic
uname -r
6.7 Install manually
make modules_install re-runs the signing step and fails withSSL error: no such file: ../crypto/bio/bss_file.c when no signing key exists. Copy the
modules by hand instead:
sudo mkdir -p /lib/modules/$(uname -r)/extra
sudo find drivers/net/wireless/intel/iwlwifi -name "*.ko" \
-exec cp {} /lib/modules/$(uname -r)/extra/ \;
ls /lib/modules/$(uname -r)/extra/ # want iwlwifi.ko and iwlmvm.ko
sudo depmod -a
Unsigned modules load fine — CONFIG_MODULE_SIG=y only enables signature support;
enforcement would be CONFIG_MODULE_SIG_FORCE.
6.8 Decompress the firmware
NVIDIA's kernel lacks CONFIG_FW_LOADER_COMPRESS_ZSTD, so it cannot read the .zst
firmware that ships with Ubuntu 24.04. Symptom:
Direct firmware load failed with error -2
no suitable firmware found!
minimum version required: iwlwifi-8265-22 / maximum version supported: iwlwifi-8265-36
cd /lib/firmware
sudo unzstd -k iwlwifi-8265-*.ucode.zst
ls iwlwifi-8265*
6.9 Load and connect
sudo modprobe iwlwifi
sudo dmesg | grep -i iwlwifi # want "Detected Intel(R) Dual Band Wireless AC 8265"
lspci -k | grep -A3 -i network # want "Kernel driver in use: iwlwifi"
ip -br link # wlP1p1s0 appears (DOWN is normal)
rfkill list
sudo rfkill unblock all
sudo nmcli radio wifi on
nmcli device wifi list
sudo nmcli device wifi connect "SSID" password "password"
nmcli networking connectivity check # want "full"
Maintenance
Three things on the 7.2 system are not package-managed and will not survive a kernel
update:
iwlwifi.koandiwlmvm.koin/lib/modules/6.8.12-1021-tegra/extra/- The decompressed
.ucodefiles in/lib/firmware/ - Both are pinned to that exact kernel version
Any L4T kernel update replaces the kernel without rebuilding these, and Wi-Fi disappears on
the next boot.
Before any kernel or JetPack upgrade: have Ethernet or the stock Realtek RTL8822CE card
on hand. Keep the extracted kernel source tree and the Module.symvers copy — rebuilding is
then §6.6 through §6.9 rather than the whole exercise.
Consider the Realtek card if this ever needs to be low-maintenance. It's supported
in-tree on both JetPack versions, needs no compilation, and survives updates untouched.
Quick reference — traps that cost the most time
| Symptom | Cause |
|---|---|
| Black screen, non-blinking cursor after 7.2 install | QSPI capsule update prompt was missed; firmware still 36.x |
INCOMPLETE in ip neigh over USB |
On 7.2, l4tbr0 doesn't pass ECM traffic — address usb1 directly |
Mac shows 169.254.x.x on the USB interface |
Duelling DHCP servers; assign both ends statically |
bridge100 lists only vmenet0 |
"Linux for Tegra" not checked in Internet Sharing |
| apt hash sum mismatch | Captive portal serving HTML instead of package indexes |
krealloc undefined! from modpost |
Missing Module.symvers |
| Module builds but won't load | vermagic mismatch — set LOCALVERSION=-1021-tegra |
Direct firmware load failed error -2 |
.zst firmware, kernel lacks zstd decompression |
DKMS status stuck at added |
OBSOLETE_BY="6.7.0" — backport won't build on 6.8 |
| USB drive absent from Boot Manager | No EFI System partition, or wrong arch (BOOTX64 vs BOOTAA64) |
.img file copied to a stick doesn't boot |
Must be written raw (Etcher/dd), not copied as a file |