Read NVLink and GPU-to-adapter distance from nvidia-smi topo

The release binary is built without cgo, so without NVML, and NVML was
the only source of NVLink peers: on every NVLink machine the portable
agent reported none, and tensor-parallel groups were chosen by GPU index.
Discovery now reads `nvidia-smi topo -m` after either path, for the
NVLink peers (kept from NVML where it gave them), each card's NUMA node,
and how far each network adapter is from it - PIX, PXB, PHB, NODE or
SYS - which travels to the control plane as nic_paths for placement to
use. Both the NICn-with-legend layout of newer drivers and the
adapter-named columns of older ones are read.

Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com>
This commit is contained in:
Ilker ManapandClaude Opus 5.5 committed 2026-09-29 00:09:26 +02:00
1 parent 22bb098247
commit bf2d171e89
8 files changed
+363 -30

No files matched your search

+3
View File
@@ -3,6 +3,7 @@ package agentsvc
import (
"fmt"
"maps"
"time"
llmgwv1 "gitea.mynodes.xyz/ilker/llmgw/api/gen/llmgw/v1"
@@ -59,6 +60,7 @@ func NodeFromRegister(r *llmgwv1.Register) inventory.Node {
UtilizationPercent: int(g.GetUtilizationPercent()),
CUDAVersion: g.GetCudaVersion(),
NVLinkPeers: intSlice(g.GetNvlinkPeers()),
NICPaths: maps.Clone(g.GetNicPaths()),
Health: discovery.GPUHealth{
ECCErrors: int(g.GetEccErrors()),
TemperatureC: int(g.GetTemperatureC()),
@@ -112,6 +114,7 @@ func RegisterFromInventory(nodeID, hostname, mgmtAddr, agentVersion string,
UtilizationPercent: int32(g.UtilizationPercent),
CudaVersion: g.CUDAVersion,
NvlinkPeers: int32Slice(g.NVLinkPeers),
NicPaths: maps.Clone(g.NICPaths),
Problems: g.Health.Problems,
TemperatureC: int32(g.Health.TemperatureC),
EccErrors: int32(g.Health.ECCErrors),