C
CYSKA
Consulting
EN
Navigation
OpenStack · GPU · Guide de conception

Exposer des GPU à des instances OpenStack : passthrough PCI et vGPU avec Nova et Kolla-Ansible

La chaîne complète pour donner un GPU à une instance : préparation de l'hôte (IOMMU, vfio-pci), configuration Nova via Kolla-Ansible (device_spec, alias, filtre du scheduler), flavors GPU et propriétés d'image, puis l'alternative partagée avec vGPU ou MIG par mediated devices. Se termine par les vérifications Placement et les pièges à tester sur un pilote.

Public : ingénieurs plateforme Référence : Nova 2024.1+, Kolla-Ansible, KVM, GPU datacenter NVIDIA Mise à jour : septembre 2026

Statut de ce guide

Ceci est un guide de conception, pas un retour d'expérience : la configuration ci-dessous est tirée de la documentation officielle Nova, Kolla-Ansible et NVIDIA et recoupée, mais nous ne l'avons pas encore exécutée en production pour un client. Considérez chaque bloc comme un point de départ à valider sur un nœud pilote avant tout engagement de production. Nous mettrons cette page à jour avec des résultats mesurés dès que nous en aurons.

1. Trois façons d'exposer un GPU

Passthrough PCI

La carte entière est confiée à une instance via VFIO. Performance native, aucune licence constructeur, fonctionne avec tout GPU PCI. Une carte, une instance ; pas de live migration par défaut.

vGPU / MIG (mediated devices)

Le pilote hôte découpe une carte en plusieurs GPU virtuels exposés comme périphériques mdev ; Nova les ordonnance comme ressources VGPU. Exige le logiciel de virtualisation du constructeur (NVIDIA vGPU est sous licence). Idéal pour de nombreux petits workloads d'inférence ou de notebooks.

Bare metal (Ironic)

Le serveur entier est provisionné par Ironic et les GPU sont utilisés directement par l'OS ou un nœud Kubernetes. Aucun surcoût de virtualisation, accès complet NVLink/RDMA ; l'option la moins flexible. Non détaillée ici.

2. Préparer l'hôte de calcul

Le passthrough exige VT-d ou AMD-Vi activé dans le firmware, l'IOMMU activé dans le noyau, et le GPU lié à vfio-pci plutôt qu'au pilote du constructeur. Identifiez d'abord les identifiants vendor et product : vous les réutiliserez dans chaque option Nova. Liez aussi la fonction audio de la carte quand elle partage le groupe IOMMU.

# 1. Identify the GPU: PCI address and vendor:product IDs (NVIDIA vendor id is 10de)
lspci -nn | grep -i nvidia
#   41:00.0 3D controller [0302]: NVIDIA Corporation ... [10de:2331]

# 2. Enable the IOMMU (Intel: intel_iommu=on ; AMD: amd_iommu=on), then reboot
sed -i 's/GRUB_CMDLINE_LINUX="/GRUB_CMDLINE_LINUX="intel_iommu=on iommu=pt /' /etc/default/grub
update-grub && reboot
dmesg | grep -i -e DMAR -e IOMMU | head          # after reboot: "IOMMU enabled"

# 3. Bind the GPU to vfio-pci and keep the vendor driver off the host
cat > /etc/modprobe.d/vfio.conf <<'EOF'
options vfio-pci ids=10de:2331
softdep nvidia pre: vfio-pci
softdep nouveau pre: vfio-pci
EOF
echo "blacklist nouveau" > /etc/modprobe.d/blacklist-nouveau.conf
echo vfio-pci > /etc/modules-load.d/vfio-pci.conf
update-initramfs -u && reboot

# 4. Check the binding and the IOMMU group
lspci -nnk -s 41:00.0 | grep -i 'kernel driver'   # Kernel driver in use: vfio-pci
find /sys/kernel/iommu_groups/ -type l | grep 41:00

3. Configurer Nova via Kolla-Ansible

