RTX 5080 eGPU (USB4/Thunderbolt) on Ubuntu 24.04: cuCtxCreate() returns CUDA_ERROR_UNKNOWN or hangs, while nvidia-smi works

Hardware

  • Laptop: HP ENVY x360 Convertible 15-es2xxx

  • BIOS: F.20 (2025-03-26)

  • eGPU: NVIDIA GeForce RTX 5080 in a USB4 / Thunderbolt enclosure

Software

  • Ubuntu 24.04

  • Kernel 7.0.0-28-generic

  • NVIDIA Open Kernel Driver 610.43.02

  • CUDA UMD 13.3

  • CUDA Toolkit 13.3

Problem

The GPU is detected correctly and nvidia-smi works normally.

Basic CUDA initialization also succeeds:

  • cuInit()CUDA_SUCCESS

  • cuDeviceGet()CUDA_SUCCESS

  • cudaGetDeviceCount()1

However, creating the first CUDA context fails.

Minimal reproducer:

CUresult r;

cuInit(0);

CUdevice dev;
cuDeviceGet(&dev, 0);

CUcontext ctx;
CUctxCreateParams params = {};

r = cuCtxCreate(&ctx, &params, 0, dev);

Observed behavior, running thisreproducer:

Without the kernel parameter iommu=pt, the machine usually hard-locks during cuCtxCreate().

With iommu=pt, the machine no longer hard-locks, but cuCtxCreate() returns CUDA_ERROR_UNKNOWN (999).

Application behavior

  • CUDA Samples

    • deviceQuery hangs.
  • Hashcat 7.1.2

    • Reports cuCtxCreate(): unknown error. and hangs
  • Ollama

    • Freezes the machine when attempting to initialize the GPU.

Windows comparison

The same hardware works correctly under Windows 10.

GPU compute has been verified with:

  • Hashcat

  • X-Plane

Both applications successfully use the RTX 5080 without any stability issues.

Additional observations

  • nvidia-smi communicates with the GPU normally.

  • No Xid messages are generated.

  • No PCIe AER errors are reported.

  • No IOMMU/DMAR faults appear in the kernel log.

  • boltctl reports the USB4/Thunderbolt device as authorized with a 40 Gb/s RX / 40 Gb/s TX link.

I have attached in tar.gz:

  • nvidia-bug-report.log.gz

  • minimal cuCtxCreate() reproducer (test3.cpp)

  • nvidia-smi -q output

  • lspci -vv output

  • kernel logs

nvidia-rtx5080-tb5-cuCtxCreate-report.tar.gz (911.9 KB)

Hardware: RTX 5080 over Intel USB4/TBT5 eGPU
Kernel: 7.0.0-28-generic
Driver: 610.43.02 open
CUDA UMD: 13.3

cuInit: succeeds
cuDeviceGet: succeeds
cuCtxCreate: hangs, occasionally returns 999 with iommu=pt

NVreg_DynamicPowerManagement=0x00:
First cuCtxCreate succeeded once; next invocation hung. Not reproducible as a fix.

pcie_ports=native:
GPU unavailable to NVIDIA driver.

pcie_port_pm=off:
GPU unavailable to NVIDIA driver.

thunderbolt.clx=0:
cuCtxCreate still hangs.

ACS disabled on 00:07.0:
ACS control changed from 001f to 0000.
AER was cleared.
nvidia-smi continued working.
cuCtxCreate still hung.

PTM disabled on 00:07.0:
PTM control changed from 00000003 to 00000000.
AER Unsupported Request 00100000 appeared.
Configuration did not solve the hang and caused startup instability.

God bless OpenAI and ChatGPT

Resolved with a reproducible workaround

After further testing, I found that the failure is related to the PCIe link between the Thunderbolt enclosure’s downstream bridge and the RTX 5080.

The immediate parent bridge of the GPU is:

0000:03:00.0
Intel Thunderbolt 80/120G Bridge
Barlow Ridge Hub 80G 2023
PCI ID: 8086:5786

