Skip to main content

void_core/metadata/
hashing.rs

1//! Path hashing utilities.
2
3use sha2::{Digest, Sha256};
4use void_crypto::RepoSecret;
5
6/// Computes a 64-bit hash key for a path (file or directory).
7///
8/// Uses SHA-256 over `repo_secret || path` and interprets the first 8 bytes as
9/// a big-endian integer. Big-endian keeps bytewise prefix ordering consistent
10/// with numeric ordering when ranges are compared lexicographically.
11pub fn hash_path_u64(repo_secret: &RepoSecret, path: &str) -> u64 {
12    let mut hasher = Sha256::new();
13    hasher.update(repo_secret.as_bytes());
14    hasher.update(path.as_bytes());
15    let hash = hasher.finalize();
16
17    u64::from_be_bytes([
18        hash[0], hash[1], hash[2], hash[3], hash[4], hash[5], hash[6], hash[7],
19    ])
20}
21
22/// Computes a 64-bit hash key for a directory listing.
23///
24/// Directory paths use trailing "/" to distinguish from files. Root directory
25/// uses "/" as the hash input.
26pub fn hash_dir_path_u64(repo_secret: &RepoSecret, dir_path: &str) -> u64 {
27    let hash_path = if dir_path.is_empty() { "/" } else { dir_path };
28    let mut with_slash = String::with_capacity(hash_path.len() + 1);
29    with_slash.push_str(hash_path);
30    if !with_slash.ends_with('/') {
31        with_slash.push('/');
32    }
33    hash_path_u64(repo_secret, &with_slash)
34}