Repository: informalsystems/tendermint-rs (language: rust)

Issue:
FR: Loosen bound on merkle tree inputs from &[Vec<u8>] to &[impl AsRef<[u8]>]
### Description
Change the API of `MerkleHash::hash_byte_vectors` and `simple_hash_from_byte_vectors` to accept `&[impl AsRef<[u8]>]` as an argument instead of only `&[Vec<u8>]`. This will allow consumers to hash borrowed data, avoiding unnecessary copies.

### Definition of "done"
The APIs of both functions have been updated. 

```rust
pub fn simple_hash_from_byte_vectors<H>(byte_vecs: &[impl AsRef<[u8]>]) -> Hash
where
    H: MerkleHash + Default,
{
    let mut hasher = H::default();
    hasher.hash_byte_vectors(byte_vecs)
}

pub trait MerkleHash { 
    // ...
    fn hash_byte_vectors(&mut self, byte_vecs: &[impl AsRef<[u8]>]) -> Hash {
        let length = byte_vecs.len();
        match length {
            0 => self.empty_hash(),
            1 => self.leaf_hash(byte_vecs[0].as_ref()),
            _ => {
                let split = length.next_power_of_two() / 2;
                let left = self.hash_byte_vectors(&byte_vecs[..split]);
                let right = self.hash_byte_vectors(&byte_vecs[split..]);
                self.inner_hash(left, right)
            },
        }
    }
    }


Discussion / hints:

Fix patch:
diff --git a/.changelog/unreleased/improvements/1310-loosen-merkle-tree-bounds.md b/.changelog/unreleased/improvements/1310-loosen-merkle-tree-bounds.md
new file mode 100644
index 000000000..5c6bf542a
--- /dev/null
+++ b/.changelog/unreleased/improvements/1310-loosen-merkle-tree-bounds.md
@@ -0,0 +1,2 @@
+- [`tendermint`]: Loosen bounds of merkle hashing functions to accept borrowed data.
+  ([\#1310](https://github.com/informalsystems/tendermint-rs/issues/1310))
diff --git a/tendermint/src/merkle.rs b/tendermint/src/merkle.rs
index 44611189e..63c6361fb 100644
--- a/tendermint/src/merkle.rs
+++ b/tendermint/src/merkle.rs
@@ -20,7 +20,7 @@ pub type Hash = [u8; HASH_SIZE];
 /// Compute a simple Merkle root from vectors of arbitrary byte vectors.
 /// The leaves of the tree are the bytes of the given byte vectors in
 /// the given order.
-pub fn simple_hash_from_byte_vectors<H>(byte_vecs: &[Vec<u8>]) -> Hash
+pub fn simple_hash_from_byte_vectors<H>(byte_vecs: &[impl AsRef<[u8]>]) -> Hash
 where
     H: MerkleHash + Default,
 {
@@ -48,11 +48,11 @@ pub trait MerkleHash {
     // Implements recursion into subtrees.
     // Pre and post-conditions: the hasher is in the reset state
     // before and after calling this function.
-    fn hash_byte_vectors(&mut self, byte_vecs: &[Vec<u8>]) -> Hash {
+    fn hash_byte_vectors(&mut self, byte_vecs: &[impl AsRef<[u8]>]) -> Hash {
         let length = byte_vecs.len();
         match length {
             0 => self.empty_hash(),
-            1 => self.leaf_hash(&byte_vecs[0]),
+            1 => self.leaf_hash(byte_vecs[0].as_ref()),
             _ => {
                 let split = length.next_power_of_two() / 2;
                 let left = self.hash_byte_vectors(&byte_vecs[..split]);


Test patch: