Add a second GPU card to the monitor page
The 3080 was invisible because the stats parser only ever described GPU 0.
This commit is contained in:
@@ -95,35 +95,54 @@ function vv_docker_stopped(): array {
|
||||
return $containers;
|
||||
}
|
||||
|
||||
function vv_gpu_stats(): array {
|
||||
$out = shell_exec('nvidia-smi --query-gpu=name,memory.used,memory.total,utilization.gpu,temperature.gpu,power.draw,utilization.encoder,utilization.decoder --format=csv,noheader,nounits 2>/dev/null');
|
||||
if (!$out) return ['available' => false];
|
||||
// Every installed GPU, one entry per card. Parsed line by line — nvidia-smi emits one row
|
||||
// per GPU, so splitting the whole output on commas (as this once did) runs the rows together
|
||||
// and only ever describes GPU 0.
|
||||
function vv_gpu_stats_all(): array {
|
||||
$out = shell_exec('nvidia-smi --query-gpu=index,uuid,name,memory.used,memory.total,utilization.gpu,temperature.gpu,power.draw,utilization.encoder,utilization.decoder --format=csv,noheader,nounits 2>/dev/null');
|
||||
if (!$out) return [];
|
||||
|
||||
$parts = array_map('trim', explode(',', $out));
|
||||
$power = is_numeric($parts[5] ?? '') ? round((float)$parts[5], 1) : null;
|
||||
return [
|
||||
'available' => true,
|
||||
'name' => $parts[0] ?? '',
|
||||
'memory_used' => (int)($parts[1] ?? 0),
|
||||
'memory_total' => (int)($parts[2] ?? 0),
|
||||
'utilization' => (int)($parts[3] ?? 0),
|
||||
'temperature' => (int)($parts[4] ?? 0),
|
||||
'power_w' => $power,
|
||||
'enc_pct' => (int)($parts[6] ?? 0),
|
||||
'dec_pct' => (int)($parts[7] ?? 0),
|
||||
];
|
||||
$gpus = [];
|
||||
foreach (explode("\n", trim($out)) as $line) {
|
||||
if (!$line) continue;
|
||||
$p = array_map('trim', explode(',', $line));
|
||||
if (count($p) < 10) continue;
|
||||
$gpus[] = [
|
||||
'available' => true,
|
||||
'index' => (int)$p[0],
|
||||
'uuid' => $p[1],
|
||||
'name' => $p[2],
|
||||
'memory_used' => (int)$p[3],
|
||||
'memory_total' => (int)$p[4],
|
||||
'utilization' => (int)$p[5],
|
||||
'temperature' => (int)$p[6],
|
||||
'power_w' => is_numeric($p[7]) ? round((float)$p[7], 1) : null,
|
||||
'enc_pct' => (int)$p[8],
|
||||
'dec_pct' => (int)$p[9],
|
||||
];
|
||||
}
|
||||
return $gpus;
|
||||
}
|
||||
|
||||
// Kept for the existing single-GPU consumers — same shape as before, always GPU 0.
|
||||
function vv_gpu_stats(): array {
|
||||
$gpus = vv_gpu_stats_all();
|
||||
return $gpus[0] ?? ['available' => false];
|
||||
}
|
||||
|
||||
// gpu_uuid is included so each process can be attributed to the card it is actually running
|
||||
// on. Without it a two-GPU box shows every process under every card.
|
||||
function vv_gpu_processes(): array {
|
||||
$out = shell_exec('nvidia-smi --query-compute-apps=pid,used_gpu_memory,name --format=csv,noheader,nounits 2>/dev/null');
|
||||
$out = shell_exec('nvidia-smi --query-compute-apps=gpu_uuid,pid,used_gpu_memory,name --format=csv,noheader,nounits 2>/dev/null');
|
||||
$procs = [];
|
||||
foreach (explode("\n", trim($out ?? '')) as $line) {
|
||||
if (!$line) continue;
|
||||
$parts = array_map('trim', explode(',', $line));
|
||||
$procs[] = [
|
||||
'pid' => $parts[0] ?? '',
|
||||
'memory_mb' => $parts[1] ?? '',
|
||||
'name' => $parts[2] ?? '',
|
||||
'gpu_uuid' => $parts[0] ?? '',
|
||||
'pid' => $parts[1] ?? '',
|
||||
'memory_mb' => $parts[2] ?? '',
|
||||
'name' => $parts[3] ?? '',
|
||||
];
|
||||
}
|
||||
return $procs;
|
||||
|
||||
Reference in New Issue
Block a user