{"record":{"id":"0119e15135850381","repo":"astrid-runtime/astrid","slug":"legacy-source-contains-a-special-entry","errorCode":null,"errorMessage":"legacy source contains a special entry: {}","messagePattern":"legacy source contains a special entry: (.+?)","errorType":"validation","errorClass":null,"httpStatus":null,"severity":"error","filePath":"crates/astrid-kernel/src/legacy_migration_barrier/host_fs.rs","lineNumber":642,"sourceCode":"        return Err(io::Error::new(\n            io::ErrorKind::InvalidData,\n            format!(\"legacy source is an active mount: {}\", path.display()),\n        ));\n    }\n    let device = device_id(&metadata);\n    let mut hasher = blake3::Hasher::new_derive_key(\"astrid layout component source v1\");\n    let mut identity = SourceInventory::default();\n    if metadata.is_file() {\n        // A top-level regular file is itself one source entry.  Directory\n        // snapshots count children in `snapshot_dir`; keeping the same\n        // cardinality here lets retirement bind a single-file source to the\n        // exact preflight manifest as well.\n        identity.entries = SourceCount::new(1);\n        read_regular_file(path, &mut hasher, &mut identity)?;\n    } else if metadata.is_dir() {\n        snapshot_dir(path, path, device, access, &mut hasher, &mut identity)?;\n    } else {\n        return Err(io::Error::new(\n            io::ErrorKind::InvalidData,\n            format!(\"legacy source contains a special entry: {}\", path.display()),\n        ));\n    }\n    SourceIdentity::present(\n        SourceDigest::from_blake3(hasher.finalize()),\n        identity.entries,\n        identity.bytes,\n    )\n    .map_err(|error| io::Error::new(io::ErrorKind::InvalidData, error))\n}\n\n/// Validate one regular-file source using the same no-follow, private,\n/// same-device, and mount checks as recursive snapshots.  Distro lock files\n/// keep their component-owned digest format, so they use this structural\n/// check instead of the generic tree hash.\npub(super) fn validate_source_path(path: &Path) -> io::Result<()> {\n    let metadata = fs::symlink_metadata(path)?;","sourceCodeStart":624,"sourceCodeEnd":660,"githubUrl":"https://github.com/astrid-runtime/astrid/blob/affd8760f44190dbdfbec23403f4c4b642c33112/crates/astrid-kernel/src/legacy_migration_barrier/host_fs.rs#L624-L660","documentation":"snapshot_path_with_access can only fingerprint regular files and directories. If the top-level legacy source is neither (fifo, socket, device node, other special file), it cannot be hashed or counted as source entries, so the library raises InvalidData. Note validate_source_entry has already run for the path itself, so this fires when the top-level entry type is admissible to earlier checks but not a file/dir for snapshotting.","triggerScenarios":"Calling snapshot_path or snapshot_owner_controlled_path on a legacy source path that resolves to a special file rather than a regular file or directory; the final else-branch of the file/dir dispatch.","commonSituations":"A legacy component path occupied by a socket or pipe left by an old daemon; a device node appearing where data used to live; corrupted layout after a crashed tool.","solutions":["Stop the process owning the special file and remove it from the legacy source path.","Restore the expected regular file or directory at that path (from backup or by re-creating the legacy layout).","Re-run the migration/snapshot once the source is a plain file or directory."],"exampleFix":"// before\nprw-r--r-- legacy-ctl (fifo) at the component source path\n// after\nrm legacy-ctl\n# restore or create a regular file/directory at the path, then re-run","handlingStrategy":"validation","validationCode":"match std::fs::symlink_metadata(&source) {\n    Ok(m) if m.is_file() || m.is_dir() => {},\n    Ok(_) => eprintln!(\"{} is a special file; remove it first\", source.display()),\n    Err(_) => {},\n}","typeGuard":"fn is_snapshotable(p: &Path) -> bool {\n    std::fs::symlink_metadata(p).map(|m| m.is_file() || m.is_dir()).unwrap_or(false)\n}","tryCatchPattern":"if let Err(e) = snapshot_path(&source) {\n    if e.to_string().contains(\"special entry\") {\n        // remove/replace the special file at the source path, then retry\n    }\n}","preventionTips":["Ensure legacy source paths hold only regular files/directories.","Stop daemons that create sockets/pipes inside legacy component paths.","Verify entry types with symlink_metadata before snapshotting."],"tags":["filesystem","special-file","snapshot","migration"],"backgroundTag":"incompatible-source-type","analyzedSha":"affd8760f44190dbdfbec23403f4c4b642c33112","analyzedAt":"2026-09-09T21:28:12.402Z","contentChangedAt":"2026-09-09T21:28:12.402Z","schemaVersion":2},"datasetVersion":"2026-09-14T05:17:10.506Z"}