# Container Device Interface (CDI) Usage Guide ## Overview Container Device Interface (CDI) enables defining specifications that allow greater control on how devices are exposed to containers. Instead of running containers in `--privileged` mode, which exposes every host device, or manually bind-mounting `/dev/dri` paths, CDI lets you request devices by name — the runtime handles device nodes, permissions, and mounts automatically. CDI uses predefined YAML specification files in `/etc/cdi/` to describe the device files, mounts, and environment variables that are exposed to the container. | CDI Kind | Specification File | Device Names | Description | |----------|-----------|--------------|-------------| | `intel.com/gpu` | `intel.com-gpu.yaml` | `card0`, `card1`, … | Intel® GPU devices [Physical Function (PF) and SR-IOV Virtual Functions (VFs)] | | `intel.com/npu` | `intel.com-npu.yaml` | `npu0` | Intel® NPU accelerator device | --- ## Prerequisites - Edge Node Infrastructure Blueprint image deployed - Docker Engine version 25 or newer (with CDI support enabled), Podman version 4.1 or newer, or containerd version 1.7 or newer - Intel GPU with SR-IOV VFs enabled - Intel NPU hardware present (optional) - `sudo` access --- ## Step 1: CDI Specification Generation (Automatic on First Boot) In Edge Node Infrastructure Blueprint images, the CDI specification generation service is **automatically started on first boot**. The service includes: - **GPU specifications**: Generated using the official `intel-cdi-specs-generator-gpu` binary from [Intel® Resource Drivers for Kubernetes ](https://github.com/intel/intel-resource-drivers-for-kubernetes) - **NPU specifications**: Generated using the custom `intel-cdi-npu-generator.sh` bash script The CDI generation service is pre-configured with: 1. **Udev rules** — triggers CDI regeneration when GPU VFs or NPU devices appear 2. **Systemd service** (`intel-cdi-regenerate.service`) — runs both GPU and NPU generators 3. **Systemd timer** — periodic fallback regeneration (every 5 minutes) ### Verify CDI Specification Generation After the first boot, verify that the service ran successfully: ```bash systemctl status intel-cdi-regenerate.service journalctl -u intel-cdi-regenerate.service --no-pager -n 20 ``` Verify that the specifications were generated: ```bash ls /etc/cdi/ # Expected: intel.com-gpu.yaml intel.com-npu.yaml ``` ### Manual Regeneration (If Needed) If you need to trigger specification regeneration manually: ```bash sudo systemctl start intel-cdi-regenerate.service ``` Or run the generators directly: ```bash # Scripts are located at /opt/edge/scripts/cdi sudo /opt/edge/scripts/cdi/intel-cdi-specs-generator-gpu --cdi-dir /etc/cdi gpu sudo bash /opt/edge/scripts/cdi/intel-cdi-npu-generator.sh --cdi-dir /etc/cdi ``` --- ## Step 2: Configure Docker Daemon for CDI Check `/etc/docker/daemon.json`: ```json { "features": { "cdi": true }, "cdi-spec-dirs": ["/etc/cdi"] } ``` Restart Docker daemon after any changes: ```bash sudo systemctl restart docker ``` --- ## Step 3: Run Containers with CDI Devices ### GPU Container Use the `--device` flag with the CDI device name from the specification file: ```bash docker run --rm --device intel.com/gpu=card1 ubuntu:24.04 ls /dev/dri/ ``` Expected output — the container sees only the assigned GPU device: ```text card1 renderD129 ``` ### NPU Container ```bash docker run --rm --device intel.com/npu=npu0 ubuntu:24.04 ls /dev/accel/ ``` Expected output: ```text accel0 ``` ### Multiple Devices Assign a GPU and an NPU to the same container: ```bash docker run --rm \ --device intel.com/gpu=card1 \ --device intel.com/npu=npu0 \ ubuntu:24.04 sh -c "ls /dev/dri/ && ls /dev/accel/" ``` ### Multiple GPU VFs Assign two GPU VFs to a single container: ```bash docker run --rm \ --device intel.com/gpu=card1 \ --device intel.com/gpu=card2 \ ubuntu:24.04 ls /dev/dri/ ``` --- ## Step 4: Use CDI Devices with Docker Compose Reference CDI device names directly in your Docker Compose file: ```yaml services: gpu-workload: image: my-inference-app:latest devices: - intel.com/gpu=card1 - intel.com/npu=npu0 ``` Run: ```bash docker compose up ``` GPU-only example: ```yaml services: gpu-worker: image: my-gpu-worker:latest devices: - intel.com/gpu=card1 ``` --- ## CDI Specification Format Reference The GPU specification generated by `intel-cdi-specs-generator-gpu` follows the standard CDI 0.5.0 format: ```yaml --- cdiVersion: 0.5.0 kind: intel.com/gpu devices: - name: card1 containerEdits: deviceNodes: - path: /dev/dri/card1 hostPath: /dev/dri/card1 type: c - path: /dev/dri/renderD129 hostPath: /dev/dri/renderD129 type: c mounts: - hostPath: /dev/dri/by-path/pci-0000:00:02.1-card containerPath: /dev/dri/by-path/pci-0000:00:02.1-card options: - bind - rw type: none ``` The NPU specification generated by `intel-cdi-npu-generator.sh`: ```yaml --- cdiVersion: "0.5.0" kind: intel.com/npu devices: - name: npu0 containerEdits: deviceNodes: - path: /dev/accel/accel0 hostPath: /dev/accel/accel0 type: c ``` --- ## Troubleshooting ### No CDI Specification Files in `/etc/cdi/` ```bash # Scripts are located at /opt/edge/scripts/cdi sudo /opt/edge/scripts/cdi/intel-cdi-specs-generator-gpu --cdi-dir /etc/cdi gpu sudo bash /opt/edge/scripts/cdi/intel-cdi-npu-generator.sh --cdi-dir /etc/cdi ``` ### Docker Says "CDI device not found" 1. Verify that the Docker Engine version is 25 or newer: ```bash docker --version ``` 2. Verify that CDI is enabled in `/etc/docker/daemon.json`: ```json { "features": { "cdi": true }, "cdi-spec-dirs": ["/etc/cdi"] } ``` 3. Restart the Docker service: ```bash sudo systemctl restart docker ``` ### NPU Not Detected Verify that the NPU driver is loaded and the device exists: ```bash ls /sys/bus/pci/drivers/intel_vpu/ ls /dev/accel/ ``` If `/dev/accel/` is empty, load the driver: ```bash sudo modprobe intel_vpu ``` For kernel version 6.17 or newer, verify that the NPU firmware is present: ```bash ls /lib/firmware/intel/vpu/ dmesg | grep -i vpu ``` ### GPU VFs Not Showing in CDI Specification Verify that SR-IOV VFs are enabled: ```bash cat /sys/bus/pci/devices/0000:00:02.0/sriov_numvfs ls /dev/dri/renderD* ``` If the VFs are not created, enable them first, then regenerate the CDI specifications. --- ## References - [Intel GPU Plugin — CDI Support](https://github.com/intel/intel-device-plugins-for-kubernetes/tree/main/cmd/gpu_plugin#cdi-support) - [Intel GPU Plugin — CDI and Docker Daemon Usage](https://github.com/intel/intel-device-plugins-for-kubernetes/blob/main/cmd/gpu_plugin/cdi.md) - [Intel NPU Plugin — CDI Leverage](https://github.com/intel/intel-device-plugins-for-kubernetes/tree/main/cmd/npu_plugin#leverage-cdi) - [CDI Specification](https://github.com/cncf-tags/container-device-interface/blob/main/SPEC.md)