From 657d313bc458a09823d9f5bc07842eb197e9b774 Mon Sep 17 00:00:00 2001 From: Zach Obront Date: Fri, 22 Nov 2024 13:13:14 -0600 Subject: [PATCH] L2ExecutePayloadProof Hint Type (#832) * l2 execute payload proof hint type * lint * correct types * tested & linted * rm engine featue import * change naming to align with spec --- Cargo.lock | 12 ++++++++++ Cargo.toml | 4 ++-- bin/host/Cargo.toml | 1 + bin/host/src/fetcher/mod.rs | 38 ++++++++++++++++++++++++++++-- crates/proof-sdk/proof/src/hint.rs | 5 ++++ 5 files changed, 56 insertions(+), 4 deletions(-) diff --git a/Cargo.lock b/Cargo.lock index 1912dc618..a5d280249 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -312,6 +312,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "c74832aa474b670309c20fffc2a869fa141edab7c79ff7963fad0a08de60bae1" dependencies = [ "alloy-primitives", + "alloy-rpc-types-debug", "alloy-rpc-types-eth", "alloy-serde", "serde", @@ -331,6 +332,16 @@ dependencies = [ "thiserror 1.0.69", ] +[[package]] +name = "alloy-rpc-types-debug" +version = "0.6.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ba2253bee958658ebd614c07a61c40580e09dd1fad3f017684314442332ab753" +dependencies = [ + "alloy-primitives", + "serde", +] + [[package]] name = "alloy-rpc-types-engine" version = "0.6.4" @@ -2447,6 +2458,7 @@ dependencies = [ "kona-proof", "op-alloy-genesis", "op-alloy-protocol", + "op-alloy-rpc-types-engine", "os_pipe", "proptest", "reqwest", diff --git a/Cargo.toml b/Cargo.toml index 661e4a017..4f13681ab 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -81,7 +81,7 @@ alloy-provider = { version = "0.6.4", default-features = false } alloy-primitives = { version = "0.8.12", default-features = false } alloy-consensus = { version = "0.6.4", default-features = false } alloy-transport = { version = "0.6.4", default-features = false } -alloy-rpc-types = { version = "0.6.4", default-features = false } +alloy-rpc-types = { version = "0.6.4", default-features = false, features = ["debug"] } alloy-rpc-client = { version = "0.6.4", default-features = false } alloy-node-bindings = { version = "0.6.4", default-features = false } alloy-transport-http = { version = "0.6.4", default-features = false } @@ -93,7 +93,7 @@ op-alloy-genesis = { version = "0.6.8", default-features = false } op-alloy-registry = { version = "0.6.8", default-features = false } op-alloy-protocol = { version = "0.6.8", default-features = false } op-alloy-consensus = { version = "0.6.8", default-features = false } -op-alloy-rpc-types-engine = { version = "0.6.8", default-features = false } +op-alloy-rpc-types-engine = { version = "0.6.8", default-features = false, features = ["serde"] } # General lru = "0.12.4" diff --git a/bin/host/Cargo.toml b/bin/host/Cargo.toml index 66058f0e1..43ee726db 100644 --- a/bin/host/Cargo.toml +++ b/bin/host/Cargo.toml @@ -35,6 +35,7 @@ alloy-rpc-types-beacon.workspace = true # Op Alloy op-alloy-genesis = { workspace = true, features = ["std", "serde"] } op-alloy-protocol = { workspace = true, features = ["std", "serde"] } +op-alloy-rpc-types-engine.workspace = true # Revm revm = { workspace = true, features = ["std", "c-kzg", "secp256k1", "portable", "blst"] } diff --git a/bin/host/src/fetcher/mod.rs b/bin/host/src/fetcher/mod.rs index e635335a1..07557348e 100644 --- a/bin/host/src/fetcher/mod.rs +++ b/bin/host/src/fetcher/mod.rs @@ -8,17 +8,19 @@ use crate::{ }; use alloy_consensus::{Header, TxEnvelope, EMPTY_ROOT_HASH}; use alloy_eips::{eip2718::Encodable2718, eip4844::FIELD_ELEMENTS_PER_BLOB, BlockId}; -use alloy_primitives::{address, keccak256, Address, Bytes, B256}; +use alloy_primitives::{address, keccak256, map::HashMap, Address, Bytes, B256}; use alloy_provider::{Provider, ReqwestProvider}; use alloy_rlp::{Decodable, EMPTY_STRING_CODE}; use alloy_rpc_types::{ - Block, BlockNumberOrTag, BlockTransactions, BlockTransactionsKind, Transaction, + debug::ExecutionWitness, Block, BlockNumberOrTag, BlockTransactions, BlockTransactionsKind, + Transaction, }; use anyhow::{anyhow, Result}; use kona_derive::sources::IndexedBlobHash; use kona_preimage::{PreimageKey, PreimageKeyType}; use kona_proof::HintType; use op_alloy_protocol::BlockInfo; +use op_alloy_rpc_types_engine::OpPayloadAttributes; use std::sync::Arc; use tokio::sync::RwLock; use tracing::{error, trace, warn}; @@ -507,6 +509,38 @@ where Ok::<(), anyhow::Error>(()) })?; } + HintType::L2PayloadWitness => { + if hint_data.len() < 32 { + anyhow::bail!("Invalid hint data length: {}", hint_data.len()); + } + let parent_block_hash = B256::from_slice(&hint_data.as_ref()[..32]); + let payload_attributes: OpPayloadAttributes = + serde_json::from_slice(&hint_data[32..])?; + + let execute_payload_response: ExecutionWitness = self + .l2_provider + .client() + .request::<(B256, OpPayloadAttributes), ExecutionWitness>( + "debug_executePayload", + (parent_block_hash, payload_attributes), + ) + .await + .map_err(|e| anyhow!("Failed to fetch preimage: {e}"))?; + + let mut merged = HashMap::::new(); + merged.extend(execute_payload_response.state); + merged.extend(execute_payload_response.codes); + merged.extend(execute_payload_response.keys); + + let mut kv_write_lock = self.kv_store.write().await; + for (hash, preimage) in merged.into_iter() { + let computed_hash = keccak256(preimage.as_ref()); + assert_eq!(computed_hash, hash, "Preimage hash does not match expected hash"); + + let key = PreimageKey::new(*hash, PreimageKeyType::Keccak256); + kv_write_lock.set(key.into(), preimage.into())?; + } + } } Ok(()) diff --git a/crates/proof-sdk/proof/src/hint.rs b/crates/proof-sdk/proof/src/hint.rs index fce3218ca..f63af9b5f 100644 --- a/crates/proof-sdk/proof/src/hint.rs +++ b/crates/proof-sdk/proof/src/hint.rs @@ -36,6 +36,9 @@ pub enum HintType { /// A hint that specifies the proof on the path to a storage slot in an account within in the /// L2 state trie. L2AccountStorageProof, + /// A hint that specifies bulk storage of all the code, state and keys generated by an + /// execution witness. + L2PayloadWitness, } impl HintType { @@ -63,6 +66,7 @@ impl TryFrom<&str> for HintType { "l2-state-node" => Ok(Self::L2StateNode), "l2-account-proof" => Ok(Self::L2AccountProof), "l2-account-storage-proof" => Ok(Self::L2AccountStorageProof), + "l2-payload-witness" => Ok(Self::L2PayloadWitness), _ => Err(HintParsingError(value.to_string())), } } @@ -83,6 +87,7 @@ impl From for &str { HintType::L2StateNode => "l2-state-node", HintType::L2AccountProof => "l2-account-proof", HintType::L2AccountStorageProof => "l2-account-storage-proof", + HintType::L2PayloadWitness => "l2-payload-witness", } } }