Skip to content

Commit 916ae2d

Browse files
committed
99-mellanox: fix array skew and abort on degraded NIC
Three independent sysfs globs (infiniband_verbs, infiniband, infiniband_mad) built the parallel arrays assuming equal counts and aligned ordering. When a PCI function exposed a verbs device but no infiniband/ class entry (BlueField DPU, SF/SR-IOV representor, down port), ifaces[] ended up shorter than devices[]. The mount loop only range-checked against ${#devices[@]}, so it dereferenced an unset ifaces[id] and, under set -euo pipefail, aborted the hook: /etc/enroot/hooks.d/99-mellanox.sh: line 88: ifaces[id]: unbound variable [ERROR] /etc/enroot/hooks.d/99-mellanox.sh exited with return code 1 This killed every container launch on affected nodes. Observed breaking NCCL alltoall_perf_mpi, all_gather_perf_mpi, all_reduce_perf_mpi, and reduce_scatter_perf_mpi. Fix: enumerate per PCI function anchored on infiniband_verbs and resolve the iface and management nodes from the same <bdf> directory, so the arrays are always index-aligned regardless of which sysfs sub-entries are present. A missing iface is now an explicit common::err (degraded NIC detected) rather than an unbound-variable crash, preserving the job-blocking behavior with a clear message. umad/issm entries are guarded with [ -n ] since their absence is less critical. Signed-off-by: Eric Lordahl <elordahl@nvidia.com>
1 parent ead3a25 commit 916ae2d

1 file changed

Lines changed: 39 additions & 19 deletions

File tree

‎conf/hooks/99-mellanox.sh‎

Lines changed: 39 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -39,28 +39,41 @@ declare -a issms=()
3939
declare -a umads=()
4040
declare -A providers=()
4141

42-
# Lookup all the devices and their respective driver.
42+
# Enumerate per PCI function anchored on infiniband_verbs, resolving the
43+
# interface and management nodes from the same <bdf> directory. Three
44+
# independent globs over different sysfs subtrees previously left ifaces[]
45+
# shorter than devices[] when a function had no infiniband/ entry (DPU,
46+
# SF/SR-IOV representor, down port), causing "ifaces[id]: unbound variable"
47+
# under set -u and aborting every container launch on the affected node.
4348
for uevent in /sys/bus/pci/drivers/mlx?_core/*/infiniband_verbs/*/uevent; do
4449
case "${uevent}" in
45-
*mlx4*) drivers+=("mlx4") ;;
46-
*mlx5*) drivers+=("mlx5") ;;
50+
*mlx4*) driver="mlx4" ;;
51+
*mlx5*) driver="mlx5" ;;
4752
*) continue ;;
4853
esac
54+
55+
# .../0000:xx:00.0/infiniband_verbs/uverbsN/uevent -> .../0000:xx:00.0
56+
pcidir="${uevent%/infiniband_verbs/*}"
57+
58+
drivers+=("${driver}")
4959
devices+=("$(. "${uevent}"; echo "/dev/${DEVNAME}")")
50-
done
5160

52-
# Lookup all the interfaces.
53-
for uevent in /sys/bus/pci/drivers/mlx?_core/*/infiniband/*/uevent; do
54-
ifaces+=("$(. "${uevent}"; echo "${NAME}")")
55-
done
61+
iface=""
62+
for ib_uevent in "${pcidir}"/infiniband/*/uevent; do
63+
iface="$(. "${ib_uevent}"; echo "${NAME}")"
64+
break
65+
done
66+
ifaces+=("${iface}")
5667

57-
# Lookup all the management devices.
58-
for uevent in /sys/bus/pci/drivers/mlx?_core/*/infiniband_mad/*/uevent; do
59-
case "${uevent}" in
60-
*issm*) issms+=("$(. "${uevent}"; echo "/dev/${DEVNAME}")") ;;
61-
*umad*) umads+=("$(. "${uevent}"; echo "/dev/${DEVNAME}")") ;;
62-
*) continue ;;
63-
esac
68+
umad="" issm=""
69+
for mad_uevent in "${pcidir}"/infiniband_mad/*/uevent; do
70+
case "${mad_uevent}" in
71+
*issm*) issm="$(. "${mad_uevent}"; echo "/dev/${DEVNAME}")" ;;
72+
*umad*) umad="$(. "${mad_uevent}"; echo "/dev/${DEVNAME}")" ;;
73+
esac
74+
done
75+
umads+=("${umad}")
76+
issms+=("${issm}")
6477
done
6578

6679
# Hide all the device entries in sysfs by default and mount RDMA CM.
@@ -85,13 +98,20 @@ for id in ${MELLANOX_VISIBLE_DEVICES//,/ }; do
8598
fi
8699
providers["${drivers[id]}"]=true
87100
enroot-mount --root "${ENROOT_ROOTFS}" - <<< "${devices[id]} ${devices[id]} none x-create=file,bind,ro,nosuid,noexec,private"
101+
if [ -z "${ifaces[id]}" ]; then
102+
common::err "MELLANOX device id ${id} (${devices[id]}) has no InfiniBand interface — degraded NIC detected, refusing to start container"
103+
fi
88104
ln -s "$(common::realpath "/sys/class/infiniband/${ifaces[id]}")" "${ENROOT_ROOTFS}/sys/class/infiniband/${ifaces[id]}"
89105
ln -s "$(common::realpath "/sys/class/infiniband_verbs/${devices[id]##*/}")" "${ENROOT_ROOTFS}/sys/class/infiniband_verbs/${devices[id]##*/}"
90106

91107
if [ -n "${ENROOT_ALLOW_SUPERUSER-}" ] && [ "$(awk '{print $2}' /proc/self/uid_map)" -eq 0 ]; then
92-
enroot-mount --root "${ENROOT_ROOTFS}" - <<< "${umads[id]} ${umads[id]} none x-create=file,bind,ro,nosuid,noexec,private,nofail,silent"
93-
enroot-mount --root "${ENROOT_ROOTFS}" - <<< "${issms[id]} ${issms[id]} none x-create=file,bind,ro,nosuid,noexec,private,nofail,silent"
94-
ln -s "$(common::realpath "/sys/class/infiniband_mad/${umads[id]##*/}")" "${ENROOT_ROOTFS}/sys/class/infiniband_mad/${umads[id]##*/}"
95-
ln -s "$(common::realpath "/sys/class/infiniband_mad/${issms[id]##*/}")" "${ENROOT_ROOTFS}/sys/class/infiniband_mad/${issms[id]##*/}"
108+
if [ -n "${umads[id]}" ]; then
109+
enroot-mount --root "${ENROOT_ROOTFS}" - <<< "${umads[id]} ${umads[id]} none x-create=file,bind,ro,nosuid,noexec,private,nofail,silent"
110+
ln -s "$(common::realpath "/sys/class/infiniband_mad/${umads[id]##*/}")" "${ENROOT_ROOTFS}/sys/class/infiniband_mad/${umads[id]##*/}"
111+
fi
112+
if [ -n "${issms[id]}" ]; then
113+
enroot-mount --root "${ENROOT_ROOTFS}" - <<< "${issms[id]} ${issms[id]} none x-create=file,bind,ro,nosuid,noexec,private,nofail,silent"
114+
ln -s "$(common::realpath "/sys/class/infiniband_mad/${issms[id]##*/}")" "${ENROOT_ROOTFS}/sys/class/infiniband_mad/${issms[id]##*/}"
115+
fi
96116
fi
97117
done

0 commit comments

Comments
 (0)