一次 nvidia_uvm 模块异常导致的排查记录

本文最后更新于:2026年6月3日 晚上

最近在服务器上跑 MMDetection / PyTorch 实验时遇到了一个比较迷惑的问题:机器明明有 4 张 RTX 4090,nvidia-smi 也能正常识别 GPU,但 PyTorch 却突然无法使用 CUDA。由于之前同一个环境一直能正常跑实验,因此一开始很容易误判为 PyTorch、CUDA 或驱动版本不匹配。最后排查发现,问题实际出在 NVIDIA 的 nvidia_uvm 内核模块状态异常,重载该模块后恢复正常。

本文记录一下完整排查过程和解决方法。


1. 问题现象

运行分析脚本时,程序在 model.to(device) 阶段报错:

1
RuntimeError: CUDA driver initialization failed, you might not have a CUDA gpu.

对应代码大致是:

1
model.to(device)

其中 device 设置为:

1
cuda:0

同时,PyTorch 在初始化 CUDA 时给出如下 warning:

1
UserWarning: CUDA initialization: CUDA driver initialization failed, you might not have a CUDA gpu.

最开始看到这个报错,很容易以为是机器没有 GPU、CUDA 不可用,或者 PyTorch 装错了。但实际情况并不是这样。


2. 基础环境检查

首先检查 PyTorch 和 CUDA 信息:

1
2
3
4
5
6
7
8
9
10
11
12
13
conda activate openmmlab

python - <<'PY'
import torch

print("torch:", torch.__version__)
print("cuda version:", torch.version.cuda)
print("cuda available:", torch.cuda.is_available())
print("device count:", torch.cuda.device_count())

if torch.cuda.is_available():
print("gpu:", torch.cuda.get_device_name(0))
PY

输出结果如下:

1
2
3
4
torch: 2.4.1
cuda version: 12.4
cuda available: False
device count: 4

这个结果很关键:

1
2
torch.cuda.is_available() = False
torch.cuda.device_count() = 4

也就是说,PyTorch 实际上能枚举到 4 张 GPU,但是 CUDA runtime 初始化失败。

这类情况和“完全没有 GPU”不一样。它说明 NVIDIA 驱动 / NVML 层面可以看到设备,但 CUDA runtime 在创建 context 时失败。

随后检查 nvidia-smi

1
nvidia-smi

输出中可以看到:

1
2
3
NVIDIA-SMI 575.57.08
Driver Version: 575.57.08
CUDA Version: 12.9

驱动版本是 575.57.08,支持 CUDA 12.9。对于 PyTorch 2.4.1 + CUDA 12.4 来说,驱动版本足够新,因此基本可以排除“驱动版本太旧”的问题。


3. 典型误判:不是 PyTorch CUDA 版本问题

因为环境中 PyTorch 显示:

1
torch.version.cuda = 12.4

nvidia-smi 显示:

1
CUDA Version: 12.9

这里需要注意:nvidia-smi 里显示的 CUDA Version 代表当前 NVIDIA driver 最高支持的 CUDA runtime API 版本,并不等同于系统实际安装的 CUDA toolkit 版本,也不要求必须和 PyTorch 的 CUDA 版本完全一致。

只要 driver 版本足够新,一般可以向下兼容 PyTorch 自带的 CUDA runtime。因此这里不是因为 12.912.4 不一致导致的问题。


4. 尝试 GPU reset

由于之前同一环境能正常运行,只是跑了几组实验后突然出问题,因此更像是 GPU driver runtime 状态异常、残留 CUDA context 或某些监控进程占用设备。

尝试 reset GPU:

1
sudo nvidia-smi --gpu-reset -i 0,1,2,3

结果提示:

1
2
3
4
5
6
7
The following GPUs could not be reset:
GPU 00000000:18:00.0: In use by another client
GPU 00000000:3B:00.0: In use by another client
GPU 00000000:86:00.0: In use by another client
GPU 00000000:D8:00.0: In use by another client

4 devices are currently being used by one or more other processes.

