2. IGX系统架构与容器化基础

NVIDIA IGX 是一套面向工业与医疗边缘场景的“软硬协同”平台。要理解它的容器化部署与远程运维,必须先建立一条从硬件到容器运行时的完整认知链:IGX Orin 模组提供算力与安全内核,IGX 板卡把模组扩展为可接入工业现场的平台,JetPack/L4T提供操作系统与 CUDA 软件栈,Docker/containerd负责容器生命周期管理,而nvidia-container-toolkit则把 GPU 设备安全地暴露给容器。这五层各司其职,缺一不可。

一、从模组到板卡:IGX 的硬件分层

IGX Orin 模组是核心计算单元,它把 GPU、CPU、内存、存储以及一颗独立的安全芯片集成在一块紧凑的模块上。以 IGX Orin 700 为例,它提供约 275 TOPS 的 AI 算力,并支持 ECC 内存与安全启动,这使得它能够满足工业现场对可靠性和功能安全的要求。模组本身并不是一块可以直接接线的“板子”,它需要通过板对板连接器安装到载板上。

IGX 板卡(开发套件/载板)则承担了“对外接口”的角色:它把模组的 PCIe、USB、以太网、MIPI CSI 等信号引出,形成可连接工业相机、传感器、PLC 和网络设备的物理端口。同时,板卡还提供电源管理、散热设计和安全启动所需的固件环境。可以这样理解:模组决定“算得多快、多安全”,板卡决定“能接什么、怎么接”。在部署容器之前,确认板卡上的网口、相机接口和存储接口是否与现场设备匹配,是第一步实际工作。

二、JetPack 与 L4T:容器运行的操作系统底座

JetPack 是 NVIDIA 为 Jetson/IGX 系列提供的软件开发套件,它并不是一个单独的操作系统,而是一组组件的集合:L4T(Linux for Tegra)提供基于 Ubuntu 的根文件系统、内核、引导程序和硬件驱动;CUDA、cuDNN、TensorRT 等提供 GPU 计算与推理能力;容器运行时相关组件也在其中。L4T 的版本号与 JetPack 版本号一一对应,例如 JetPack 6.x 对应 L4T 36.x,底层是 Ubuntu 22.04。

这里有一个实际部署中必须注意的点:容器内使用的 CUDA 版本、驱动版本必须与宿主 L4T 的版本兼容。如果宿主的 L4T 是 36.3,而容器镜像要求 CUDA 12.6 以上,就可能出现 GPU 无法调用的情况。因此,在拉取镜像前,先用以下命令确认宿主环境:

# 查看 L4T 版本
cat /etc/nv_tegra_release

# 查看 JetPack 版本
cat /etc/nv_jetpack_release

# 查看 GPU 与驱动状态
nvidia-smi

如果 nvidia-smi 能正常输出 GPU 型号、驱动版本和显存占用,说明宿主 GPU 栈是健康的,这是后续容器调用 GPU 的前提。

三、Docker 与 containerd:谁在真正运行容器

很多初学者会把 Docker 等同于容器,实际上 Docker 只是容器生态中的“上层工具”。在 IGX 上,典型的调用链是:用户执行 docker run,Docker CLI 把请求发给 Docker Daemon(dockerd),dockerd 再通过 containerd 创建容器,containerd 调用 runc 真正启动进程。也就是说,containerd 是底层的容器运行时,Docker 是面向用户的管理工具。

这个分层在 IGX 上尤其重要,因为 Kubernetes 默认使用的容器运行时就是 containerd,而不是 Docker。如果现场采用 K8s 做远程编排,节点上通常只安装 containerd,此时 docker 命令可能根本不存在。因此,在 IGX 上做容器化部署时,需要明确当前平台使用的是哪种运行时:

# 查看 containerd 状态
systemctl status containerd

# 查看 Docker 状态
systemctl status docker

# 查看 K8s 节点使用的运行时
kubectl get nodes -o wide

