From f9907a86da6e08c523c8df2b4b81f0fc5af34099 Mon Sep 17 00:00:00 2001 From: SW van Heerden Date: Tue, 30 Jul 2024 14:16:05 +0200 Subject: [PATCH] chore: remove domain digest (#6436) Description --- removes domain digest from MMR Motivation and Context --- MMR should not care what hasher you want to use. --- Cargo.lock | 3 - base_layer/mmr/Cargo.toml | 1 - .../mmr/src/balanced_binary_merkle_proof.rs | 5 +- .../mmr/src/balanced_binary_merkle_tree.rs | 3 +- base_layer/mmr/src/common.rs | 3 +- base_layer/mmr/src/functions.rs | 5 +- base_layer/mmr/src/merkle_mountain_range.rs | 5 +- base_layer/mmr/src/merkle_proof.rs | 25 +--- base_layer/mmr/src/pruned_hashset.rs | 3 +- common/Cargo.toml | 2 - common/src/hashing.rs | 128 ------------------ common/src/lib.rs | 3 - 12 files changed, 16 insertions(+), 170 deletions(-) delete mode 100644 common/src/hashing.rs diff --git a/Cargo.lock b/Cargo.lock index 1457faebe4..8f30fa3620 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -6033,7 +6033,6 @@ name = "tari_common" version = "1.0.0-pre.18" dependencies = [ "anyhow", - "blake2", "config", "dirs-next 1.0.2", "git2", @@ -6047,7 +6046,6 @@ dependencies = [ "serde_yaml", "sha2 0.10.8", "structopt", - "tari_crypto", "tari_features", "tari_test_utils", "tempfile", @@ -6471,7 +6469,6 @@ dependencies = [ "rand 0.8.5", "serde", "serde_json", - "tari_common", "tari_crypto", "tari_utilities", "thiserror", diff --git a/base_layer/mmr/Cargo.toml b/base_layer/mmr/Cargo.toml index 07aaf72069..91602f895f 100644 --- a/base_layer/mmr/Cargo.toml +++ b/base_layer/mmr/Cargo.toml @@ -13,7 +13,6 @@ default = [] [dependencies] tari_utilities = { version = "0.7" } tari_crypto = { version = "0.20.3" } -tari_common = { path = "../../common", version = "1.0.0-pre.18" } thiserror = "1.0" borsh = "1.2" digest = "0.10" diff --git a/base_layer/mmr/src/balanced_binary_merkle_proof.rs b/base_layer/mmr/src/balanced_binary_merkle_proof.rs index eb8ee789ce..a42d30409c 100644 --- a/base_layer/mmr/src/balanced_binary_merkle_proof.rs +++ b/base_layer/mmr/src/balanced_binary_merkle_proof.rs @@ -29,7 +29,6 @@ use std::{ use borsh::{BorshDeserialize, BorshSerialize}; use digest::Digest; use serde::{Deserialize, Serialize}; -use tari_common::DomainDigest; use thiserror::Error; use crate::{common::hash_together, BalancedBinaryMerkleTree, Hash}; @@ -47,7 +46,7 @@ pub struct BalancedBinaryMerkleProof { } impl BalancedBinaryMerkleProof -where D: Digest + DomainDigest +where D: Digest { #[must_use = "Must use the result of the proof verification"] pub fn verify(&self, root: &Hash, leaf_hash: Hash) -> bool { @@ -137,7 +136,7 @@ pub struct MergedBalancedBinaryMerkleProof { } impl MergedBalancedBinaryMerkleProof -where D: Digest + DomainDigest +where D: Digest { pub fn create_from_proofs(proofs: &[BalancedBinaryMerkleProof]) -> Result { let heights = proofs diff --git a/base_layer/mmr/src/balanced_binary_merkle_tree.rs b/base_layer/mmr/src/balanced_binary_merkle_tree.rs index e534773189..38cc3f1995 100644 --- a/base_layer/mmr/src/balanced_binary_merkle_tree.rs +++ b/base_layer/mmr/src/balanced_binary_merkle_tree.rs @@ -24,7 +24,6 @@ use std::{convert::TryFrom, marker::PhantomData}; use digest::Digest; use serde::{Deserialize, Serialize}; -use tari_common::DomainDigest; use thiserror::Error; use crate::{common::hash_together, Hash}; @@ -54,7 +53,7 @@ pub struct BalancedBinaryMerkleTree { } impl BalancedBinaryMerkleTree -where D: Digest + DomainDigest +where D: Digest { // There is no push method for this tree. This tree is created at once and no modifications are allowed. pub fn create(leaves: Vec) -> Self { diff --git a/base_layer/mmr/src/common.rs b/base_layer/mmr/src/common.rs index b2a74668f1..7ddb35e03c 100644 --- a/base_layer/mmr/src/common.rs +++ b/base_layer/mmr/src/common.rs @@ -26,7 +26,6 @@ use std::convert::TryInto; use digest::Digest; -use tari_common::DomainDigest; use crate::{error::MerkleMountainRangeError, Hash}; @@ -187,7 +186,7 @@ pub fn is_left_sibling(pos: usize) -> bool { (peak_map & peak) == 0 } -pub fn hash_together(left: &[u8], right: &[u8]) -> Hash { +pub fn hash_together(left: &[u8], right: &[u8]) -> Hash { D::new().chain_update(left).chain_update(right).finalize().to_vec() } diff --git a/base_layer/mmr/src/functions.rs b/base_layer/mmr/src/functions.rs index aeb3fd6e58..1f4265c7e1 100644 --- a/base_layer/mmr/src/functions.rs +++ b/base_layer/mmr/src/functions.rs @@ -23,7 +23,6 @@ use std::{convert::TryFrom, marker::PhantomData}; use digest::Digest; -use tari_common::DomainDigest; use crate::{error::MerkleMountainRangeError, pruned_hashset::PrunedHashSet, ArrayLike, Hash, MerkleMountainRange}; @@ -36,7 +35,7 @@ pub type PrunedMmr = MerkleMountainRange; /// `validate` will throw an error. pub fn prune_mmr(mmr: &MerkleMountainRange) -> Result, MerkleMountainRangeError> where - D: Digest + DomainDigest, + D: Digest, B: ArrayLike, { let backend = PrunedHashSet::try_from(mmr)?; @@ -51,7 +50,7 @@ pub fn calculate_mmr_root( additions: Vec, ) -> Result where - D: Digest + DomainDigest, + D: Digest, B: ArrayLike, { let mut mmr = prune_mmr(src)?; diff --git a/base_layer/mmr/src/merkle_mountain_range.rs b/base_layer/mmr/src/merkle_mountain_range.rs index 8aa3338ea1..a3270d419a 100644 --- a/base_layer/mmr/src/merkle_mountain_range.rs +++ b/base_layer/mmr/src/merkle_mountain_range.rs @@ -27,7 +27,6 @@ use std::{ }; use digest::Digest; -use tari_common::DomainDigest; use crate::{ backend::ArrayLike, @@ -62,7 +61,7 @@ pub struct MerkleMountainRange { impl MerkleMountainRange where - D: Digest + DomainDigest, + D: Digest, B: ArrayLike, { /// Create a new Merkle mountain range using the given backend for storage @@ -282,7 +281,7 @@ where impl PartialEq> for MerkleMountainRange where - D: Digest + DomainDigest, + D: Digest, B: ArrayLike, B2: ArrayLike, { diff --git a/base_layer/mmr/src/merkle_proof.rs b/base_layer/mmr/src/merkle_proof.rs index 52f8b351b7..d695018f03 100644 --- a/base_layer/mmr/src/merkle_proof.rs +++ b/base_layer/mmr/src/merkle_proof.rs @@ -25,7 +25,6 @@ use std::fmt::{self, Display, Formatter}; use digest::Digest; use log::error; use serde::{Deserialize, Serialize}; -use tari_common::DomainDigest; use tari_utilities::hex::Hex; use thiserror::Error; @@ -81,7 +80,7 @@ impl MerkleProof { leaf_index: LeafIndex, ) -> Result where - D: Digest + DomainDigest, + D: Digest, B: ArrayLike, { let pos = node_index(leaf_index); @@ -100,7 +99,7 @@ impl MerkleProof { /// other MMR implementations work). pub fn for_node(mmr: &MerkleMountainRange, pos: usize) -> Result where - D: Digest + DomainDigest, + D: Digest, B: ArrayLike, { // check this pos is actually a leaf in the MMR @@ -113,7 +112,7 @@ impl MerkleProof { fn generate_proof(mmr: &MerkleMountainRange, pos: usize) -> Result where - D: Digest + DomainDigest, + D: Digest, B: ArrayLike, { // check we actually have a hash in the MMR at this pos @@ -155,7 +154,7 @@ impl MerkleProof { }) } - pub fn verify_leaf( + pub fn verify_leaf( &self, root: &HashSlice, hash: &HashSlice, @@ -166,12 +165,7 @@ impl MerkleProof { } /// Verifies the Merkle proof against the provided root hash, element and position in the MMR. - pub fn verify( - &self, - root: &HashSlice, - hash: &HashSlice, - pos: usize, - ) -> Result<(), MerkleProofError> { + pub fn verify(&self, root: &HashSlice, hash: &HashSlice, pos: usize) -> Result<(), MerkleProofError> { let mut proof = self.clone(); // calculate the peaks once as these are based on overall MMR size (and will not change) let peaks = find_peaks(self.mmr_size).ok_or(MerkleMountainRangeError::InvalidMmrSize)?; @@ -191,12 +185,7 @@ impl MerkleProof { /// /// After running [verify_consume], we'll know the hash of 6 and it's position (the local root), and so we'll also /// know where to insert the hash in the peak list. - fn check_root( - &self, - hash: &HashSlice, - pos: usize, - peaks: &[usize], - ) -> Result { + fn check_root(&self, hash: &HashSlice, pos: usize, peaks: &[usize]) -> Result { // The peak hash list provided in the proof does not include the local peak determined from the candidate // node, so len(peak) must be len(self.peaks) + 1. if peaks.len() != self.peaks.len() + 1 { @@ -230,7 +219,7 @@ impl MerkleProof { /// calculating the parent hash, and then calling `verify_consume` again using the parent hash and position. /// Once `self.path` is empty, we have the local root and position, this data is used to hash all the peaks /// together in `check_root` to calculate the final merkle root. - fn verify_consume( + fn verify_consume( &mut self, root: &HashSlice, hash: &HashSlice, diff --git a/base_layer/mmr/src/pruned_hashset.rs b/base_layer/mmr/src/pruned_hashset.rs index b318f4a609..a41f10fe25 100644 --- a/base_layer/mmr/src/pruned_hashset.rs +++ b/base_layer/mmr/src/pruned_hashset.rs @@ -24,7 +24,6 @@ use std::convert::TryFrom; use digest::Digest; use serde::{Deserialize, Serialize}; -use tari_common::DomainDigest; use crate::{common::find_peaks, error::MerkleMountainRangeError, ArrayLike, Hash, MerkleMountainRange}; @@ -51,7 +50,7 @@ pub struct PrunedHashSet { impl TryFrom<&MerkleMountainRange> for PrunedHashSet where - D: Digest + DomainDigest, + D: Digest, B: ArrayLike, { type Error = MerkleMountainRangeError; diff --git a/common/Cargo.toml b/common/Cargo.toml index 79206b934b..a1fbb2e45e 100644 --- a/common/Cargo.toml +++ b/common/Cargo.toml @@ -14,11 +14,9 @@ build = ["toml", "prost-build"] static-application-info = ["git2"] [dependencies] -tari_crypto = { version = "0.20.3" } tari_features = { path = "./tari_features", version = "1.0.0-pre.18"} anyhow = "1.0.53" -blake2 = "0.10" config = { version = "0.14.0", default-features = false, features = ["toml"] } dirs-next = "1.0.2" git2 = { version = "0.18", default-features = false, optional = true } diff --git a/common/src/hashing.rs b/common/src/hashing.rs deleted file mode 100644 index fa5508b445..0000000000 --- a/common/src/hashing.rs +++ /dev/null @@ -1,128 +0,0 @@ -// Copyright 2019. The Tari Project -// -// Redistribution and use in source and binary forms, with or without modification, are permitted provided that the -// following conditions are met: -// -// 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following -// disclaimer. -// -// 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the -// following disclaimer in the documentation and/or other materials provided with the distribution. -// -// 3. Neither the name of the copyright holder nor the names of its contributors may be used to endorse or promote -// products derived from this software without specific prior written permission. -// -// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, -// INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE -// DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, -// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR -// SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, -// WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE -// USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. - -use sha2::Digest; -use tari_crypto::hashing::{DomainSeparatedHasher, LengthExtensionAttackResistant}; - -/// A marker trait for tight coupling of DomainSeparatedHasher to Digest; this is useful when a low level hashing -/// function that accepts Digest as type needs to guarantee that domain separated hashing is implemented. -pub trait DomainDigest: Digest {} - -impl DomainDigest for DomainSeparatedHasher where Self: Digest {} - -/// A MAC hasher that guarantees implementation of DomainSeparatedHasher and LengthExtensionAttackResistant. -#[allow(dead_code)] -pub fn mac_domain_hasher() -> DomainSeparatedHasher -where - D: LengthExtensionAttackResistant, - DomainSeparatedHasher: Digest, - D: Digest, -{ - DomainSeparatedHasher::::new() -} - -#[cfg(test)] -mod test { - use blake2::Blake2b; - use sha2::{ - digest::{consts::U32, Output}, - Digest, - Sha256, - }; - use tari_crypto::{ - hash_domain, - hashing::{AsFixedBytes, DomainSeparatedHasher}, - }; - - use crate::{hashing::mac_domain_hasher, DomainDigest}; - - hash_domain!(HashDomain, "com.tari.test.hash_domain", 1); - type DomainHasher = DomainSeparatedHasher; - - fn use_as_digest_function(data: &[u8]) -> Output> - where D: Digest { - D::new().chain_update(data).finalize() - } - - fn use_as_domain_digest_function(data: &[u8]) -> Output> - where D: DomainDigest { - D::new().chain_update(data).finalize() - } - - #[test] - fn test_domain_digest() { - let some_data = b"some data"; - - let hashed = use_as_digest_function::>(some_data); - let hash_as_digest_1: [u8; 32] = hashed.into(); - - let hashed = use_as_digest_function::>>(some_data); - let hash_as_digest_2: [u8; 32] = hashed.into(); - - assert_ne!(hash_as_digest_2, hash_as_digest_1); - - let hashed = use_as_domain_digest_function::>>(some_data); - let hash_as_domain_digest: [u8; 32] = hashed.into(); - - assert_eq!(hash_as_domain_digest, hash_as_digest_2); - - // The compiler won't even let you write these tests :), so they're commented out. - // let hashed = use_as_mac_domain_digest_function::>(some_data); - // - // error[E0277]: the trait bound `Blake2b: MacDomainDigest` is not satisfied - // --> common\src\hashing_domain.rs:85:58 - // | - // 85 | let hashed = use_as_mac_domain_digest_function::>(some_data); - // | ^^^^^^^^ the trait `MacDomainDigest` is not - } - - #[test] - fn test_mac_domain_digest() { - hash_domain!(MacDomain, "com.tari.test.mac_domain.my_function", 1); - let some_data = b"some data"; - - // The 'mac_domain_hasher' introduce specific trait bounds - let hasher = mac_domain_hasher::, MacDomain>(); - let hash_from_mac_domain_hasher: [u8; 32] = hasher.digest(some_data).as_fixed_bytes().unwrap(); - - // The compiler won't even let you write these tests :), so they're commented out. - // let hasher = mac_domain_hasher::(); - // error[E0277]: the trait bound `Sha256: LengthExtensionAttackResistant` is not satisfied - // --> common\src\hashing.rs:117:42 - // | - // 117 | let hasher = mac_domain_hasher::(); - // | ^^^^^^ the trait `LengthExtensionAttackResistant` is not - // implemented for `Sha256` - - // A custom domain separated hasher can be created that gives the same results... - let hasher = DomainSeparatedHasher::, MacDomain>::new(); - let hash_from_custom_hasher_1: [u8; 32] = hasher.digest(some_data).as_fixed_bytes().unwrap(); - - assert_eq!(hash_from_mac_domain_hasher, hash_from_custom_hasher_1); - - // ... but quite easily not adhering to the desired mac properties - let hasher = DomainSeparatedHasher::::new(); - let hash_from_custom_hasher_2: [u8; 32] = hasher.digest(some_data).as_fixed_bytes().unwrap(); - - assert_ne!(hash_from_custom_hasher_2, hash_from_custom_hasher_1); - } -} diff --git a/common/src/lib.rs b/common/src/lib.rs index 8df6bddc02..2056c59ae1 100644 --- a/common/src/lib.rs +++ b/common/src/lib.rs @@ -67,9 +67,6 @@ pub use configuration::{ pub mod dir_utils; pub use logging::initialize_logging; -mod hashing; -pub use hashing::{mac_domain_hasher, DomainDigest}; - pub const DEFAULT_CONFIG: &str = "config/config.toml"; pub const DEFAULT_BASE_NODE_LOG_CONFIG: &str = "config/log4rs_base_node.yml"; pub const DEFAULT_WALLET_LOG_CONFIG: &str = "config/log4rs_console_wallet.yml";