这说明 GPU 当前仍然被某些 client 占用,无法直接 reset。


5. 检查设备占用

先用 fuser 查看 /dev/nvidia* 的占用情况:

1
sudo fuser -v /dev/nvidia*

最开始发现是 nvidia-persistenced 占用:

1
2
3
4
5
/dev/nvidia0:        nvidia-persistenced   1326 F.... nvidia-persiste
/dev/nvidia1: nvidia-persistenced 1326 F.... nvidia-persiste
/dev/nvidia2: nvidia-persistenced 1326 F.... nvidia-persiste
/dev/nvidia3: nvidia-persistenced 1326 F.... nvidia-persiste
/dev/nvidiactl: nvidia-persistenced 1326 F.... nvidia-persiste

停止该服务:

1
sudo systemctl stop nvidia-persistenced

再次 reset,仍然失败。

继续检查:

1
sudo fuser -v /dev/nvidia*

发现还有 gpustat 在占用设备:

1
2
3
4
5
6
/dev/nvidia0:        chenjiajun  3863230 F.... gpustat
/dev/nvidia1: chenjiajun 3863230 F.... gpustat
/dev/nvidia2: chenjiajun 3863230 F.... gpustat
/dev/nvidia3: chenjiajun 3863230 F.... gpustat
/dev/nvidiactl: chenjiajun 3863230 F...m gpustat
/dev/nvidia-uvm: chenjiajun 3863230 F.... gpustat

杀掉该进程:

1
kill -9 3863230

然后再次确认:

1
sudo fuser -v /dev/nvidia*

这时已经没有用户态进程占用了。

但此时执行 GPU reset 仍然提示:

1
In use by another client

这说明可能不是普通用户进程占用,而是 NVIDIA 驱动内部状态、UVM 模块、内核级 client 或残留 context 的问题。


6. 最终解决:重载 nvidia_uvm

尝试重载 NVIDIA Unified Virtual Memory 模块:

1
2
sudo rmmod nvidia_uvm
sudo modprobe nvidia_uvm

然后重新测试 PyTorch:

1
2
3
4
5
6
7
8
9
python - <<'PY'
import torch

print("available:", torch.cuda.is_available())
print("count:", torch.cuda.device_count())

x = torch.zeros(1, device="cuda:0")
print("CUDA OK:", x)
PY

输出恢复正常:

1
2
3
available: True
count: 4
CUDA OK: tensor([0.], device='cuda:0')

至此问题解决。


7. 原因分析

这次问题的核心现象是:

1
2
3
4
nvidia-smi 正常
PyTorch 能看到 GPU 数量
但 torch.cuda.is_available() 为 False
创建 cuda tensor 失败

这种情况下,问题通常不在于 GPU 是否存在,而在于 CUDA runtime 无法成功初始化 driver context。

nvidia_uvm 是 NVIDIA Unified Virtual Memory 相关的内核模块。PyTorch 初始化 CUDA、创建 CUDA context、分配显存时都会依赖相关驱动组件。当该模块状态异常时,可能出现如下现象:

1
2
3
4
5
NVML / nvidia-smi 可以正常枚举 GPU
CUDA runtime 初始化失败
torch.cuda.device_count() 能返回 GPU 数量
torch.cuda.is_available() 返回 False
torch.cuda.get_device_name() 或 cuda tensor 创建时报错

也就是:设备可见,但 CUDA 不可用。

这类问题在长时间多卡实验、频繁中断训练、异常退出、监控工具长时间占用 GPU、CUDA context 未正常释放时都有可能出现。


8. 推荐排查流程

以后如果再次遇到类似问题,可以按下面顺序排查。

8.1 检查 PyTorch CUDA 状态

1
2
3
4
5
6
7
8
9
10
11
12
13
14
python - <<'PY'
import torch

print("torch:", torch.__version__)
print("torch cuda:", torch.version.cuda)
print("available:", torch.cuda.is_available())
print("count:", torch.cuda.device_count())

