Skip to content

Commit

Permalink
Update doc and add CI lint (#673)
Browse files Browse the repository at this point in the history
  • Loading branch information
Nashtare authored Sep 30, 2024
1 parent 8c89084 commit a4c5260
Show file tree
Hide file tree
Showing 7 changed files with 128 additions and 55 deletions.
4 changes: 3 additions & 1 deletion .github/workflows/ci.yml
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,8 @@ concurrency:

env:
CARGO_TERM_COLOR: always
RUSTFLAGS: "-D warnings"
RUSTDOCFLAGS: "-D warnings"

jobs:
test_mpt_trie:
Expand Down Expand Up @@ -204,4 +206,4 @@ jobs:
run: cargo clippy --package zero --all-targets --no-default-features --features cdk_erigon -- -D warnings -A incomplete-features

- name: Rustdoc
run: cargo doc --all
run: cargo doc --all --no-deps
10 changes: 5 additions & 5 deletions evm_arithmetization/src/cpu/kernel/constants/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -472,7 +472,7 @@ pub mod cancun_constants {
pub mod global_exit_root {
use super::*;

/// Taken from https://github.com/0xPolygonHermez/cdk-erigon/blob/61f0b6912055c73f6879ea7e9b5bac22ea5fc85c/zk/utils/global_exit_root.go#L16.
/// Taken from <https://github.com/0xPolygonHermez/cdk-erigon/blob/61f0b6912055c73f6879ea7e9b5bac22ea5fc85c/zk/utils/global_exit_root.go#L16>.
pub const GLOBAL_EXIT_ROOT_MANAGER_L2: (&str, [u8; 20]) = (
"GLOBAL_EXIT_ROOT_MANAGER_L2",
GLOBAL_EXIT_ROOT_ADDRESS.to_fixed_bytes(),
Expand All @@ -486,7 +486,7 @@ pub mod global_exit_root {
"GLOBAL_EXIT_ROOT_MANAGER_L2_STATE_KEY",
GLOBAL_EXIT_ROOT_ADDRESS_HASHED.to_fixed_bytes(),
);
/// Taken from https://github.com/0xPolygonHermez/cdk-erigon/blob/dc3cbcc59a95769626056c7bc70aade501e7741d/core/state/intra_block_state_zkevm.go#L20.
/// Taken from <https://github.com/0xPolygonHermez/cdk-erigon/blob/dc3cbcc59a95769626056c7bc70aade501e7741d/core/state/intra_block_state_zkevm.go#L20>.
pub const ADDRESS_SCALABLE_L2: Address = H160(hex!("000000000000000000000000000000005ca1ab1e"));

pub const ADDRESS_SCALABLE_L2_ADDRESS_HASHED: H256 = H256(hex!(
Expand All @@ -497,16 +497,16 @@ pub mod global_exit_root {
"ADDRESS_SCALABLE_L2_STATE_KEY",
ADDRESS_SCALABLE_L2_ADDRESS_HASHED.to_fixed_bytes(),
);
/// Taken from https://github.com/0xPolygonHermez/cdk-erigon/blob/61f0b6912055c73f6879ea7e9b5bac22ea5fc85c/zk/utils/global_exit_root.go#L17.
/// Taken from <https://github.com/0xPolygonHermez/cdk-erigon/blob/61f0b6912055c73f6879ea7e9b5bac22ea5fc85c/zk/utils/global_exit_root.go#L17>.
pub const GLOBAL_EXIT_ROOT_STORAGE_POS: (&str, u64) = ("GLOBAL_EXIT_ROOT_STORAGE_POS", 0);

/// Taken from https://github.com/0xPolygonHermez/cdk-erigon/blob/dc3cbcc59a95769626056c7bc70aade501e7741d/core/state/intra_block_state_zkevm.go#L16.
/// Taken from <https://github.com/0xPolygonHermez/cdk-erigon/blob/dc3cbcc59a95769626056c7bc70aade501e7741d/core/state/intra_block_state_zkevm.go#L16>.
pub const LAST_BLOCK_STORAGE_POS: (&str, u64) = ("LAST_BLOCK_STORAGE_POS", 0);
pub const STATE_ROOT_STORAGE_POS: (&str, u64) = ("STATE_ROOT_STORAGE_POS", 1);
pub const TIMESTAMP_STORAGE_POS: (&str, u64) = ("TIMESTAMP_STORAGE_POS", 2);
pub const BLOCK_INFO_ROOT_STORAGE_POS: (&str, u64) = ("BLOCK_INFO_ROOT_STORAGE_POS", 3);

/// Taken from https://zkevm.polygonscan.com/address/0xa40D5f56745a118D0906a34E69aeC8C0Db1cB8fA#code.
/// Taken from <https://zkevm.polygonscan.com/address/0xa40D5f56745a118D0906a34E69aeC8C0Db1cB8fA#code>.
pub const GLOBAL_EXIT_ROOT_CONTRACT_CODE: [u8; 2112] = hex!("60806040526004361061004e5760003560e01c80633659cfe6146100655780634f1ef286146100855780635c60da1b146100985780638f283970146100c9578063f851a440146100e95761005d565b3661005d5761005b6100fe565b005b61005b6100fe565b34801561007157600080fd5b5061005b6100803660046106ca565b610118565b61005b6100933660046106e5565b61015f565b3480156100a457600080fd5b506100ad6101d0565b6040516001600160a01b03909116815260200160405180910390f35b3480156100d557600080fd5b5061005b6100e43660046106ca565b61020b565b3480156100f557600080fd5b506100ad610235565b610106610292565b610116610111610331565b61033b565b565b61012061035f565b6001600160a01b0316336001600160a01b031614156101575761015481604051806020016040528060008152506000610392565b50565b6101546100fe565b61016761035f565b6001600160a01b0316336001600160a01b031614156101c8576101c38383838080601f01602080910402602001604051908101604052809392919081815260200183838082843760009201919091525060019250610392915050565b505050565b6101c36100fe565b60006101da61035f565b6001600160a01b0316336001600160a01b03161415610200576101fb610331565b905090565b6102086100fe565b90565b61021361035f565b6001600160a01b0316336001600160a01b0316141561015757610154816103f1565b600061023f61035f565b6001600160a01b0316336001600160a01b03161415610200576101fb61035f565b606061028583836040518060600160405280602781526020016107e460279139610445565b9392505050565b3b151590565b61029a61035f565b6001600160a01b0316336001600160a01b031614156101165760405162461bcd60e51b815260206004820152604260248201527f5472616e73706172656e745570677261646561626c6550726f78793a2061646d60448201527f696e2063616e6e6f742066616c6c6261636b20746f2070726f78792074617267606482015261195d60f21b608482015260a4015b60405180910390fd5b60006101fb610519565b3660008037600080366000845af43d6000803e80801561035a573d6000f35b3d6000fd5b60007fb53127684a568b3173ae13b9f8a6016e243e63b6e8ee1178d6a717850b5d61035b546001600160a01b0316919050565b61039b83610541565b6040516001600160a01b038416907fbc7cd75a20ee27fd9adebab32041f755214dbc6bffa90cc0225b39da2e5c2d3b90600090a26000825111806103dc5750805b156101c3576103eb8383610260565b50505050565b7f7e644d79422f17c01e4894b5f4f588d331ebfa28653d42ae832dc59e38c9798f61041a61035f565b604080516001600160a01b03928316815291841660208301520160405180910390a1610154816105e9565b6060833b6104a45760405162461bcd60e51b815260206004820152602660248201527f416464726573733a2064656c65676174652063616c6c20746f206e6f6e2d636f6044820152651b9d1c9858dd60d21b6064820152608401610328565b600080856001600160a01b0316856040516104bf9190610794565b600060405180830381855af49150503d80600081146104fa576040519150601f19603f3d011682016040523d82523d6000602084013e6104ff565b606091505b509150915061050f828286610675565b9695505050505050565b60007f360894a13ba1a3210667c828492db98dca3e2076cc3735a920a3ca505d382bbc610383565b803b6105a55760405162461bcd60e51b815260206004820152602d60248201527f455243313936373a206e657720696d706c656d656e746174696f6e206973206e60448201526c1bdd08184818dbdb9d1c9858dd609a1b6064820152608401610328565b807f360894a13ba1a3210667c828492db98dca3e2076cc3735a920a3ca505d382bbc5b80546001600160a01b0319166001600160a01b039290921691909117905550565b6001600160a01b03811661064e5760405162461bcd60e51b815260206004820152602660248201527f455243313936373a206e65772061646d696e20697320746865207a65726f206160448201526564647265737360d01b6064820152608401610328565b807fb53127684a568b3173ae13b9f8a6016e243e63b6e8ee1178d6a717850b5d61036105c8565b60608315610684575081610285565b8251156106945782518084602001fd5b8160405162461bcd60e51b815260040161032891906107b0565b80356001600160a01b03811681146106c557600080fd5b919050565b6000602082840312156106dc57600080fd5b610285826106ae565b6000806000604084860312156106fa57600080fd5b610703846106ae565b9250602084013567ffffffffffffffff8082111561072057600080fd5b818601915086601f83011261073457600080fd5b81358181111561074357600080fd5b87602082850101111561075557600080fd5b6020830194508093505050509250925092565b60005b8381101561078357818101518382015260200161076b565b838111156103eb5750506000910152565b600082516107a6818460208701610768565b9190910192915050565b60208152600082518060208401526107cf816040850160208701610768565b601f01601f1916919091016040019291505056fe416464726573733a206c6f772d6c6576656c2064656c65676174652063616c6c206661696c6564a26469706673582212204675187caf3a43285d9a2c1844a981e977bd52a85ff073e7fc649f73847d70a464736f6c63430008090033");
pub const GLOBAL_EXIT_ROOT_CONTRACT_CODE_HASH: [u8; 32] =
hex!("6bec2bf64f7e824109f6ed55f77dd7665801d6195e461666ad6a5342a9f6daf5");
Expand Down
3 changes: 2 additions & 1 deletion evm_arithmetization/src/fixed_recursive_verifier.rs
Original file line number Diff line number Diff line change
Expand Up @@ -2555,7 +2555,8 @@ where
.verify(wrapped_block_proof.clone())
}

/// Aggregates two proofs in manner similar to [`prove_aggregation`].
/// Aggregates two proofs in a manner similar to
/// [`AllRecursiveCircuits::prove_batch_aggregation`].
///
/// # Arguments
///
Expand Down
150 changes: 110 additions & 40 deletions evm_arithmetization/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -38,74 +38,123 @@
//!
//! Transactions need to be processed into an Intermediary Representation (IR)
//! format for the prover to be able to generate proofs of valid state
//! transition. This involves passing the encoded transaction, the header of the
//! block in which it was included, some information on the state prior
//! execution of this transaction, etc.
//! This intermediary representation is called [`GenerationInputs`].
//! transition. This involves passing the encoded transactions, the header of
//! the block in which they were included, some information on the state prior
//! execution of these transactions, etc.
//! This intermediary representation is called [`GenerationInputs`], although
//! the prover may sometimes rely on a trimmed version,
//! [`TrimmedGenerationInputs`], if some initial data processing already
//! happened.
//!
//!
//! # Generating succinct proofs
//!
//! ## Transaction proofs
//! ## Segment proofs
//!
//! To generate a proof for a transaction, given its [`GenerationInputs`] and an
//! [`AllRecursiveCircuits`] prover state, one can simply call the
//! [prove_root](AllRecursiveCircuits::prove_root) method.
//! To generate a proof for a batch of transactions,
//! given their [`GenerationInputs`] and an [`AllRecursiveCircuits`] prover
//! state, we first break the execution down into consecutive segments, each
//! representing a partial run of the zkCPU over these inputs. For this step,
//! one must first generate the data needed for each of these segments by
//! initializing a [`SegmentDataIterator`] from the inputs and an optional
//! maximum segment length, and running it until exhaustion. One can then call
//! the [prove_segment](AllRecursiveCircuits::prove_segment) method over each of
//! these obtained segment data independently to generate individual segment
//! proofs:
//!
//! ```ignore
//! type F = GoldilocksField;
//!
//! let mut timing = TimingTree::new("prove", log::Level::Debug);
//! let kill_signal = None; // Useful only with distributed proving to kill hanging jobs.
//! let (proof, public_values) =
//! prover_state.prove_root(all_stark, config, inputs, &mut timing, kill_signal);
//!
//! // Collect the segment data needed to prove this batch.
//! let data_iterator =
//! SegmentDataIterator::<Field>::new(inputs, Some(max_segment_log_length));
//!
//! // Prove all segments associated to this batch
//! let mut segment_proof_data = vec![];
//! for segment_run in data_iterator {
//! let (_, mut segment_data) = segment_run?;
//! segment_proof_data.push(
//! prover_state.prove_segment(
//! all_stark,
//! config,
//! inputs,
//! segment_data,
//! &mut timing,
//! kill_signal
//! )?
//! );
//! }
//! ```
//!
//! This outputs a transaction proof and its associated public values. These are
//! necessary during the aggregation levels (see below). If one were to miss the
//! public values, they are also retrievable directly from the proof's encoded
//! public inputs, as such:
//! The [prove_segment](AllRecursiveCircuits::prove_segment) method outputs a
//! segment proof and its associated public values. Public values are also
//! directly retrievable from the proof's encoded public inputs, as such:
//!
//! ```ignore
//! let public_values = PublicValues::from_public_inputs(&proof.public_inputs);
//! ```
//!
//! ## Aggregation proofs
//! ## Segment aggregation proofs
//!
//! Because the plonky2 zkEVM generates proofs on a transaction basis, we then
//! need to aggregate them for succinct verification. This is done in a binary
//! tree fashion, where each inner node proof verifies two children proofs,
//! through the [prove_aggregation](AllRecursiveCircuits::prove_aggregation)
//! To improve parallelism and overall proving costs, segments of
//! execution can be proven independently once their associated data have been
//! generated, and are then aggregated together in a binary tree fashion,
//! where each inner node proof verifies two children proofs, through the
//! [prove_segment_aggregation](AllRecursiveCircuits::prove_segment_aggregation)
//! method. Note that the tree does *not* need to be complete, as this
//! aggregation process can take as inputs both regular transaction proofs and
//! aggregation proofs. We only need to specify for each child if it is an
//! aggregation proof or a regular one.
//! aggregation process can take as inputs both simple segment proofs and
//! aggregated segment proofs. We only need to specify for each child which
//! type of proof it corresponds to.
//!
//! ```ignore
//! let (proof_1, pv_1) =
//! prover_state.prove_root(all_stark, config, inputs_1, &mut timing, None);
//! prover_state.prove_segment(all_stark, config, inputs_1, &mut timing, None);
//! let (proof_2, pv_2) =
//! prover_state.prove_root(all_stark, config, inputs_2, &mut timing, None);
//! prover_state.prove_segment(all_stark, config, inputs_2, &mut timing, None);
//! let (proof_3, pv_3) =
//! prover_state.prove_root(all_stark, config, inputs_3, &mut timing, None);
//! prover_state.prove_segment(all_stark, config, inputs_3, &mut timing, None);
//!
//! // Now aggregate proofs for txn 1 and 2.
//! let (agg_proof_1_2, pv_1_2) =
//! prover_state.prove_aggregation(false, proof_1, pv_1, false, proof_2, pv_2);
//! // Now aggregate proofs for segments 1 and 2.
//! let agg_proof_1_2 =
//! prover_state.prove_segment_aggregation(proof_1, proof_2);
//!
//! // Now aggregate the newly generated aggregation proof with the last regular txn proof.
//! let (agg_proof_1_3, pv_1_3) =
//! prover_state.prove_aggregation(true, agg_proof_1_2, pv_1_2, false, proof_3, pv_3);
//! // Now aggregate the newly generated aggregation proof with the last regular segment proof.
//! let agg_proof_1_3 =
//! prover_state.prove_segment_aggregation(agg_proof_1_2, proof_3);
//! ```
//!
//! **Note**: The proofs provided to the
//! [prove_aggregation](AllRecursiveCircuits::prove_aggregation) method *MUST*
//! have contiguous states. Trying to combine `proof_1` and `proof_3` from the
//! example above would fail.
//! [prove_segment_aggregation](AllRecursiveCircuits::prove_segment_aggregation)
//! method *MUST* have contiguous states. Trying to combine `proof_1` and
//! `proof_3` from the example above, or reverting the order of `agg_proof_1_2`
//! and `proof_3`, would fail.
//!
//! ## Batch aggregation proofs
//!
//! In a similar manner to the previous stage, once an entire batch of
//! transaction has been proven and reduced to a single segment aggregation
//! proof, it can then be combined with other batch proofs or aggregated batch
//! proofs, through the
//! [prove_batch_aggregation](AllRecursiveCircuits::prove_batch_aggregation)
//! method.
//!
//! ```ignore
//! let batch_agg_proof =
//! prover_state.prove_batch_aggregation(false, batch_proof_1, false, batch_proof_2);
//!
//! // Now aggregate the newly generated batch aggregation proof with the last regular batch proof.
//! let batch_agg_proof =
//! prover_state.prove_batch_aggregation(batch_agg_proof, batch_proof_3);
//! ```
//!
//! ## Block proofs
//!
//! Once all transactions of a block have been proven and we are left with a
//! single aggregation proof and its public values, we can then wrap it into a
//! final block proof, attesting validity of the entire block.
//! single aggregated batch proof and its public values, we can then wrap it
//! into a final block proof, attesting validity of the entire block.
//! This [prove_block](AllRecursiveCircuits::prove_block) method accepts an
//! optional previous block proof as argument, which will then try combining the
//! previously proven block with the current one, generating a validity proof
Expand All @@ -114,8 +163,8 @@
//!
//! ```ignore
//! let previous_block_proof = { ... };
//! let (block_proof, block_public_values) =
//! prover_state.prove_block(Some(&previous_block_proof), &agg_proof, agg_pv)?;
//! let block_proof =
//! prover_state.prove_block(Some(&previous_block_proof), &agg_proof)?;
//! ```
//!
//! ### Checkpoint heights
Expand All @@ -135,10 +184,31 @@
//!
//!
//! ```ignore
//! let (block_proof, block_public_values) =
//! prover_state.prove_block(None, &agg_proof, agg_pv)?;
//! let block_proof =
//! prover_state.prove_block(None, &agg_proof)?;
//! ```
//!
//! ## Wrapped block proofs
//!
//! Public values expose data useful for aggregating intermediate proofs
//! together, but may not be disclosed to verifiers outside of the chain in
//! their entirety. For this purpose, once a chain has aggregated sufficiently
//! many blocks together and wants to ship the final generated proof, it may
//! call the [prove_block_wrapper](AllRecursiveCircuits::prove_block_wrapper)
//! method to obfuscate any non-required chain data. The remaining
//! [FinalPublicValues](proof::FinalPublicValues) contain all the data
//! needed to identify the chain and its claimed state transition between two
//! checkpoint heights.
//!
//! ```ignore
//! let (wrapped_block_proof, final_public_values) =
//! prover_state.prove_block_wrapper(&block_proof, public_values)?;
//! ```
//!
//! **Note**: Despite its name, the method produces a [`plonky2`] proof, which
//! may not be suitable for direct on-chain verification in a smart-contract,
//! unlike pairing-based SNARK proofs.
//!
//! # Prover state serialization
//!
//! Because the recursive circuits only need to be generated once, they can be
Expand Down
2 changes: 1 addition & 1 deletion smt_trie/src/smt.rs
Original file line number Diff line number Diff line change
Expand Up @@ -161,7 +161,7 @@ impl<D: Db> Smt<D> {

/// Set the value associated with the key in the SMT.
/// If the value is 0 and the key is in the SMT, the key is removed from the
/// SMT. Reference implementation in https://github.com/0xPolygonHermez/zkevm-commonjs/blob/main/src/smt.js.
/// SMT. Reference implementation in <https://github.com/0xPolygonHermez/zkevm-commonjs/blob/main/src/smt.js>.
pub fn set(&mut self, key: Key, value: U256) {
if value.is_zero() {
self.kv_store.remove(&key);
Expand Down
2 changes: 1 addition & 1 deletion trace_decoder/src/core.rs
Original file line number Diff line number Diff line change
Expand Up @@ -27,7 +27,7 @@ use crate::{
TxnInfo, TxnMeta, TxnTrace,
};

/// TODO(0xaatif): document this after https://github.com/0xPolygonZero/zk_evm/issues/275
/// TODO(0xaatif): document this after <https://github.com/0xPolygonZero/zk_evm/issues/275>
pub fn entrypoint(
trace: BlockTrace,
other: OtherBlockData,
Expand Down
12 changes: 6 additions & 6 deletions zero/src/prover_state/mod.rs
Original file line number Diff line number Diff line change
@@ -1,16 +1,16 @@
//! Global prover state management and utilities.
//!
//! This module provides the following:
//! - [`Circuit`] and [`CircuitConfig`] which can be used to dynamically
//! construct [`evm_arithmetization::fixed_recursive_verifier::AllRecursiveCircuits`]
//! from the specified circuit sizes.
//! - [`ProverState`] and [`CircuitConfig`] which can be used to dynamically
//! construct [`evm_arithmetization::AllRecursiveCircuits`] from the specified
//! circuit sizes.
//! - Command line arguments for constructing a [`CircuitConfig`].
//! - Provides default values for the circuit sizes.
//! - Allows the circuit sizes to be specified via environment variables.
//! - Persistence utilities for saving and loading
//! [`evm_arithmetization::fixed_recursive_verifier::AllRecursiveCircuits`].
//! - Global prover state management via the [`P_STATE`] static and the
//! [`set_prover_state_from_config`] function.
//! [`evm_arithmetization::AllRecursiveCircuits`].
//! - Global prover state management via the `P_STATE` static and the
//! [`p_state`] function.
use std::borrow::Borrow;
use std::{fmt::Display, sync::OnceLock};

Expand Down

0 comments on commit a4c5260

Please sign in to comment.