#[derive(Debug, Clone, Hash, PartialEq, Eq)]
pub struct Tier2CacheKey {
pub root_hash: [u8; 32],
pub inlined_hashes: Vec<[u8; 32]>,
pub compiler_version: u32,
pub schema_version: u32,
pub feedback_epoch: u32,
}
impl Tier2CacheKey {
pub fn new(root_hash: [u8; 32], mut inlined: Vec<[u8; 32]>, compiler_version: u32) -> Self {
inlined.sort();
Self {
root_hash,
inlined_hashes: inlined,
compiler_version,
schema_version: 0,
feedback_epoch: 0,
}
}
pub fn with_versions(
root_hash: [u8; 32],
mut inlined: Vec<[u8; 32]>,
compiler_version: u32,
schema_version: u32,
feedback_epoch: u32,
) -> Self {
inlined.sort();
Self {
root_hash,
inlined_hashes: inlined,
compiler_version,
schema_version,
feedback_epoch,
}
}
pub fn combined_hash(&self) -> [u8; 32] {
use sha2::{Digest, Sha256};
let mut hasher = Sha256::new();
hasher.update(self.root_hash);
for h in &self.inlined_hashes {
hasher.update(h);
}
hasher.update(self.compiler_version.to_le_bytes());
hasher.update(self.schema_version.to_le_bytes());
hasher.update(self.feedback_epoch.to_le_bytes());
hasher.finalize().into()
}
}
#[cfg(test)]
mod tests {
use super::*;
fn hash(n: u8) -> [u8; 32] {
[n; 32]
}
#[test]
fn test_tier2_cache_key() {
let k1 = Tier2CacheKey::new(hash(1), vec![hash(2), hash(3)], 1);
let k2 = Tier2CacheKey::new(hash(1), vec![hash(3), hash(2)], 1);
assert_eq!(k1.combined_hash(), k2.combined_hash());
}
}