{"record":{"id":"91f69bf919b4e5e1","repo":"gastownhall/beads","slug":"capture-proxy-birth-identity-w","errorCode":null,"errorMessage":"capture proxy birth identity: %w","messagePattern":"capture proxy birth identity: %w","errorType":"exception","errorClass":null,"httpStatus":null,"severity":"error","filePath":"internal/storage/dbproxy/proxy/server.go","lineNumber":282,"sourceCode":"\t\tif changed, cerr := stopEpochChanged(p.rootDir, p.stopEpoch); cerr == nil && changed {\n\t\t\treturn fmt.Errorf(\"%w for %s: stop epoch advanced during backend start (%v)\", errStartInterrupted, p.rootDir, err)\n\t\t}\n\t\treturn fmt.Errorf(\"start database server: %w\", err)\n\t}\n\n\tif err := waitForServerReady(ctx, p.server, serverReadyTimeout); err != nil {\n\t\tif changed, cerr := stopEpochChanged(p.rootDir, p.stopEpoch); cerr == nil && changed {\n\t\t\treturn abortInterruptedStart()\n\t\t}\n\t\tp.stats.IncBackendStop()\n\t\t_ = stopBackendBounded(p.server)\n\t\treturn fmt.Errorf(\"database server not ready: %w\", err)\n\t}\n\tbirth, err := procid.Capture(os.Getpid())\n\tif err != nil {\n\t\tp.stats.IncBackendStop()\n\t\t_ = stopBackendBounded(p.server)\n\t\treturn fmt.Errorf(\"capture proxy birth identity: %w\", err)\n\t}\n\trootID, err := identity.RootID(p.rootDir)\n\tif err != nil {\n\t\tp.stats.IncBackendStop()\n\t\t_ = stopBackendBounded(p.server)\n\t\treturn fmt.Errorf(\"resolve proxy root identity: %w\", err)\n\t}\n\tupstreamID := p.server.ID(ctx)\n\tidentMu.Lock()\n\tidentReply.RootID = rootID\n\tidentReply.UpstreamID = upstreamID\n\tidentReply.PID = os.Getpid()\n\tidentReply.Birth = string(birth)\n\tidentReply.ControlPort = control.Port()\n\tidentMu.Unlock()\n\n\t// Last fence before publishing: the spawn marker was cleared when this\n\t// process took proxy.lock, so a `bd dolt stop` that began during a slow","sourceCodeStart":264,"sourceCodeEnd":300,"githubUrl":"https://github.com/gastownhall/beads/blob/71377f276968b452ee607177637970a4ff888584/internal/storage/dbproxy/proxy/server.go#L264-L300","documentation":"Wraps a failure of procid.Capture(os.Getpid()), which snapshots the proxy process's birth identity (e.g. start time + pid used to safely identify the process later). If this OS-level capture fails, ListenAndServe tears down the backend and aborts startup, because publishing a pidfile without a verified birth identity would be unsafe for later ownership checks.","triggerScenarios":"procid.Capture fails, typically when the OS mechanism used to read process start metadata (e.g. /proc/<pid>/stat on Linux) is unavailable or unreadable in the container/sandbox.","commonSituations":"Minimal containers without /proc mounted (or mounted with hidepid); hardened seccomp profiles blocking the required syscalls; exotic platforms where the procid implementation is unsupported.","solutions":["Ensure /proc is mounted and readable for the proxy process inside the container","Review seccomp/AppArmor policies blocking procfs reads and allowlist them","Upgrade to a release supporting the current platform if the OS lacks the required metadata file","Check that the process was not already reaped/modified concurrently (very rare)"],"exampleFix":null,"handlingStrategy":"validation","validationCode":"// Verify procfs is readable before starting (Linux)\nif _, err := os.Stat(\"/proc/self/stat\"); err != nil {\n    log.Fatalf(\"procfs unavailable, procid.Capture will fail: %v\", err)\n}","typeGuard":null,"tryCatchPattern":"if err := p.ListenAndServe(ctx); err != nil {\n    if strings.Contains(err.Error(), \"capture proxy birth identity\") {\n        log.Fatalf(\"process identity capture unsupported in this environment: %v\", err)\n    }\n    log.Fatal(err)\n}","preventionTips":["Mount /proc normally in containers (do not use hidepid=2 with the proxy user)","Review seccomp profiles to allow procfs reads","Test proxy startup in minimal images before deploying"],"tags":["process","procfs","identity","container"],"backgroundTag":"procfs-unavailable","analyzedSha":"71377f276968b452ee607177637970a4ff888584","analyzedAt":"2026-08-30T18:55:39.744Z","schemaVersion":2},"datasetVersion":"2026-08-30T23:17:21.991Z"}