The GPU is:

0000:04:00.0
NVIDIA GeForce RTX 5080
PCI ID: 10de:2c02

By default, the bridge-to-GPU link operated at PCIe Gen4 x4:

LnkSta: Speed 16GT/s, Width x4
LnkCtl2: Target Link Speed: 16GT/s, SpeedDis-

The system became stable after I forced this link to PCIe Gen3 x4 and disabled hardware-autonomous speed changes before loading the NVIDIA kernel modules.

The working register configuration is:

BR=0000:03:00.0

sudo setpci -s "$BR" CAP_EXP+30.w=0023:002f
sudo setpci -s "$BR" CAP_EXP+10.w=0020:0020

This performs the following:

Target Link Speed: Gen3 / 8 GT/s
Hardware Autonomous Speed Disable: enabled
Link retrain: requested once

It is important to wait until link training has completely finished before loading nvidia.ko.

The stable state is:

LnkSta: Speed 8GT/s, Width x4
LnkCtl2: Target Link Speed: 8GT/s, SpeedDis+

Raw register values:

LnkCtl2: 0063
LnkSta:  7043

I initially loaded the NVIDIA driver while the raw Link Status value was 3843. Although this already reported Gen3 x4, the Link Training bit was still set, and modprobe nvidia failed with:

modprobe: ERROR: could not insert 'nvidia': No such device

The reliable procedure waits for:

Current link speed = Gen3
Current link width = x4
Link Training bit = clear
Data Link Layer Active bit = set
Several consecutive stable readings

It then waits an additional two seconds before loading the NVIDIA modules.

After the link is stable, I load:

sudo modprobe nvidia

# NVIDIA initialization sometimes changes the target for the next retrain,
# so reassert Gen3 without requesting another retrain.
sudo setpci -s "$BR" CAP_EXP+30.w=0023:002f

sudo modprobe nvidia_modeset
sudo modprobe nvidia_uvm
sudo modprobe nvidia_drm

sudo setpci -s "$BR" CAP_EXP+30.w=0023:002f

I made this persistent with a systemd oneshot service. Automatic NVIDIA loading is blocked using:

modprobe.blacklist=nvidia,nvidia_drm,nvidia_modeset,nvidia_uvm

The service dynamically detects GPU 10de:2c02, finds its immediate parent bridge, verifies that it is Intel bridge 8086:5786, applies the Gen3 configuration, waits for link training to finish, and then explicitly loads the NVIDIA modules.

Successful service log:

egpu-gen3: GPU=0000:04:00.0, parent bridge=0000:03:00.0
egpu-gen3: before: LnkCtl2=0044 LnkSta=3044
egpu-gen3: Gen3 stable before NVIDIA: width=x4 LnkSta=7043
egpu-gen3: GPU configuration space ready: 10de:2c02
egpu-gen3: ready: LnkCtl2=0063 LnkSta=7043 width=x4

The service now completes successfully during every tested cold boot:

Active: active (exited)
Result: SUCCESS

Results after applying this workaround:

nvidia-smi: works
cuInit(): succeeds
cuDeviceGet(): succeeds
cuCtxCreate(): repeatedly succeeds
cuCtxDestroy(): repeatedly succeeds
Hashcat: works
Ollama: works

I ran multiple consecutive CUDA context creation/destruction tests and real GPU workloads without another hang.

The following changes were not required for the working setup:

No NVIDIA source patch
No HMM disable
No D3cold modification
No ACS modification
No PTM modification
No IOMMU disable

I kept:

iommu=pt
NVIDIA open driver 610.43.02
Kernel 7.0.0-28-generic

My conclusion is that the hard lock is triggered by either PCIe Gen4 operation or autonomous PCIe speed changes/retraining on the tunneled bridge-to-GPU link. The failure occurred when the first significant CUDA operation initialized the GPU, while forcing a stable Gen3 x4 link before NVIDIA driver initialization resolves it.

