reth_engine_primitives/
lib.rs

1//! Traits, validation methods, and helper types used to abstract over engine types.
2
3#![doc(
4    html_logo_url = "https://raw.githubusercontent.com/paradigmxyz/reth/main/assets/reth-docs.png",
5    html_favicon_url = "https://avatars0.githubusercontent.com/u/97369466?s=256",
6    issue_tracker_base_url = "https://github.com/SeismicSystems/seismic-reth/issues/"
7)]
8#![cfg_attr(not(test), warn(unused_crate_dependencies))]
9#![cfg_attr(docsrs, feature(doc_cfg, doc_auto_cfg))]
10#![cfg_attr(not(feature = "std"), no_std)]
11
12extern crate alloc;
13
14use alloy_consensus::BlockHeader;
15use reth_errors::ConsensusError;
16use reth_payload_primitives::{
17    EngineApiMessageVersion, EngineObjectValidationError, InvalidPayloadAttributesError,
18    NewPayloadError, PayloadAttributes, PayloadOrAttributes, PayloadTypes,
19};
20use reth_primitives_traits::{Block, RecoveredBlock};
21use reth_trie_common::HashedPostState;
22use serde::{de::DeserializeOwned, Serialize};
23
24// Re-export [`ExecutionPayload`] moved to `reth_payload_primitives`
25pub use reth_payload_primitives::ExecutionPayload;
26
27mod error;
28pub use error::*;
29
30mod forkchoice;
31pub use forkchoice::{ForkchoiceStateHash, ForkchoiceStateTracker, ForkchoiceStatus};
32
33mod message;
34pub use message::*;
35
36mod event;
37pub use event::*;
38
39mod invalid_block_hook;
40pub use invalid_block_hook::InvalidBlockHook;
41
42pub mod config;
43pub use config::*;
44
45/// This type defines the versioned types of the engine API based on the [ethereum engine API](https://github.com/ethereum/execution-apis/tree/main/src/engine).
46///
47/// This includes the execution payload types and payload attributes that are used to trigger a
48/// payload job. Hence this trait is also [`PayloadTypes`].
49///
50/// Implementations of this type are intended to be stateless and just define the types as
51/// associated types.
52/// This type is intended for non-ethereum chains that closely mirror the ethereum engine API spec,
53/// but may have different payload, for example opstack, but structurally equivalent otherwise (same
54/// engine API RPC endpoints for example).
55pub trait EngineTypes:
56    PayloadTypes<
57        BuiltPayload: TryInto<Self::ExecutionPayloadEnvelopeV1>
58                          + TryInto<Self::ExecutionPayloadEnvelopeV2>
59                          + TryInto<Self::ExecutionPayloadEnvelopeV3>
60                          + TryInto<Self::ExecutionPayloadEnvelopeV4>
61                          + TryInto<Self::ExecutionPayloadEnvelopeV5>,
62    > + DeserializeOwned
63    + Serialize
64{
65    /// Execution Payload V1 envelope type.
66    type ExecutionPayloadEnvelopeV1: DeserializeOwned
67        + Serialize
68        + Clone
69        + Unpin
70        + Send
71        + Sync
72        + 'static;
73    /// Execution Payload V2  envelope type.
74    type ExecutionPayloadEnvelopeV2: DeserializeOwned
75        + Serialize
76        + Clone
77        + Unpin
78        + Send
79        + Sync
80        + 'static;
81    /// Execution Payload V3 envelope type.
82    type ExecutionPayloadEnvelopeV3: DeserializeOwned
83        + Serialize
84        + Clone
85        + Unpin
86        + Send
87        + Sync
88        + 'static;
89    /// Execution Payload V4 envelope type.
90    type ExecutionPayloadEnvelopeV4: DeserializeOwned
91        + Serialize
92        + Clone
93        + Unpin
94        + Send
95        + Sync
96        + 'static;
97    /// Execution Payload V5 envelope type.
98    type ExecutionPayloadEnvelopeV5: DeserializeOwned
99        + Serialize
100        + Clone
101        + Unpin
102        + Send
103        + Sync
104        + 'static;
105}
106
107/// Type that validates an [`ExecutionPayload`].
108#[auto_impl::auto_impl(&, Arc)]
109pub trait PayloadValidator: Send + Sync + Unpin + 'static {
110    /// The block type used by the engine.
111    type Block: Block;
112
113    /// The execution payload type used by the engine.
114    type ExecutionData;
115
116    /// Ensures that the given payload does not violate any consensus rules that concern the block's
117    /// layout.
118    ///
119    /// This function must convert the payload into the executable block and pre-validate its
120    /// fields.
121    ///
122    /// Implementers should ensure that the checks are done in the order that conforms with the
123    /// engine-API specification.
124    fn ensure_well_formed_payload(
125        &self,
126        payload: Self::ExecutionData,
127    ) -> Result<RecoveredBlock<Self::Block>, NewPayloadError>;
128
129    /// Verifies payload post-execution w.r.t. hashed state updates.
130    fn validate_block_post_execution_with_hashed_state(
131        &self,
132        _state_updates: &HashedPostState,
133        _block: &RecoveredBlock<Self::Block>,
134    ) -> Result<(), ConsensusError> {
135        // method not used by l1
136        Ok(())
137    }
138}
139
140/// Type that validates the payloads processed by the engine.
141pub trait EngineValidator<Types: PayloadTypes>:
142    PayloadValidator<ExecutionData = Types::ExecutionData>
143{
144    /// Validates the presence or exclusion of fork-specific fields based on the payload attributes
145    /// and the message version.
146    fn validate_version_specific_fields(
147        &self,
148        version: EngineApiMessageVersion,
149        payload_or_attrs: PayloadOrAttributes<
150            '_,
151            Types::ExecutionData,
152            <Types as PayloadTypes>::PayloadAttributes,
153        >,
154    ) -> Result<(), EngineObjectValidationError>;
155
156    /// Ensures that the payload attributes are valid for the given [`EngineApiMessageVersion`].
157    fn ensure_well_formed_attributes(
158        &self,
159        version: EngineApiMessageVersion,
160        attributes: &<Types as PayloadTypes>::PayloadAttributes,
161    ) -> Result<(), EngineObjectValidationError>;
162
163    /// Validates the payload attributes with respect to the header.
164    ///
165    /// By default, this enforces that the payload attributes timestamp is greater than the
166    /// timestamp according to:
167    ///   > 7. Client software MUST ensure that payloadAttributes.timestamp is greater than
168    ///   > timestamp
169    ///   > of a block referenced by forkchoiceState.headBlockHash.
170    ///
171    /// See also [engine api spec](https://github.com/ethereum/execution-apis/tree/fe8e13c288c592ec154ce25c534e26cb7ce0530d/src/engine)
172    fn validate_payload_attributes_against_header(
173        &self,
174        attr: &<Types as PayloadTypes>::PayloadAttributes,
175        header: &<Self::Block as Block>::Header,
176    ) -> Result<(), InvalidPayloadAttributesError> {
177        if attr.timestamp() <= header.timestamp() {
178            return Err(InvalidPayloadAttributesError::InvalidTimestamp);
179        }
180        Ok(())
181    }
182}