try:
x = torch.zeros(1, device="cuda:0")
print("CUDA OK:", x)
except Exception as e:
print("CUDA FAILED:", repr(e))
PY

如果出现:

1
2
3
available: False
count: 4
CUDA driver initialization failed

说明 GPU 可见但 CUDA runtime 初始化失败。


8.2 检查驱动

1
nvidia-smi

确认 driver 正常,GPU 正常显示。


8.3 检查用户进程占用

1
sudo fuser -v /dev/nvidia*

或者:

1
sudo lsof /dev/nvidia*

如果有残留进程,例如:

1
2
3
4
5
python
torchrun
gpustat
nvtop
nvidia-smi

可以先杀掉:

1
2
3
4
pkill -9 -f gpustat
pkill -9 -f nvtop
pkill -9 -f torchrun
pkill -9 -u $USER -f python

杀进程时要谨慎,尤其是多人服务器,避免误杀其他人的任务。


8.4 重载 UVM 模块

如果确认没有重要进程占用,可以执行:

1
2
sudo rmmod nvidia_uvm
sudo modprobe nvidia_uvm

然后重新测试:

1
2
3
4
5
python - <<'PY'
import torch
print(torch.cuda.is_available(), torch.cuda.device_count())
print(torch.zeros(1, device="cuda:0"))
PY

如果恢复正常,说明问题就是 UVM 模块状态异常。


8.5 如果 rmmod 提示模块正在使用

如果执行:

1
sudo rmmod nvidia_uvm

提示:

1
Module nvidia_uvm is in use

说明仍然有进程占用 /dev/nvidia-uvm。继续查:

1
2
sudo fuser -v /dev/nvidia-uvm
sudo lsof /dev/nvidia-uvm

找到 PID 后杀掉:

1
sudo kill -9 PID

然后再重载:

1
2
sudo rmmod nvidia_uvm
sudo modprobe nvidia_uvm

8.6 实在不行再重启

如果:

1
2
3
4
5
fuser 查不到进程
lsof 查不到进程
rmmod nvidia_uvm 失败
gpu-reset 失败
PyTorch 仍然无法初始化 CUDA

那大概率是驱动内部状态已经卡死。最稳妥的方式是重启服务器:

1
sudo reboot

9. 最终可复用命令

这次问题的最小修复命令是:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
pkill -9 -f gpustat
pkill -9 -f nvtop

sudo fuser -v /dev/nvidia*

sudo rmmod nvidia_uvm
sudo modprobe nvidia_uvm

python - <<'PY'
import torch
print("available:", torch.cuda.is_available())
print("count:", torch.cuda.device_count())
print(torch.zeros(1, device="cuda:0"))
PY

如果需要 reset GPU,可以在无进程占用后执行:

1
sudo nvidia-smi --gpu-reset -i 0,1,2,3

但这次实际并不需要 reset GPU,只需要重载 nvidia_uvm 即可恢复。


10. 小结

这次问题的关键点是:

1
2
3
torch.cuda.device_count() = 4
torch.cuda.is_available() = False
CUDA driver initialization failed

这类报错不一定是 PyTorch 安装错误,也不一定是 CUDA 版本不匹配。特别是当 nvidia-smi 正常、之前环境也能正常跑时,更应该优先怀疑:

1
2
3
4
5
残留 CUDA 进程
监控工具占用
nvidia-persistenced
nvidia_uvm 状态异常
driver 内部 context 未释放

最终通过:

1
2
sudo rmmod nvidia_uvm
sudo modprobe nvidia_uvm

成功恢复。

对于多卡深度学习服务器来说,nvidia-smi 正常只能说明 NVML 层面能看到 GPU,并不等价于 CUDA runtime 一定能正常创建 context。PyTorch 能枚举 GPU 数量但不能初始化 CUDA 时,nvidia_uvm 是一个非常值得优先检查的方向。


一次 nvidia_uvm 模块异常导致的排查记录
https://blog.wholesli.de/2026/06/57307.html
作者
Jason Chen
发布于
2026年6月3日
许可协议