{"record":{"id":"33868e33677e731d","repo":"tinyhumansai/openhuman","slug":"jail-id-dir-is-outside-registry-base","errorCode":null,"errorMessage":"jail {id} dir {} is outside registry base {}","messagePattern":"jail (.+?) dir (.+?) is outside registry base (.+?)","errorType":"exception","errorClass":"io::Error","httpStatus":null,"severity":"error","filePath":"src/openhuman/sandbox/cwd_jail/registry.rs","lineNumber":366,"sourceCode":"        let record = self\n            .get(id)\n            .ok_or_else(|| io::Error::new(io::ErrorKind::NotFound, format!(\"no jail {id}\")))?;\n\n        let resolved = record\n            .dir\n            .canonicalize()\n            .unwrap_or_else(|_| record.dir.clone());\n        let resolved_base = self\n            .base\n            .canonicalize()\n            .unwrap_or_else(|_| self.base.clone());\n        if !resolved.starts_with(&resolved_base) {\n            log::warn!(\n                \"[cwd_jail] refusing spawn: jail {id} dir {} not under base {}\",\n                resolved.display(),\n                resolved_base.display()\n            );\n            return Err(io::Error::new(\n                io::ErrorKind::PermissionDenied,\n                format!(\n                    \"jail {id} dir {} is outside registry base {}\",\n                    resolved.display(),\n                    resolved_base.display()\n                ),\n            ));\n        }\n\n        let mut jail = Jail::new(&record.dir, &record.label);\n        jail.canonicalize()?;\n        Ok(jail)\n    }\n\n    /// Atomic-rename write of the index. Falls back to direct write on\n    /// Windows if rename-over fails (Windows traditionally refused\n    /// rename-over-existing, though modern NTFS/Win10 supports it).\n    fn persist(&self, idx: &Index) -> io::Result<()> {","sourceCodeStart":348,"sourceCodeEnd":384,"githubUrl":"https://github.com/tinyhumansai/openhuman/blob/749120085864ce16e0f273c7b86fac7740b39c5b/src/openhuman/sandbox/cwd_jail/registry.rs#L348-L384","documentation":"The registry refused to spawn a process into a jail whose canonicalized directory is outside the registry base. Same guard family as the delete refusal: the sandbox's containment guarantee depends on jail dirs living under the managed base, so a record pointing elsewhere (tampered index, relocated base) fails closed — spawn is denied rather than running outside containment.","triggerScenarios":"Thrown at src/openhuman/sandbox/cwd_jail/registry.rs:366 when the library encounters an invalid state.","commonSituations":"See trigger scenarios.","solutions":["Compare the jail record's dir with the registry base (canonicalize both) to find the divergence","Repair the registry index entry so the jail dir is under base, or recreate the jail","If the base directory moved (e.g. workspace migration), re-register jails under the new base"],"exampleFix":null,"handlingStrategy":"validation","validationCode":null,"typeGuard":null,"tryCatchPattern":null,"preventionTips":[],"tags":[],"backgroundTag":null,"analyzedSha":"749120085864ce16e0f273c7b86fac7740b39c5b","analyzedAt":"2026-08-17T21:21:45.363Z","contentChangedAt":null,"schemaVersion":2},"datasetVersion":"2026-09-14T05:17:10.506Z"}