Trois services doivent connaître le GPU : nova-compute (quels périphériques peuvent être passés, via device_spec), nova-api et nova-scheduler (l'alias que les utilisateurs demandent dans les flavors, et le PciPassthroughFilter). Kolla-Ansible fusionne les surcharges par service depuis /etc/kolla/config/nova/, et par hôte depuis un sous-répertoire au nom de l'hôte d'inventaire, pour que les réglages GPU n'atteignent que les nœuds GPU.

# /etc/kolla/config/nova/gpu-node-01/nova.conf   (per-host override: only the GPU computes)
[pci]
# Every device matching vendor/product becomes assignable; add "address" to pin specific slots
device_spec = { "vendor_id": "10de", "product_id": "2331" }
# Optional since Zed: publish PCI inventory to Placement (rollback is not supported once enabled on a host)
report_in_placement = true

# /etc/kolla/config/nova/nova-api.conf   and   /etc/kolla/config/nova/nova-scheduler.conf
[pci]
alias = { "vendor_id": "10de", "product_id": "2331", "device_type": "type-PCI", "name": "h100", "numa_policy": "preferred" }

[filter_scheduler]
enabled_filters = ComputeFilter,ComputeCapabilitiesFilter,ImagePropertiesFilter,ServerGroupAntiAffinityFilter,ServerGroupAffinityFilter,PciPassthroughFilter,AggregateInstanceExtraSpecsFilter
available_filters = nova.scheduler.filters.all_filters
pci_in_placement = true

# The alias must also be visible to nova-compute: put the same [pci] alias line in the per-host file above.

# Apply with Kolla-Ansible (nova only), then check the compute picked up the devices
kolla-ansible -i ./multinode reconfigure --tags nova
docker logs nova_compute 2>&1 | grep -i pci | tail

Placez les nœuds GPU dans un host aggregate dédié et liez les flavors GPU à ses métadonnées avec AggregateInstanceExtraSpecsFilter. Cette contrainte dirige les flavors GPU vers ces hôtes, mais n'empêche pas à elle seule les flavors ordinaires d'y être planifiés. Si les nœuds doivent être réservés, ajoutez et testez une politique explicite d'ordonnancement ou d'accès.

openstack aggregate create --zone GPU gpu
openstack aggregate set --property gpu=true gpu
openstack aggregate add host gpu gpu-node-01

4. Flavor GPU, image et premier démarrage

Le flavor demande l'alias (nom:nombre). Les GPU datacenter exposent de très grands BAR PCI : démarrez l'invité en machine q35 avec un firmware UEFI, sinon le périphérique peut ne pas s'initialiser. L'invité a ensuite besoin du pilote du constructeur et, pour les conteneurs, du NVIDIA container toolkit.

# Flavor: 1 GPU via the alias, pinned to the GPU aggregate
openstack flavor create --vcpus 16 --ram 131072 --disk 200 g1.h100.1
openstack flavor set g1.h100.1 \
  --property "pci_passthrough:alias"="h100:1" \
  --property "aggregate_instance_extra_specs:gpu"="true" \
  --property "hw:pci_numa_affinity_policy"="preferred"

# Image: q35 + UEFI so large-BAR GPUs initialise correctly
openstack image set --property hw_machine_type=q35 --property hw_firmware_type=uefi ubuntu-24.04-gpu

# Boot and verify from inside the guest
openstack server create --flavor g1.h100.1 --image ubuntu-24.04-gpu --network <NET_ID> --key-name <KEY> gpu-test-01
#   guest$ lspci -nn | grep -i nvidia
#   guest$ install the exact driver validated by the NVIDIA compatibility matrix, then reboot
#   guest$ nvidia-smi

5. Partager une carte : vGPU et MIG

Pour de nombreux petits workloads, une carte par instance gaspille de la capacité. Avec le pilote hôte NVIDIA vGPU (sous licence), la carte est exposée en mediated devices d'un type donné, et Nova les ordonnance comme ressources VGPU. Sur Ampere et suivants, MIG partitionne d'abord le GPU en matériel ; chaque instance MIG est ensuite exposée comme un type mdev. Dans les deux cas c'est le pilote hôte, et non vfio-pci, qui doit posséder la carte : cette configuration exclut le passthrough sur le même périphérique.

# Host: NVIDIA vGPU host driver installed (licensed), card NOT bound to vfio-pci
nvidia-smi                                       # host driver sees the card
ls /sys/class/mdev_bus/                          # PCI addresses that can create mediated devices
ls /sys/class/mdev_bus/0000:41:00.0/mdev_supported_types/
cat /sys/class/mdev_bus/0000:41:00.0/mdev_supported_types/nvidia-*/name   # e.g. GRID H100-20C

# Optional, Ampere+: MIG partitions (hardware slices) before vGPU
nvidia-smi -i 0 -mig 1
nvidia-smi mig -i 0 -cgi 9,9,9 -C                # three 3g.40gb instances on an 80 GB card, profile ids vary per model
/usr/lib/nvidia/sriov-manage -e 0000:41:00.0     # enable the SR-IOV VFs that carry the MIG-backed vGPUs

# /etc/kolla/config/nova/gpu-node-02/nova.conf
[devices]
enabled_mdev_types = nvidia-XXX                  # the mdev type name from mdev_supported_types

[mdev_nvidia-XXX]
device_addresses = 0000:41:00.0                  # one or more PCI addresses providing this type

kolla-ansible -i ./multinode reconfigure --tags nova

# Flavor: request one virtual GPU
openstack flavor create --vcpus 8 --ram 32768 --disk 100 g1.vgpu.1
openstack flavor set g1.vgpu.1 --property "resources:VGPU"="1" --property "aggregate_instance_extra_specs:gpu"="true"

Nova crée le mediated device à la demande au démarrage de l'instance. Installez la version exacte du pilote invité validée avec le vGPU Manager, l'OS invité, la pile CUDA et la release vGPU retenue. Le jeton client configure l'accès au service de licences NVIDIA ; supervisez l'acquisition de licence et testez la perte de connectivité plutôt que de supposer un mode de dégradation universel.

6. Vérifier avec Placement

L'inventaire VGPU apparaît sur un resource provider enfant du nœud de calcul. Pour le passthrough, report_in_placement publie l'inventaire PCI sous forme de ressources CUSTOM_PCI_VENDOR_PRODUCT ; le scheduler n'utilise les allocations Placement que lorsque pci_in_placement est également activé de manière cohérente. PciPassthroughFilter reste requis.

# Resource providers for a GPU node and their inventories
openstack resource provider list --name gpu-node-01
openstack resource provider list --in-tree <GPU_NODE_RP_UUID>          # child providers (one per mdev-capable PCI device)
openstack resource provider inventory list <CHILD_RP_UUID>             # resource_class VGPU or CUSTOM_PCI_10DE_2331, total / used

# What the scheduler would find for a flavor
openstack allocation candidate list --resource VGPU=1
openstack allocation candidate list --resource CUSTOM_PCI_10DE_2331=1

# After boot: the instance's allocations
openstack resource provider allocation show <SERVER_UUID>

7. Pièges à tester sur le pilote

  • ■Affinité NUMA : par défaut Nova exige le GPU et les CPU de l'instance sur le même nœud NUMA. Sur des hôtes denses cela bloque l'ordonnancement ; numa_policy preferred échange un peu de latence contre la plaçabilité. Mesurez les deux.
  • ■Pas de live migration pour les instances en passthrough (et contrainte pour les vGPU) : planifiez la maintenance des hôtes en fenêtres stop / start et prévenez les tenants.
  • ■Groupes IOMMU : si le GPU partage un groupe avec un autre périphérique (fonction audio, carte réseau sur le même switch PCIe), tous doivent être liés à vfio-pci sinon le passthrough échoue. Vérifiez avant de commander les serveurs.
  • ■Matrice pilotes et firmware : pilote hôte vGPU, pilote invité, versions CUDA et frameworks doivent correspondre à la table de compatibilité du constructeur ; épinglez-les dans vos images et mettez-les à niveau ensemble.
  • ■Licences : un vGPU sans serveur de licences joignable se dégrade silencieusement. Supervisez l'état de licence depuis les invités et alertez dessus.
  • ■Observabilité : exportez les métriques GPU (DCGM exporter dans les invités ou sur bare metal) dans la même chaîne Prometheus que la plateforme ; un GPU à 0 % sur un nœud chargé est un bug d'ordonnancement, pas de la capacité libre.
  • ■Couche suivante : une fois que des instances démarrent avec un GPU fonctionnel, provisionnez Kubernetes sur des flavors GPU et installez le NVIDIA GPU Operator ; servez les modèles avec vLLM. Ce sera un guide distinct une fois que nous l'aurons exécuté.
Lire le guide observabilité →