asar_rust/
path_validation.rs1use crate::disk::AsarError;
2use std::path::{Path, PathBuf};
3
4pub fn ensure_within(container: &Path, file_path: &str) -> Result<PathBuf, AsarError> {
7 let resolved_container = container
8 .canonicalize()
9 .unwrap_or_else(|_| container.to_path_buf());
10
11 let candidate = resolved_container.join(file_path);
12 let resolved_path = candidate
13 .canonicalize()
14 .unwrap_or_else(|_| candidate.clone());
15
16 if !resolved_path.starts_with(&resolved_container)
17 && resolved_path != resolved_container
18 {
19 return Err(AsarError::PathTraversal(format!(
20 "Path \"{}\" resolves to \"{}\" which is outside \"{}\"",
21 file_path,
22 resolved_path.display(),
23 resolved_container.display()
24 )));
25 }
26
27 Ok(resolved_path)
28}