This is a workaround rather than an ideal permanent fix. NVIDIA may need a driver or firmware quirk for the following combination:

GPU: 10de:2c02
Parent bridge: 8086:5786
Connection: Thunderbolt 5 / tunneled PCIe

It may be useful for the driver to prevent autonomous speed changes, select a safe link speed for affected external Blackwell GPUs, or ensure that PCIe link training has completely finished before GSP initialization.

@n.ivankin would you like to adopt gen4?

echo "=== 1. Ustawienie zgody udev i Skanowanie magistrali PCIe ==="
# Tworzymy zielone światło dla udev
sudo touch /tmp/egpu_allow

# Teren czysty - udev przepuści urządzenie bez usuwania!
echo 1 | sudo tee /sys/bus/pci/rescan > /dev/null
sleep 1


sudo bash -c 'echo performance > /sys/module/pcie_aspm/parameters/policy' 2>/dev/null || true

echo "# 2. Wyłączenie ASPM L0s/L1 na mostku i karcie"
sudo setpci -s 08:00.0 CAP_EXP+10.w=0000
sudo setpci -s 09:00.0 CAP_EXP+10.w=0000

echo "# 3. Wyłączenie L1 Substates (L1.1 / L1.2)"
sudo setpci -s 08:00.0 ECAP_1E+04.l=00000000 2>/dev/null || true
sudo setpci -s 09:00.0 ECAP_1E+04.l=00000000 2>/dev/null || true

echo "# 4. Wymuszenie PCIe Gen4 (0004) + Retrain (0020) na MOSTKU (08:00.0)"
sudo setpci -s 08:00.0 CAP_EXP+30.w=0004
sudo setpci -s 08:00.0 CAP_EXP+10.w=0020

echo "# 5. Wymuszenie PCIe Gen4 (0004) + Retrain (0020) na KARCIE (09:00.0)"
sudo setpci -s 09:00.0 CAP_EXP+30.w=0004
sudo setpci -s 09:00.0 CAP_EXP+10.w=0020
sleep 1

echo "=== 4. LnkCtl2 Registers & Active Link Status / Rejestry LnkCtl2 i stan magistrali: ==="
echo "Bridge / Mostek 08:00.0 (Target Speed): $(sudo setpci -s 08:00.0 CAP_EXP+30.w)"
echo "Card / Karta   09:00.0 (Target Speed): $(sudo setpci -s 09:00.0 CAP_EXP+30.w)"

echo "--- Weryfikacja aktywnego połączenia (LnkSta) ---"
echo "Mostek 08:00.0: $(sudo lspci -vv -s 08:00.0 | grep LnkSta | xargs)"
echo "Karta  09:00.0: $(sudo lspci -vv -s 09:00.0 | grep LnkSta | xargs)"

echo "=== 5. Loading NVIDIA Drivers / Ładowanie sterownika NVIDIA ==="
sudo modprobe nvidia nvidia_uvm nvidia_modeset nvidia_drm

echo "=== 6. Setting Power Limits & Disabling Auto-PM / Ustawianie limitów mocy i wyłączenie Auto-PM ==="
sudo nvidia-smi -pl 180

sudo nvidia-smi -lmc 28002,28002
sudo nvidia-smi -lgc 3090,3090

echo "=== 7. Verifying PCIe Link Speed / Sprawdzić prędkość linku: ==="
sudo lspci -vv -s 09:00.0 | grep -iE "LnkSta:|LnkCtl2:"

powerprofilesctl set performance

# Usuwamy flagę zezwolenia, aby ewentualny kolejny rescan/unplug znów był chroniony
sudo rm -f /tmp/egpu_allow

echo "=== 8. Detaching iGPU from PCIe bus / Odcinanie iGPU z szyny PCIe ==="
echo 1 | sudo tee /sys/bus/pci/devices/0000:c7:00.0/remove

there is only some changes for you. ;)