stablyai/orca · error · Error
Could not find helper owned by sidecar ${sidecarPid}
Error message
Could not find helper owned by sidecar ${sidecarPid} What it means
waitForHelper polls process listings to find the computer-use helper child spawned by a sidecar (matching sidecar pid as pgid, helper pid, and a command line containing the helper path and ' --agent '). It throws when the helper never appears within the poll budget — i.e. the helper did not start or its process-tree shape does not match the regex assumptions.
Source
Thrown at config/scripts/macos-computer-helper-owner-loss-benchmark.mjs:178
const output = execFileSync('ps', ['-axo', 'pid=,ppid=,pgid=,command='], {
encoding: 'utf8',
maxBuffer: 20 * 1024 * 1024
})
for (const line of output.split('\n')) {
const match = line.trim().match(/^(\d+)\s+(\d+)\s+(\d+)\s+(.+)$/)
if (
match &&
Number(match[2]) === sidecarPid &&
Number(match[3]) === Number(match[1]) &&
match[4].includes(helperPath) &&
match[4].includes(' --agent ')
) {
return { pid: Number(match[1]), pgid: Number(match[3]), command: match[4] }
}
}
await sleep(50)
}
throw new Error(`Could not find helper owned by sidecar ${sidecarPid}`)
}
function socketPathFromCommand(command) {
const match = command.match(/ --agent (.+?) --token-file /)
if (!match) {
throw new Error(`Could not read helper socket path from command: ${command}`)
}
return match[1]
}
function connectInvalidPeer(socketPath) {
return new Promise((resolve, reject) => {
const socket = net.createConnection(socketPath)
let accepted = false
const timeout = setTimeout(() => {
socket.destroy()
reject(new Error('Invalid-peer connection timed out'))
}, 5_000)View on GitHub (pinned to 1136503c6a)
Solutions
- Run the sidecar manually and inspect its stderr/logs to see why the helper did not spawn.
- Capture the ps output the poller reads and confirm the regex captures pid/pgid/command as expected on this macOS version.
- Verify the helper binary exists at helperPath and is signed/notarized so it is not killed on launch.
- Increase the poll budget if the helper is merely slow to appear.
Example fix
// before
throw new Error(`Could not find helper owned by sidecar ${sidecarPid}`)
// after (diagnostics)
const ps = readPsOutput()
throw new Error(`Could not find helper owned by sidecar ${sidecarPid}; ps lines=${ps.length}; matching children=${ps.filter(l => l.includes(String(sidecarPid))).length}`) Defensive patterns
Strategy: retry
Validate before calling
async function waitHelperOrDiagnose(sidecarPid, budgetMs) {
const start = Date.now()
while (Date.now() - start < budgetMs) {
const h = findHelper(sidecarPid); if (h) return h
await sleep(50)
}
throw new Error(`Helper not found; children=${readPs().filter(l => l.includes(String(sidecarPid))).length}`)
} Type guard
const isHelperRecord = (h) => h && Number.isInteger(h.pid) && typeof h.command === 'string'
Try / catch
try {
helper = await waitForHelper(sidecar.child.pid)
} catch (e) {
if (/Could not find helper/.test(e.message)) { /* inspect sidecar stderr, raise budget, retry once */ }
throw e
} Prevention
- Capture sidecar stderr so a failed helper spawn is visible.
- Verify helper binary path and code-signing/notarization before the run.
- Log the ps lines the poller scans to catch macOS format drift.
When it happens
Trigger: The sidecar failed to spawn the helper, the helper exited immediately, the platform's ps output format differs so the regex never matches, or the polling budget elapsed before the helper appeared (slow spawn).
Common situations: macOS version differences changing ps column layout, code-signing/notarization blocking the helper launch, a security policy killing the helper, or the helper binary path shifting so helperPath no longer matches.
Related errors
- The production watchdog is macOS-only; run this benchmark on
- Could not read watchdog child RSS for PID ${pid}
- Could not read physical footprint for PIDs ${pids.join(', ')
- Could not read CPU time for PID ${pid}
- Could not read helper socket path from command: ${command}
AI-assisted analysis of stablyai/orca@1136503c6a (2026-08-12).
Data as JSON: /api/errors/36add56a3b289159.
Report an issue: GitHub.