理解这一点后,就能明白为什么有些镜像用 docker pull 能拉到,而 K8s 却提示镜像不存在——因为两者可能使用不同的镜像存储命名空间。

四、nvidia-container-toolkit:让容器看见 GPU

默认情况下,容器是隔离的,它看不到宿主上的 /dev/nvidia0、/dev/nvidiactl 等设备节点,也加载不了 NVIDIA 驱动库。nvidia-container-toolkit 的作用,就是在容器启动时,把宿主上的 GPU 设备节点、驱动库和必要的工具自动挂载进容器,使容器内的进程能够像在宿主上一样调用 GPU。

它的工作方式可以概括为三步:第一,配置容器运行时(Docker 或 containerd),使其在创建容器时调用 nvidia-container-runtime;第二,nvidia-container-runtime 读取环境变量 NVIDIA_VISIBLE_DEVICES,决定暴露哪些 GPU;第三,通过 hook 机制把设备节点和库文件注入容器。配置完成后,用 --gpus all 或 --runtime=nvidia 启动容器,容器内执行 nvidia-smi 就能看到 GPU。

# 配置 Docker 使用 nvidia 运行时
sudo nvidia-ctk runtime configure --runtime=docker
sudo systemctl restart docker

# 验证容器内 GPU 可见性
docker run --rm --gpus all nvidia/cuda:12.2.0-base-ubuntu22.04 nvidia-smi

如果这条命令能输出与宿主一致的 GPU 信息,说明 GPU 容器运行时链路已经打通;如果报错 “could not select device driver”,则说明 toolkit 未正确配置或运行时未重启。

IGX 容器化部署五层架构与 GPU 调用链 硬件层 IGX Orin 模组(GPU/CPU/安全芯片) IGX 板卡(PCIe/网口/CSI/电源) 工业相机 / 传感器 / PLC / 网络 操作系统与软件栈层 L4T(Ubuntu 22.04 + 内核 + 驱动) JetPack(CUDA / cuDNN / TensorRT) nvidia-smi / 驱动库 容器运行时层 Docker CLI docker run / pull dockerd Docker Daemon containerd K8s 默认运行时 runc 启动进程 GPU 容器运行时层 nvidia-container-toolkit nvidia-container-runtime hook 注入设备节点与驱动库 容器内进程可见 GPU:nvidia-smi 正常输出 失败信号 could not select device driver 成功信号 GPU 型号/显存 与宿主一致

五、把五层串起来:一次 GPU 容器启动发生了什么

假设现场要在 IGX 上运行一个基于 TensorRT 的视觉推理容器,实际过程如下:首先确认板卡已正确供电并接入相机;然后检查 L4T 版本与 nvidia-smi 输出;接着确认 containerd 或 Docker 已配置 nvidia 运行时;最后执行 docker run --gpus all 或对应的 K8s Pod 配置。容器启动时,nvidia-container-runtime 会把 /dev/nvidia* 和驱动库挂载进去,容器内的推理进程才能调用 GPU。

如果中间任何一层断裂,表现出的现象是不同的:L4T 版本不匹配,容器可能启动但 GPU 调用失败;containerd 未配置 nvidia 运行时,容器内看不到 GPU;toolkit 未安装,--gpus 参数直接报错。因此,排障时应按“硬件→系统→运行时→GPU 运行时→容器”的顺序逐层确认,而不是一上来就怀疑镜像问题。

实用检查清单:在 IGX 上部署 GPU 容器前,依次执行:① cat /etc/nv_tegra_release 确认 L4T 版本;② nvidia-smi 确认宿主 GPU 正常;③ systemctl status containerd 或 docker 确认运行时;④ nvidia-ctk runtime configure 配置 GPU 运行时;⑤ 用 nvidia/cuda 基础镜像做一次最小验证。五步全部通过,再部署业务容器。

理解这五层关系后,后续的镜像构建、容器编排和远程运维才有稳固的落脚点。IGX 的容器化并不是简单地把应用塞进 Docker,而是要让 GPU、驱动、运行时和容器四者版本与配置彼此对齐。