From 4ff0050f300df36c68b83d12f97c58051efc2d03 Mon Sep 17 00:00:00 2001 From: Victor Dumitrescu Date: Thu, 16 Jan 2025 10:53:21 +0100 Subject: [PATCH 1/2] RISC-V: Implement state hashing in new CommitmentLayout trait --- src/riscv/lib/src/cache_utils.rs | 13 +- .../lib/src/machine_state/block_cache.rs | 24 ++- .../src/machine_state/csregisters/values.rs | 24 ++- .../lib/src/machine_state/main_memory.rs | 28 ++- src/riscv/lib/src/pvm/node_pvm.rs | 24 +-- src/riscv/lib/src/state_backend.rs | 2 + .../src/state_backend/commitment_layout.rs | 168 ++++++++++++++++++ src/riscv/lib/src/state_backend/hash.rs | 9 +- src/riscv/lib/src/state_backend/layout.rs | 7 + src/riscv/lib/src/state_backend/region.rs | 4 +- src/riscv/lib/src/stepper/pvm.rs | 14 +- 11 files changed, 251 insertions(+), 66 deletions(-) create mode 100644 src/riscv/lib/src/state_backend/commitment_layout.rs diff --git a/src/riscv/lib/src/cache_utils.rs b/src/riscv/lib/src/cache_utils.rs index 753eb0b07198..e5f136d1095e 100644 --- a/src/riscv/lib/src/cache_utils.rs +++ b/src/riscv/lib/src/cache_utils.rs @@ -1,4 +1,5 @@ // SPDX-FileCopyrightText: 2024 TriliTech +// SPDX-FileCopyrightText: 2025 Nomadic Labs // // SPDX-License-Identifier: MIT @@ -6,8 +7,10 @@ use crate::{ default::ConstDefault, machine_state::main_memory::Address, state_backend::{ - FromProofResult, Layout, ManagerAlloc, ManagerBase, Many, ProofLayout, ProofTree, + owned_backend::Owned, AllocatedOf, CommitmentLayout, FromProofResult, Layout, ManagerAlloc, + ManagerBase, Many, ProofLayout, ProofTree, Ref, }, + storage::{Hash, HashError}, }; use std::{convert::Infallible, marker::PhantomData}; @@ -87,6 +90,14 @@ impl Layout } } +impl CommitmentLayout + for Sizes +{ + fn state_hash(state: AllocatedOf>) -> Result { + Many::::state_hash(state) + } +} + impl ProofLayout for Sizes { diff --git a/src/riscv/lib/src/machine_state/block_cache.rs b/src/riscv/lib/src/machine_state/block_cache.rs index abb2c5cb5401..b357361d47fa 100644 --- a/src/riscv/lib/src/machine_state/block_cache.rs +++ b/src/riscv/lib/src/machine_state/block_cache.rs @@ -1,4 +1,5 @@ // SPDX-FileCopyrightText: 2024 TriliTech +// SPDX-FileCopyrightText: 2025 Nomadic Labs // // SPDX-License-Identifier: MIT @@ -82,7 +83,6 @@ use super::instruction::Instruction; use super::main_memory::MainMemoryLayout; use super::MachineCoreState; use super::{main_memory::Address, ProgramCounterUpdate}; -use crate::cache_utils::Sizes; use crate::machine_state::address_translation::PAGE_SIZE; use crate::parser::instruction::InstrWidth; use crate::state_backend::{ @@ -91,6 +91,10 @@ use crate::state_backend::{ }; use crate::traps::{EnvironException, Exception}; use crate::{cache_utils::FenceCounter, state_backend::FnManager}; +use crate::{ + cache_utils::Sizes, + storage::{Hash, HashError}, +}; use crate::{default::ConstDefault, state_backend::verify_backend}; use crate::{machine_state::instruction::Args, storage::binary}; use std::marker::PhantomData; @@ -116,6 +120,14 @@ impl crate::state_backend::Layout for ICallLayout { } } +impl crate::state_backend::CommitmentLayout for ICallLayout { + fn state_hash( + state: AllocatedOf>, + ) -> Result { + Hash::blake2b_hash(state) + } +} + impl crate::state_backend::ProofLayout for ICallLayout { fn from_proof(proof: state_backend::ProofTree) -> state_backend::FromProofResult { let leaf = proof.into_leaf()?; @@ -193,6 +205,14 @@ impl state_backend::Layout for AddressCellLayout { } } +impl state_backend::CommitmentLayout for AddressCellLayout { + fn state_hash( + state: AllocatedOf>, + ) -> Result { + Hash::blake2b_hash(state) + } +} + impl state_backend::ProofLayout for AddressCellLayout { fn from_proof(proof: state_backend::ProofTree) -> state_backend::FromProofResult { as state_backend::ProofLayout>::from_proof(proof) @@ -359,7 +379,7 @@ impl PartialBlock { /// Trait for capturing the different possible layouts of the instruction cache (i.e. /// controlling the number of cache entries present). -pub trait BlockCacheLayout: state_backend::ProofLayout { +pub trait BlockCacheLayout: state_backend::CommitmentLayout + state_backend::ProofLayout { type MainMemoryLayout: MainMemoryLayout; type Entries; type Sizes; diff --git a/src/riscv/lib/src/machine_state/csregisters/values.rs b/src/riscv/lib/src/machine_state/csregisters/values.rs index 8dde43c33b11..aa7cdbe5184d 100644 --- a/src/riscv/lib/src/machine_state/csregisters/values.rs +++ b/src/riscv/lib/src/machine_state/csregisters/values.rs @@ -1,5 +1,5 @@ // SPDX-FileCopyrightText: 2024 TriliTech -// SPDX-FileCopyrightText: 2024 Nomadic Labs +// SPDX-FileCopyrightText: 2024-2025 Nomadic Labs // // SPDX-License-Identifier: MIT @@ -15,12 +15,12 @@ use crate::state_backend::proof_backend::merkle::{AccessInfo, AccessInfoAggregat use crate::{ bits::Bits64, state_backend::{ - hash::{Hash, HashError, RootHashable}, + hash::{Hash, HashError}, owned_backend::Owned, proof_backend::merkle::{MerkleTree, Merkleisable}, - verify_backend, AllocatedOf, Cell, EffectCell, EffectCellLayout, FnManager, - FromProofResult, Layout, ManagerAlloc, ManagerBase, ManagerRead, ManagerReadWrite, - ManagerWrite, ProofLayout, ProofPart, ProofTree, Ref, + verify_backend, AllocatedOf, Cell, CommitmentLayout, EffectCell, EffectCellLayout, + FnManager, FromProofResult, Layout, ManagerAlloc, ManagerBase, ManagerRead, + ManagerReadWrite, ManagerWrite, ProofLayout, ProofPart, ProofTree, Ref, }, storage::binary, }; @@ -156,6 +156,12 @@ impl Layout for CSRValuesLayout { } } +impl CommitmentLayout for CSRValuesLayout { + fn state_hash(state: AllocatedOf>) -> Result { + Hash::blake2b_hash(state) + } +} + impl ProofLayout for CSRValuesLayout { fn from_proof(proof: ProofTree) -> FromProofResult { fn make_absent() -> AllocatedOf { @@ -1455,14 +1461,6 @@ impl CSRValuesF { } } -impl RootHashable - for CSRValuesF -{ - fn hash(&self) -> Result { - Hash::blake2b_hash(self) - } -} - impl Merkleisable for CSRValuesF where Raw: AccessInfoAggregatable + serde::Serialize, diff --git a/src/riscv/lib/src/machine_state/main_memory.rs b/src/riscv/lib/src/machine_state/main_memory.rs index 32e84c341361..49e1b0e40578 100644 --- a/src/riscv/lib/src/machine_state/main_memory.rs +++ b/src/riscv/lib/src/machine_state/main_memory.rs @@ -1,5 +1,5 @@ // SPDX-FileCopyrightText: 2023 TriliTech -// SPDX-FileCopyrightText: 2024 Nomadic Labs +// SPDX-FileCopyrightText: 2024-2025 Nomadic Labs // // SPDX-License-Identifier: MIT @@ -7,12 +7,12 @@ use crate::{ machine_state::registers::XValue, state_backend::{ self as backend, - hash::{Hash, HashError, RootHashable}, + hash::{Hash, HashError}, proof_backend::{ merkle::{MerkleTree, Merkleisable}, ProofGen, }, - DynArray, ManagerDeserialise, ManagerRead, ManagerSerialise, Ref, + DynArray, ManagerDeserialise, ManagerSerialise, Ref, }, }; use serde::{Deserialize, Serialize}; @@ -67,7 +67,7 @@ gen_memory_layout!(M4G = 4 GiB); // XXX: We can't associate these region types directly with [Sizes] because // inherent associated types are unstable. Hence we must go through a dummy // trait. -pub trait MainMemoryLayout: backend::ProofLayout + 'static { +pub trait MainMemoryLayout: backend::ProofLayout + backend::CommitmentLayout + 'static { type Data; const BYTES: usize; @@ -125,8 +125,6 @@ pub trait MainMemoryLayout: backend::ProofLayout + 'static { /// Clone the dynamic region. fn clone_data(data: &Self::Data) -> Self::Data; - fn hash_data(data: &Self::Data) -> Result; - fn to_merkle_tree( data: &Self::Data>>, ) -> Result; @@ -197,10 +195,6 @@ impl MainMemoryLayout for Sizes { data.clone() } - fn hash_data(data: &Self::Data) -> Result { - data.hash() - } - fn to_merkle_tree( data: &Self::Data>>, ) -> Result { @@ -218,6 +212,14 @@ impl backend::Layout for Sizes { } } +impl backend::CommitmentLayout for Sizes { + fn state_hash( + state: backend::AllocatedOf>, + ) -> Result { + DynArray::state_hash(state.data) + } +} + impl backend::ProofLayout for Sizes { fn from_proof(proof: backend::ProofTree) -> backend::FromProofResult { let data = DynArray::from_proof(proof)?; @@ -348,12 +350,6 @@ where } } -impl RootHashable for MainMemory { - fn hash(&self) -> Result { - L::hash_data(&self.data) - } -} - impl Merkleisable for MainMemory>> { diff --git a/src/riscv/lib/src/pvm/node_pvm.rs b/src/riscv/lib/src/pvm/node_pvm.rs index 0c48f2ab50a5..fae7890811a0 100644 --- a/src/riscv/lib/src/pvm/node_pvm.rs +++ b/src/riscv/lib/src/pvm/node_pvm.rs @@ -1,4 +1,4 @@ -// SPDX-FileCopyrightText: 2024 Nomadic Labs +// SPDX-FileCopyrightText: 2024-2025 Nomadic Labs // SPDX-FileCopyrightText: 2024 Trilitech // // SPDX-License-Identifier: MIT @@ -9,13 +9,12 @@ use crate::{ pvm::common::{Pvm, PvmHooks, PvmLayout, PvmStatus}, state_backend::{ self, - hash::RootHashable, owned_backend::Owned, proof_backend::{ proof::MerkleProof, ProofDynRegion, ProofEnrichedCell, ProofGen, ProofRegion, }, verify_backend::Verifier, - AllocatedOf, ProofLayout, ProofTree, Ref, + AllocatedOf, CommitmentLayout, ProofLayout, ProofTree, Ref, }, storage::{self, Hash, Repo}, }; @@ -161,6 +160,13 @@ where { state: Box::new(state), } } + + pub fn hash(&self) -> Hash { + self.with_backend(|state| { + let refs = state.struct_ref::(); + ::state_hash(refs).unwrap() + }) + } } impl NodePvm { @@ -260,18 +266,6 @@ impl NodePvm { }) } - pub fn hash(&self) -> Hash - where - M: state_backend::ManagerSerialise + state_backend::ManagerRead, - { - self.with_backend(|state| { - state - .struct_ref::() - .hash() - .unwrap() - }) - } - pub fn set_input_message(&mut self, level: u32, message_counter: u64, input: Vec) where M: state_backend::ManagerReadWrite, diff --git a/src/riscv/lib/src/state_backend.rs b/src/riscv/lib/src/state_backend.rs index d219414fbab9..24522f24af8e 100644 --- a/src/riscv/lib/src/state_backend.rs +++ b/src/riscv/lib/src/state_backend.rs @@ -56,6 +56,7 @@ //! [Layouts]: Layout //! [Locations]: Location +mod commitment_layout; mod effects; mod elems; pub mod hash; @@ -67,6 +68,7 @@ mod region; mod trans; pub mod verify_backend; +pub use commitment_layout::*; pub use effects::*; pub use elems::*; pub use layout::*; diff --git a/src/riscv/lib/src/state_backend/commitment_layout.rs b/src/riscv/lib/src/state_backend/commitment_layout.rs new file mode 100644 index 000000000000..3bb1261ccd35 --- /dev/null +++ b/src/riscv/lib/src/state_backend/commitment_layout.rs @@ -0,0 +1,168 @@ +// SPDX-FileCopyrightText: 2025 Nomadic Labs +// +// SPDX-License-Identifier: MIT + +use super::{ + chunks_to_writer, + hash::{self, Hash, HashError, HashWriter, RootHashable, DIGEST_SIZE}, + owned_backend::Owned, + AllocatedOf, Array, Atom, DynArray, Layout, Many, Ref, MERKLE_ARITY, MERKLE_LEAF_SIZE, +}; +use crate::default::ConstDefault; + +/// [`Layouts`] which may be used for commitments +/// +/// [`Layouts`]: crate::state_backend::Layout +pub trait CommitmentLayout: Layout { + /// Compute the root hash of the given state + fn state_hash(state: AllocatedOf>) -> Result; +} + +impl CommitmentLayout for Atom { + fn state_hash(state: AllocatedOf>) -> Result { + Hash::blake2b_hash(state) + } +} + +impl CommitmentLayout for Array +where + [T; LEN]: ConstDefault, +{ + fn state_hash(state: AllocatedOf>) -> Result { + Hash::blake2b_hash(state) + } +} + +impl CommitmentLayout for DynArray { + fn state_hash(state: AllocatedOf>) -> Result { + let mut writer = HashWriter::new(MERKLE_LEAF_SIZE); + chunks_to_writer::(&mut writer, |address| { + state.read::<[u8; MERKLE_LEAF_SIZE.get()]>(address) + })?; + let hashes = writer.finalise()?; + hash::build_custom_merkle_hash(MERKLE_ARITY, hashes) + } +} + +impl CommitmentLayout for (A, B) +where + A: CommitmentLayout, + B: CommitmentLayout, +{ + fn state_hash(state: AllocatedOf>) -> Result { + let hashes = [A::state_hash(state.0)?, B::state_hash(state.1)?]; + hashes.hash() + } +} + +impl CommitmentLayout for (A, B, C) +where + A: CommitmentLayout, + B: CommitmentLayout, + C: CommitmentLayout, +{ + fn state_hash(state: AllocatedOf>) -> Result { + let hashes = [ + A::state_hash(state.0)?, + B::state_hash(state.1)?, + C::state_hash(state.2)?, + ]; + hashes.hash() + } +} + +impl CommitmentLayout for (A, B, C, D) +where + A: CommitmentLayout, + B: CommitmentLayout, + C: CommitmentLayout, + D: CommitmentLayout, +{ + fn state_hash(state: AllocatedOf>) -> Result { + let hashes = [ + A::state_hash(state.0)?, + B::state_hash(state.1)?, + C::state_hash(state.2)?, + D::state_hash(state.3)?, + ]; + hashes.hash() + } +} + +impl CommitmentLayout for (A, B, C, D, E) +where + A: CommitmentLayout, + B: CommitmentLayout, + C: CommitmentLayout, + D: CommitmentLayout, + E: CommitmentLayout, +{ + fn state_hash(state: AllocatedOf>) -> Result { + let hashes = [ + A::state_hash(state.0)?, + B::state_hash(state.1)?, + C::state_hash(state.2)?, + D::state_hash(state.3)?, + E::state_hash(state.4)?, + ]; + hashes.hash() + } +} + +impl CommitmentLayout for (A, B, C, D, E, F) +where + A: CommitmentLayout, + B: CommitmentLayout, + C: CommitmentLayout, + D: CommitmentLayout, + E: CommitmentLayout, + F: CommitmentLayout, +{ + fn state_hash(state: AllocatedOf>) -> Result { + let hashes = [ + A::state_hash(state.0)?, + B::state_hash(state.1)?, + C::state_hash(state.2)?, + D::state_hash(state.3)?, + E::state_hash(state.4)?, + F::state_hash(state.5)?, + ]; + hashes.hash() + } +} + +impl CommitmentLayout for [T; LEN] +where + T: CommitmentLayout, +{ + fn state_hash(state: AllocatedOf>) -> Result { + iter_state_hash::<_, T, LEN>(state) + } +} + +impl CommitmentLayout for Many +where + T: CommitmentLayout, +{ + fn state_hash(state: AllocatedOf>) -> Result { + iter_state_hash::<_, T, LEN>(state) + } +} + +fn iter_state_hash<'a, I, T, const LEN: usize>(iter: I) -> Result +where + I: IntoIterator>>, + T: CommitmentLayout, +{ + let mut hashes: Vec = Vec::with_capacity(DIGEST_SIZE * LEN); + + iter.into_iter().try_for_each(|e| { + hashes.extend_from_slice(T::state_hash(e)?.as_ref()); + Ok::<(), HashError>(()) + })?; + + // TODO RV-250: Instead of building the whole input and hashing it, + // we should use incremental hashing, which isn't currently supported + // in `tezos_crypto_rs`. + Hash::blake2b_hash_bytes(&hashes) +} diff --git a/src/riscv/lib/src/state_backend/hash.rs b/src/riscv/lib/src/state_backend/hash.rs index 03403b605719..ba3f9b8aad6d 100644 --- a/src/riscv/lib/src/state_backend/hash.rs +++ b/src/riscv/lib/src/state_backend/hash.rs @@ -1,4 +1,4 @@ -// SPDX-FileCopyrightText: 2024 Nomadic Labs +// SPDX-FileCopyrightText: 2024-2025 Nomadic Labs // SPDX-FileCopyrightText: 2024 TriliTech // // SPDX-License-Identifier: MIT @@ -92,6 +92,7 @@ impl AsRef<[u8]> for Hash { } } +// TODO RV-398: Remove `RootHashable` trait pub trait RootHashable { /// Build the root hash corresponding to the Merkle tree described by the /// layout of the data. @@ -110,12 +111,6 @@ impl RootHashable for Hash { } } -impl RootHashable for () { - fn hash(&self) -> Result { - Hash::blake2b_hash(()) - } -} - impl RootHashable for [T] { fn hash(&self) -> Result { let mut hashes: Vec = Vec::with_capacity(DIGEST_SIZE * self.len()); diff --git a/src/riscv/lib/src/state_backend/layout.rs b/src/riscv/lib/src/state_backend/layout.rs index dde2b1554ecb..f7c4a13f9a31 100644 --- a/src/riscv/lib/src/state_backend/layout.rs +++ b/src/riscv/lib/src/state_backend/layout.rs @@ -165,6 +165,13 @@ macro_rules! struct_layout { } } + impl $crate::state_backend::CommitmentLayout for $layout_t { + fn state_hash(state: $crate::state_backend::AllocatedOf>) -> + Result<$crate::storage::Hash, $crate::storage::HashError> { + $crate::storage::Hash::blake2b_hash(state) + } + } + impl $crate::state_backend::ProofLayout for $layout_t { fn from_proof(proof: $crate::state_backend::ProofTree) -> Result, $crate::state_backend::FromProofError> { if let $crate::state_backend::ProofTree::Present(proof) = proof { diff --git a/src/riscv/lib/src/state_backend/region.rs b/src/riscv/lib/src/state_backend/region.rs index c53daf69585b..15bc2f37fc5e 100644 --- a/src/riscv/lib/src/state_backend/region.rs +++ b/src/riscv/lib/src/state_backend/region.rs @@ -609,7 +609,7 @@ pub const MERKLE_ARITY: usize = 3; /// and writing them to a writer. The last chunk may be smaller than the /// Merkle leaf size. The implementations of `RootHashable` and `Merkleisable` /// for dynamic regions both use it, ensuring consistency between the two. -fn chunks_to_writer< +pub(crate) fn chunks_to_writer< const LEN: usize, T: std::io::Write, F: Fn(usize) -> [u8; MERKLE_LEAF_SIZE.get()], @@ -639,8 +639,6 @@ fn chunks_to_writer< Ok(()) } -// TODO RV-305: Specialise implementation for `DynCells>` -// when feature becomes stable. impl RootHashable for DynCells { fn hash(&self) -> Result { let mut writer = HashWriter::new(MERKLE_LEAF_SIZE); diff --git a/src/riscv/lib/src/stepper/pvm.rs b/src/riscv/lib/src/stepper/pvm.rs index 8c2bf0e9106c..7003f8ce4fbd 100644 --- a/src/riscv/lib/src/stepper/pvm.rs +++ b/src/riscv/lib/src/stepper/pvm.rs @@ -1,5 +1,5 @@ // SPDX-FileCopyrightText: 2024 TriliTech -// SPDX-FileCopyrightText: 2024 Nomadic Labs +// SPDX-FileCopyrightText: 2024-2025 Nomadic Labs // // SPDX-License-Identifier: MIT @@ -16,11 +16,11 @@ use crate::{ pvm::{Pvm, PvmHooks, PvmLayout, PvmStatus}, range_utils::bound_saturating_sub, state_backend::{ - hash::{Hash, RootHashable}, + hash::Hash, owned_backend::Owned, proof_backend::{merkle::Merkleisable, proof::Proof, ProofGen}, verify_backend::Verifier, - AllocatedOf, FnManagerIdent, ProofLayout, ProofTree, Ref, + AllocatedOf, CommitmentLayout, FnManagerIdent, ProofLayout, ProofTree, Ref, }, storage::binary, }; @@ -134,12 +134,9 @@ impl<'hooks, ML: MainMemoryLayout, CL: CacheLayouts> PvmStepper<'hooks, ML, CL> } /// Obtain the root hash for the PVM state. - pub fn hash<'a>(&'a self) -> Hash - where - AllocatedOf, Ref<'a, Owned>>: RootHashable, - { + pub fn hash(&self) -> Hash { let refs = self.pvm.struct_ref::(); - RootHashable::hash(&refs).unwrap() + PvmLayout::::state_hash(refs).unwrap() } /// Create a new stepper in which the existing PVM is managed by @@ -216,7 +213,6 @@ impl<'hooks, ML: MainMemoryLayout, CL: CacheLayouts, M: ManagerReadWrite> impl<'hooks, ML: MainMemoryLayout, CL: CacheLayouts> PvmStepper<'hooks, ML, CL> where for<'a, 'b> AllocatedOf, Ref<'a, ProofGen>>>: Merkleisable, - for<'a> AllocatedOf, Ref<'a, Owned>>: RootHashable, { /// Produce the Merkle proof for evaluating one step on the given PVM state. /// The given stepper takes one step. -- GitLab From cf080291044a488e0b2dc6c9aa977b6c559da06d Mon Sep 17 00:00:00 2001 From: Victor Dumitrescu Date: Tue, 21 Jan 2025 18:34:41 +0100 Subject: [PATCH 2/2] RISC-V: Type alias for `AllocatedOf>` --- src/riscv/lib/src/cache_utils.rs | 6 ++--- .../src/machine_state/csregisters/values.rs | 4 +-- src/riscv/lib/src/state_backend.rs | 2 ++ .../src/state_backend/commitment_layout.rs | 27 +++++++++---------- src/riscv/lib/src/state_backend/region.rs | 2 +- src/riscv/lib/src/stepper/pvm.rs | 6 ++--- src/riscv/lib/tests/test_determinism.rs | 10 +++---- 7 files changed, 29 insertions(+), 28 deletions(-) diff --git a/src/riscv/lib/src/cache_utils.rs b/src/riscv/lib/src/cache_utils.rs index e5f136d1095e..4409360ec34d 100644 --- a/src/riscv/lib/src/cache_utils.rs +++ b/src/riscv/lib/src/cache_utils.rs @@ -7,8 +7,8 @@ use crate::{ default::ConstDefault, machine_state::main_memory::Address, state_backend::{ - owned_backend::Owned, AllocatedOf, CommitmentLayout, FromProofResult, Layout, ManagerAlloc, - ManagerBase, Many, ProofLayout, ProofTree, Ref, + CommitmentLayout, FromProofResult, Layout, ManagerAlloc, ManagerBase, Many, ProofLayout, + ProofTree, RefOwnedAlloc, }, storage::{Hash, HashError}, }; @@ -93,7 +93,7 @@ impl Layout impl CommitmentLayout for Sizes { - fn state_hash(state: AllocatedOf>) -> Result { + fn state_hash(state: RefOwnedAlloc) -> Result { Many::::state_hash(state) } } diff --git a/src/riscv/lib/src/machine_state/csregisters/values.rs b/src/riscv/lib/src/machine_state/csregisters/values.rs index aa7cdbe5184d..8533c343ff54 100644 --- a/src/riscv/lib/src/machine_state/csregisters/values.rs +++ b/src/riscv/lib/src/machine_state/csregisters/values.rs @@ -20,7 +20,7 @@ use crate::{ proof_backend::merkle::{MerkleTree, Merkleisable}, verify_backend, AllocatedOf, Cell, CommitmentLayout, EffectCell, EffectCellLayout, FnManager, FromProofResult, Layout, ManagerAlloc, ManagerBase, ManagerRead, - ManagerReadWrite, ManagerWrite, ProofLayout, ProofPart, ProofTree, Ref, + ManagerReadWrite, ManagerWrite, ProofLayout, ProofPart, ProofTree, Ref, RefOwnedAlloc, }, storage::binary, }; @@ -157,7 +157,7 @@ impl Layout for CSRValuesLayout { } impl CommitmentLayout for CSRValuesLayout { - fn state_hash(state: AllocatedOf>) -> Result { + fn state_hash(state: RefOwnedAlloc) -> Result { Hash::blake2b_hash(state) } } diff --git a/src/riscv/lib/src/state_backend.rs b/src/riscv/lib/src/state_backend.rs index 24522f24af8e..75d6cf55d6a5 100644 --- a/src/riscv/lib/src/state_backend.rs +++ b/src/riscv/lib/src/state_backend.rs @@ -393,6 +393,8 @@ impl ManagerRead for Ref<'_, M> { } } +pub type RefOwnedAlloc<'a, L> = AllocatedOf>; + #[cfg(test)] pub(crate) mod test_helpers { use super::{ diff --git a/src/riscv/lib/src/state_backend/commitment_layout.rs b/src/riscv/lib/src/state_backend/commitment_layout.rs index 3bb1261ccd35..29767671b727 100644 --- a/src/riscv/lib/src/state_backend/commitment_layout.rs +++ b/src/riscv/lib/src/state_backend/commitment_layout.rs @@ -5,8 +5,7 @@ use super::{ chunks_to_writer, hash::{self, Hash, HashError, HashWriter, RootHashable, DIGEST_SIZE}, - owned_backend::Owned, - AllocatedOf, Array, Atom, DynArray, Layout, Many, Ref, MERKLE_ARITY, MERKLE_LEAF_SIZE, + Array, Atom, DynArray, Layout, Many, RefOwnedAlloc, MERKLE_ARITY, MERKLE_LEAF_SIZE, }; use crate::default::ConstDefault; @@ -15,11 +14,11 @@ use crate::default::ConstDefault; /// [`Layouts`]: crate::state_backend::Layout pub trait CommitmentLayout: Layout { /// Compute the root hash of the given state - fn state_hash(state: AllocatedOf>) -> Result; + fn state_hash(state: RefOwnedAlloc) -> Result; } impl CommitmentLayout for Atom { - fn state_hash(state: AllocatedOf>) -> Result { + fn state_hash(state: RefOwnedAlloc) -> Result { Hash::blake2b_hash(state) } } @@ -28,13 +27,13 @@ impl CommitmentLayout for Array where [T; LEN]: ConstDefault, { - fn state_hash(state: AllocatedOf>) -> Result { + fn state_hash(state: RefOwnedAlloc) -> Result { Hash::blake2b_hash(state) } } impl CommitmentLayout for DynArray { - fn state_hash(state: AllocatedOf>) -> Result { + fn state_hash(state: RefOwnedAlloc) -> Result { let mut writer = HashWriter::new(MERKLE_LEAF_SIZE); chunks_to_writer::(&mut writer, |address| { state.read::<[u8; MERKLE_LEAF_SIZE.get()]>(address) @@ -49,7 +48,7 @@ where A: CommitmentLayout, B: CommitmentLayout, { - fn state_hash(state: AllocatedOf>) -> Result { + fn state_hash(state: RefOwnedAlloc) -> Result { let hashes = [A::state_hash(state.0)?, B::state_hash(state.1)?]; hashes.hash() } @@ -61,7 +60,7 @@ where B: CommitmentLayout, C: CommitmentLayout, { - fn state_hash(state: AllocatedOf>) -> Result { + fn state_hash(state: RefOwnedAlloc) -> Result { let hashes = [ A::state_hash(state.0)?, B::state_hash(state.1)?, @@ -78,7 +77,7 @@ where C: CommitmentLayout, D: CommitmentLayout, { - fn state_hash(state: AllocatedOf>) -> Result { + fn state_hash(state: RefOwnedAlloc) -> Result { let hashes = [ A::state_hash(state.0)?, B::state_hash(state.1)?, @@ -97,7 +96,7 @@ where D: CommitmentLayout, E: CommitmentLayout, { - fn state_hash(state: AllocatedOf>) -> Result { + fn state_hash(state: RefOwnedAlloc) -> Result { let hashes = [ A::state_hash(state.0)?, B::state_hash(state.1)?, @@ -118,7 +117,7 @@ where E: CommitmentLayout, F: CommitmentLayout, { - fn state_hash(state: AllocatedOf>) -> Result { + fn state_hash(state: RefOwnedAlloc) -> Result { let hashes = [ A::state_hash(state.0)?, B::state_hash(state.1)?, @@ -135,7 +134,7 @@ impl CommitmentLayout for [T; LEN] where T: CommitmentLayout, { - fn state_hash(state: AllocatedOf>) -> Result { + fn state_hash(state: RefOwnedAlloc) -> Result { iter_state_hash::<_, T, LEN>(state) } } @@ -144,14 +143,14 @@ impl CommitmentLayout for Many where T: CommitmentLayout, { - fn state_hash(state: AllocatedOf>) -> Result { + fn state_hash(state: RefOwnedAlloc) -> Result { iter_state_hash::<_, T, LEN>(state) } } fn iter_state_hash<'a, I, T, const LEN: usize>(iter: I) -> Result where - I: IntoIterator>>, + I: IntoIterator>, T: CommitmentLayout, { let mut hashes: Vec = Vec::with_capacity(DIGEST_SIZE * LEN); diff --git a/src/riscv/lib/src/state_backend/region.rs b/src/riscv/lib/src/state_backend/region.rs index 15bc2f37fc5e..68c4dd33f404 100644 --- a/src/riscv/lib/src/state_backend/region.rs +++ b/src/riscv/lib/src/state_backend/region.rs @@ -1,5 +1,5 @@ // SPDX-FileCopyrightText: 2023 TriliTech -// SPDX-FileCopyrightText: 2024 Nomadic Labs +// SPDX-FileCopyrightText: 2024-2025 Nomadic Labs // // SPDX-License-Identifier: MIT diff --git a/src/riscv/lib/src/stepper/pvm.rs b/src/riscv/lib/src/stepper/pvm.rs index 7003f8ce4fbd..ee81cf44f92a 100644 --- a/src/riscv/lib/src/stepper/pvm.rs +++ b/src/riscv/lib/src/stepper/pvm.rs @@ -20,7 +20,7 @@ use crate::{ owned_backend::Owned, proof_backend::{merkle::Merkleisable, proof::Proof, ProofGen}, verify_backend::Verifier, - AllocatedOf, CommitmentLayout, FnManagerIdent, ProofLayout, ProofTree, Ref, + AllocatedOf, CommitmentLayout, FnManagerIdent, ProofLayout, ProofTree, Ref, RefOwnedAlloc, }, storage::binary, }; @@ -180,7 +180,7 @@ impl<'hooks, ML: MainMemoryLayout, CL: CacheLayouts> PvmStepper<'hooks, ML, CL> /// Given a manager morphism `f : &M -> N`, return the layout's allocated structure containing /// the constituents of `N` that were produced from the constituents of `&M`. - pub fn struct_ref(&self) -> AllocatedOf, Ref<'_, Owned>> { + pub fn struct_ref(&self) -> RefOwnedAlloc> { self.pvm.struct_ref::() } @@ -188,7 +188,7 @@ impl<'hooks, ML: MainMemoryLayout, CL: CacheLayouts> PvmStepper<'hooks, ML, CL> /// ephemeral state that doesn't make it into the serialised output. pub fn rebind_via_serde(&mut self) where - for<'a> AllocatedOf, Ref<'a, Owned>>: Serialize, + for<'a> RefOwnedAlloc<'a, PvmLayout>: Serialize, AllocatedOf, Owned>: DeserializeOwned, { let space = { diff --git a/src/riscv/lib/tests/test_determinism.rs b/src/riscv/lib/tests/test_determinism.rs index d51e6b5e70cb..331b8cae4af2 100644 --- a/src/riscv/lib/tests/test_determinism.rs +++ b/src/riscv/lib/tests/test_determinism.rs @@ -8,7 +8,7 @@ use common::*; use octez_riscv::{ machine_state::{main_memory::M100M, DefaultCacheLayouts}, pvm::PvmLayout, - state_backend::{hash, owned_backend::Owned, AllocatedOf, Ref}, + state_backend::{hash, RefOwnedAlloc}, stepper::{pvm::PvmStepper, Stepper, StepperStatus}, }; use std::ops::Bound; @@ -44,7 +44,7 @@ fn test_jstz_determinism() { fn run_steps_ladder( make_stepper: F, ladder: &[usize], - expected_refs: &AllocatedOf, Ref<'_, Owned>>, + expected_refs: &RefOwnedAlloc>, expected_hash: hash::Hash, ) where F: Fn() -> PvmStepper<'static, M100M, DefaultCacheLayouts>, @@ -109,8 +109,8 @@ where } fn assert_eq_struct_wrapper<'a, 'regions1, 'regions2>( - refs: AllocatedOf, Ref<'regions1, Owned>>, - expected: &'a AllocatedOf, Ref<'regions2, Owned>>, + refs: RefOwnedAlloc<'regions1, PvmLayout>, + expected: &'a RefOwnedAlloc<'regions2, PvmLayout>, ) { // SAFETY: Rust does not allow us to compare two references with different lifetimes. // Theoretically this should be possible and safe thanks to `PartialEq`. However, Rust's @@ -120,7 +120,7 @@ fn assert_eq_struct_wrapper<'a, 'regions1, 'regions2>( // the `==` operator need to be identical in type. This also means lifetimes are forcibly // unified. We can work around this by transmuting the references to the same lifetime. This is // safe because lifetimes are not violated as dictated by the interface of this function. - let refs: AllocatedOf, Ref<'regions2, Owned>> = + let refs: RefOwnedAlloc<'regions2, PvmLayout> = unsafe { std::mem::transmute(refs) }; assert_eq_struct(&refs, expected); } -- GitLab