In /proc/stat, guest is already inside user (and guest_nice inside nice). Peardata was adding guest into the total again, which shrinks every other slice — including idle.
CI / test (push) Successful in 1m0s
Release rolling / release (push) Failing after 1m50s

readFileCached capped at 64KB. On 56-core hosts /proc/interrupts (and similar) often exceeds that — reads were silently truncated. Buffer now grows (up to 1MB). That didn’t break system.cpu idle (aggregate line is first), but it was a real high-core regression.
This commit is contained in:
Raven Scott
2026-07-22 12:36:30 -04:00
parent 6570276179
commit da9541528e
5 changed files with 114 additions and 44 deletions
+18 -3
View File
@@ -1,6 +1,8 @@
import fs from 'fs'
const READ_BUF = Buffer.alloc(65536)
/** Shared buffer — grows if a read fills it (e.g. /proc/interrupts on 56-core hosts). */
let readBuf = Buffer.alloc(65536)
const MAX_READ_BUF = 1024 * 1024
const SMALL_BUF = Buffer.alloc(8192)
const fdCache = new Map()
@@ -18,8 +20,21 @@ export function readFileCached(path) {
}
if (!entry) return null
try {
const bytesRead = fs.readSync(entry.fd, READ_BUF, 0, READ_BUF.length, 0)
return READ_BUF.toString('utf8', 0, bytesRead)
let bytesRead = fs.readSync(entry.fd, readBuf, 0, readBuf.length, 0)
// Filled the buffer → likely truncated; grow and retry (common on high-core /proc files)
while (bytesRead === readBuf.length && readBuf.length < MAX_READ_BUF) {
readBuf = Buffer.alloc(Math.min(readBuf.length * 4, MAX_READ_BUF))
bytesRead = fs.readSync(entry.fd, readBuf, 0, readBuf.length, 0)
}
if (bytesRead === readBuf.length) {
// Still truncated at cap — full read for correctness
try {
return fs.readFileSync(path, 'utf8')
} catch {
/* fall through with truncated buffer */
}
}
return readBuf.toString('utf8', 0, bytesRead)
} catch {
return null
}