mirror of
https://github.com/sigp/lighthouse.git
synced 2026-07-05 13:54:36 +00:00
Make BeaconChain::kzg field mandatory (#6267)
* make kzg field required * update todo * always load trusted setup WIP * fmt * use new rust_eth_kzg version * merge conlficts * add kzg fn with trusted setup disabled * as_slice * add kzg with no precomp * ignore udep for kzg * refactor kzg init * fix peerdas kzg schedule * fix * udeps * uuuudeps * merge conflict resolved * merge conflict * merge conflicts * resolve TODO * update * move kzg to a test util fn * remove trusted setup default impl * lint fmt * fix failing test * lint * fix test * Merge branch 'unstable' into beacon-chain-kzg-field-required
This commit is contained in:
8
Cargo.lock
generated
8
Cargo.lock
generated
@@ -1408,6 +1408,7 @@ dependencies = [
|
||||
"genesis",
|
||||
"http_api",
|
||||
"http_metrics",
|
||||
"kzg",
|
||||
"lighthouse_metrics",
|
||||
"lighthouse_network",
|
||||
"monitoring_api",
|
||||
@@ -1415,6 +1416,7 @@ dependencies = [
|
||||
"operation_pool",
|
||||
"sensitive_url",
|
||||
"serde",
|
||||
"serde_json",
|
||||
"serde_yaml",
|
||||
"slasher",
|
||||
"slasher_service",
|
||||
@@ -2621,6 +2623,7 @@ dependencies = [
|
||||
"discv5",
|
||||
"eth2_config",
|
||||
"ethereum_ssz",
|
||||
"kzg",
|
||||
"logging",
|
||||
"pretty_reqwest_error",
|
||||
"reqwest",
|
||||
@@ -4413,7 +4416,6 @@ dependencies = [
|
||||
"c-kzg",
|
||||
"criterion",
|
||||
"derivative",
|
||||
"eth2_network_config",
|
||||
"ethereum_hashing",
|
||||
"ethereum_serde_utils",
|
||||
"ethereum_ssz",
|
||||
@@ -5641,6 +5643,7 @@ dependencies = [
|
||||
"derivative",
|
||||
"error-chain",
|
||||
"eth2",
|
||||
"eth2_network_config",
|
||||
"ethereum_ssz",
|
||||
"execution_layer",
|
||||
"fnv",
|
||||
@@ -5650,6 +5653,7 @@ dependencies = [
|
||||
"hex",
|
||||
"igd-next",
|
||||
"itertools 0.10.5",
|
||||
"kzg",
|
||||
"lighthouse_metrics",
|
||||
"lighthouse_network",
|
||||
"logging",
|
||||
@@ -5658,6 +5662,7 @@ dependencies = [
|
||||
"operation_pool",
|
||||
"parking_lot 0.12.3",
|
||||
"rand",
|
||||
"serde_json",
|
||||
"slog",
|
||||
"slog-async",
|
||||
"slog-term",
|
||||
@@ -7746,6 +7751,7 @@ dependencies = [
|
||||
"eth2_network_config",
|
||||
"execution_layer",
|
||||
"futures",
|
||||
"kzg",
|
||||
"node_test_rig",
|
||||
"parking_lot 0.12.3",
|
||||
"rayon",
|
||||
|
||||
@@ -1,11 +1,11 @@
|
||||
use std::sync::Arc;
|
||||
|
||||
use beacon_chain::kzg_utils::{blobs_to_data_column_sidecars, reconstruct_data_columns};
|
||||
use beacon_chain::test_utils::get_kzg;
|
||||
use criterion::{black_box, criterion_group, criterion_main, Criterion};
|
||||
|
||||
use bls::Signature;
|
||||
use eth2_network_config::TRUSTED_SETUP_BYTES;
|
||||
use kzg::{Kzg, KzgCommitment, TrustedSetup};
|
||||
use kzg::KzgCommitment;
|
||||
use types::{
|
||||
beacon_block_body::KzgCommitments, BeaconBlock, BeaconBlockDeneb, Blob, BlobsList, ChainSpec,
|
||||
EmptyBlock, EthSpec, MainnetEthSpec, SignedBeaconBlock,
|
||||
@@ -35,11 +35,7 @@ fn all_benches(c: &mut Criterion) {
|
||||
type E = MainnetEthSpec;
|
||||
let spec = Arc::new(E::default_spec());
|
||||
|
||||
let trusted_setup: TrustedSetup = serde_json::from_reader(TRUSTED_SETUP_BYTES)
|
||||
.map_err(|e| format!("Unable to read trusted setup file: {}", e))
|
||||
.expect("should have trusted setup");
|
||||
let kzg = Arc::new(Kzg::new_from_trusted_setup(trusted_setup).expect("should create kzg"));
|
||||
|
||||
let kzg = get_kzg(&spec);
|
||||
for blob_count in [1, 2, 3, 6] {
|
||||
let kzg = kzg.clone();
|
||||
let (signed_block, blob_sidecars) = create_test_block_and_blobs::<E>(blob_count, &spec);
|
||||
|
||||
@@ -497,7 +497,7 @@ pub struct BeaconChain<T: BeaconChainTypes> {
|
||||
/// they are collected and combined.
|
||||
pub data_availability_checker: Arc<DataAvailabilityChecker<T>>,
|
||||
/// The KZG trusted setup used by this chain.
|
||||
pub kzg: Option<Arc<Kzg>>,
|
||||
pub kzg: Arc<Kzg>,
|
||||
}
|
||||
|
||||
pub enum BeaconBlockResponseWrapper<E: EthSpec> {
|
||||
@@ -5682,10 +5682,8 @@ impl<T: BeaconChainTypes> BeaconChain<T> {
|
||||
|
||||
let kzg_proofs = Vec::from(proofs);
|
||||
|
||||
let kzg = self
|
||||
.kzg
|
||||
.as_ref()
|
||||
.ok_or(BlockProductionError::TrustedSetupNotInitialized)?;
|
||||
let kzg = self.kzg.as_ref();
|
||||
|
||||
kzg_utils::validate_blobs::<T::EthSpec>(
|
||||
kzg,
|
||||
expected_kzg_commitments,
|
||||
|
||||
@@ -115,13 +115,6 @@ pub enum GossipBlobError {
|
||||
index: u64,
|
||||
},
|
||||
|
||||
/// `Kzg` struct hasn't been initialized. This is an internal error.
|
||||
///
|
||||
/// ## Peer scoring
|
||||
///
|
||||
/// The peer isn't faulty, This is an internal error.
|
||||
KzgNotInitialized,
|
||||
|
||||
/// The kzg verification failed.
|
||||
///
|
||||
/// ## Peer scoring
|
||||
@@ -559,11 +552,9 @@ pub fn validate_blob_sidecar_for_gossip<T: BeaconChainTypes>(
|
||||
}
|
||||
|
||||
// Kzg verification for gossip blob sidecar
|
||||
let kzg = chain
|
||||
.kzg
|
||||
.as_ref()
|
||||
.ok_or(GossipBlobError::KzgNotInitialized)?;
|
||||
let kzg_verified_blob = KzgVerifiedBlob::new(blob_sidecar, kzg, seen_timestamp)
|
||||
let kzg = chain.kzg.as_ref();
|
||||
|
||||
let kzg_verified_blob = KzgVerifiedBlob::new(blob_sidecar.clone(), kzg, seen_timestamp)
|
||||
.map_err(GossipBlobError::KzgError)?;
|
||||
let blob_sidecar = &kzg_verified_blob.blob;
|
||||
|
||||
|
||||
@@ -789,19 +789,11 @@ fn build_gossip_verified_data_columns<T: BeaconChainTypes>(
|
||||
// Only attempt to build data columns if blobs is non empty to avoid skewing the metrics.
|
||||
.filter(|b| !b.is_empty())
|
||||
.map(|blobs| {
|
||||
// NOTE: we expect KZG to be initialized if the blobs are present
|
||||
let kzg = chain
|
||||
.kzg
|
||||
.as_ref()
|
||||
.ok_or(BlockContentsError::DataColumnError(
|
||||
GossipDataColumnError::KzgNotInitialized,
|
||||
))?;
|
||||
|
||||
let mut timer = metrics::start_timer_vec(
|
||||
&metrics::DATA_COLUMN_SIDECAR_COMPUTATION,
|
||||
&[&blobs.len().to_string()],
|
||||
);
|
||||
let sidecars = blobs_to_data_column_sidecars(&blobs, block, kzg, &chain.spec)
|
||||
let sidecars = blobs_to_data_column_sidecars(&blobs, block, &chain.kzg, &chain.spec)
|
||||
.discard_timer_on_break(&mut timer)?;
|
||||
drop(timer);
|
||||
let mut gossip_verified_data_columns = vec![];
|
||||
|
||||
@@ -101,7 +101,7 @@ pub struct BeaconChainBuilder<T: BeaconChainTypes> {
|
||||
// Pending I/O batch that is constructed during building and should be executed atomically
|
||||
// alongside `PersistedBeaconChain` storage when `BeaconChainBuilder::build` is called.
|
||||
pending_io_batch: Vec<KeyValueStoreOp>,
|
||||
kzg: Option<Arc<Kzg>>,
|
||||
kzg: Arc<Kzg>,
|
||||
task_executor: Option<TaskExecutor>,
|
||||
validator_monitor_config: Option<ValidatorMonitorConfig>,
|
||||
import_all_data_columns: bool,
|
||||
@@ -120,7 +120,7 @@ where
|
||||
///
|
||||
/// The `_eth_spec_instance` parameter is only supplied to make concrete the `E` trait.
|
||||
/// This should generally be either the `MinimalEthSpec` or `MainnetEthSpec` types.
|
||||
pub fn new(_eth_spec_instance: E) -> Self {
|
||||
pub fn new(_eth_spec_instance: E, kzg: Arc<Kzg>) -> Self {
|
||||
Self {
|
||||
store: None,
|
||||
store_migrator_config: None,
|
||||
@@ -143,7 +143,7 @@ where
|
||||
beacon_graffiti: GraffitiOrigin::default(),
|
||||
slasher: None,
|
||||
pending_io_batch: vec![],
|
||||
kzg: None,
|
||||
kzg,
|
||||
task_executor: None,
|
||||
validator_monitor_config: None,
|
||||
import_all_data_columns: false,
|
||||
@@ -694,11 +694,6 @@ where
|
||||
self
|
||||
}
|
||||
|
||||
pub fn kzg(mut self, kzg: Option<Arc<Kzg>>) -> Self {
|
||||
self.kzg = kzg;
|
||||
self
|
||||
}
|
||||
|
||||
/// Consumes `self`, returning a `BeaconChain` if all required parameters have been supplied.
|
||||
///
|
||||
/// An error will be returned at runtime if all required parameters have not been configured.
|
||||
@@ -1157,7 +1152,7 @@ fn descriptive_db_error(item: &str, error: &StoreError) -> String {
|
||||
#[cfg(test)]
|
||||
mod test {
|
||||
use super::*;
|
||||
use crate::test_utils::EphemeralHarnessType;
|
||||
use crate::test_utils::{get_kzg, EphemeralHarnessType};
|
||||
use ethereum_hashing::hash;
|
||||
use genesis::{
|
||||
generate_deterministic_keypairs, interop_genesis_state, DEFAULT_ETH1_BLOCK_HASH,
|
||||
@@ -1204,7 +1199,9 @@ mod test {
|
||||
let (shutdown_tx, _) = futures::channel::mpsc::channel(1);
|
||||
let runtime = TestRuntime::default();
|
||||
|
||||
let chain = Builder::new(MinimalEthSpec)
|
||||
let kzg = get_kzg(&spec);
|
||||
|
||||
let chain = Builder::new(MinimalEthSpec, kzg)
|
||||
.logger(log.clone())
|
||||
.store(Arc::new(store))
|
||||
.task_executor(runtime.task_executor.clone())
|
||||
|
||||
@@ -69,7 +69,7 @@ pub const STATE_LRU_CAPACITY: usize = STATE_LRU_CAPACITY_NON_ZERO.get();
|
||||
pub struct DataAvailabilityChecker<T: BeaconChainTypes> {
|
||||
availability_cache: Arc<DataAvailabilityCheckerInner<T>>,
|
||||
slot_clock: T::SlotClock,
|
||||
kzg: Option<Arc<Kzg>>,
|
||||
kzg: Arc<Kzg>,
|
||||
spec: Arc<ChainSpec>,
|
||||
}
|
||||
|
||||
@@ -97,7 +97,7 @@ impl<E: EthSpec> Debug for Availability<E> {
|
||||
impl<T: BeaconChainTypes> DataAvailabilityChecker<T> {
|
||||
pub fn new(
|
||||
slot_clock: T::SlotClock,
|
||||
kzg: Option<Arc<Kzg>>,
|
||||
kzg: Arc<Kzg>,
|
||||
store: BeaconStore<T>,
|
||||
import_all_data_columns: bool,
|
||||
spec: ChainSpec,
|
||||
@@ -190,17 +190,16 @@ impl<T: BeaconChainTypes> DataAvailabilityChecker<T> {
|
||||
epoch: Epoch,
|
||||
blobs: FixedBlobSidecarList<T::EthSpec>,
|
||||
) -> Result<Availability<T::EthSpec>, AvailabilityCheckError> {
|
||||
let Some(kzg) = self.kzg.as_ref() else {
|
||||
return Err(AvailabilityCheckError::KzgNotInitialized);
|
||||
};
|
||||
|
||||
let seen_timestamp = self
|
||||
.slot_clock
|
||||
.now_duration()
|
||||
.ok_or(AvailabilityCheckError::SlotClockError)?;
|
||||
|
||||
let verified_blobs =
|
||||
KzgVerifiedBlobList::new(Vec::from(blobs).into_iter().flatten(), kzg, seen_timestamp)
|
||||
let verified_blobs = KzgVerifiedBlobList::new(
|
||||
Vec::from(blobs).into_iter().flatten(),
|
||||
&self.kzg,
|
||||
seen_timestamp,
|
||||
)
|
||||
.map_err(AvailabilityCheckError::Kzg)?;
|
||||
|
||||
self.availability_cache
|
||||
@@ -217,23 +216,20 @@ impl<T: BeaconChainTypes> DataAvailabilityChecker<T> {
|
||||
custody_columns: DataColumnSidecarList<T::EthSpec>,
|
||||
) -> Result<(Availability<T::EthSpec>, DataColumnsToPublish<T::EthSpec>), AvailabilityCheckError>
|
||||
{
|
||||
let Some(kzg) = self.kzg.as_ref() else {
|
||||
return Err(AvailabilityCheckError::KzgNotInitialized);
|
||||
};
|
||||
|
||||
// TODO(das): report which column is invalid for proper peer scoring
|
||||
// TODO(das): batch KZG verification here
|
||||
let verified_custody_columns = custody_columns
|
||||
.into_iter()
|
||||
.map(|column| {
|
||||
Ok(KzgVerifiedCustodyDataColumn::from_asserted_custody(
|
||||
KzgVerifiedDataColumn::new(column, kzg).map_err(AvailabilityCheckError::Kzg)?,
|
||||
KzgVerifiedDataColumn::new(column, &self.kzg)
|
||||
.map_err(AvailabilityCheckError::Kzg)?,
|
||||
))
|
||||
})
|
||||
.collect::<Result<Vec<_>, AvailabilityCheckError>>()?;
|
||||
|
||||
self.availability_cache.put_kzg_verified_data_columns(
|
||||
kzg,
|
||||
&self.kzg,
|
||||
block_root,
|
||||
epoch,
|
||||
verified_custody_columns,
|
||||
@@ -269,9 +265,6 @@ impl<T: BeaconChainTypes> DataAvailabilityChecker<T> {
|
||||
gossip_data_columns: Vec<GossipVerifiedDataColumn<T>>,
|
||||
) -> Result<(Availability<T::EthSpec>, DataColumnsToPublish<T::EthSpec>), AvailabilityCheckError>
|
||||
{
|
||||
let Some(kzg) = self.kzg.as_ref() else {
|
||||
return Err(AvailabilityCheckError::KzgNotInitialized);
|
||||
};
|
||||
let epoch = slot.epoch(T::EthSpec::slots_per_epoch());
|
||||
|
||||
let custody_columns = gossip_data_columns
|
||||
@@ -280,7 +273,7 @@ impl<T: BeaconChainTypes> DataAvailabilityChecker<T> {
|
||||
.collect::<Vec<_>>();
|
||||
|
||||
self.availability_cache.put_kzg_verified_data_columns(
|
||||
kzg,
|
||||
&self.kzg,
|
||||
block_root,
|
||||
epoch,
|
||||
custody_columns,
|
||||
@@ -314,11 +307,7 @@ impl<T: BeaconChainTypes> DataAvailabilityChecker<T> {
|
||||
let (block_root, block, blobs, data_columns) = block.deconstruct();
|
||||
if self.blobs_required_for_block(&block) {
|
||||
return if let Some(blob_list) = blobs.as_ref() {
|
||||
let kzg = self
|
||||
.kzg
|
||||
.as_ref()
|
||||
.ok_or(AvailabilityCheckError::KzgNotInitialized)?;
|
||||
verify_kzg_for_blob_list(blob_list.iter(), kzg)
|
||||
verify_kzg_for_blob_list(blob_list.iter(), &self.kzg)
|
||||
.map_err(AvailabilityCheckError::Kzg)?;
|
||||
Ok(MaybeAvailableBlock::Available(AvailableBlock {
|
||||
block_root,
|
||||
@@ -334,15 +323,11 @@ impl<T: BeaconChainTypes> DataAvailabilityChecker<T> {
|
||||
}
|
||||
if self.data_columns_required_for_block(&block) {
|
||||
return if let Some(data_column_list) = data_columns.as_ref() {
|
||||
let kzg = self
|
||||
.kzg
|
||||
.as_ref()
|
||||
.ok_or(AvailabilityCheckError::KzgNotInitialized)?;
|
||||
verify_kzg_for_data_column_list(
|
||||
data_column_list
|
||||
.iter()
|
||||
.map(|custody_column| custody_column.as_data_column()),
|
||||
kzg,
|
||||
&self.kzg,
|
||||
)
|
||||
.map_err(AvailabilityCheckError::Kzg)?;
|
||||
Ok(MaybeAvailableBlock::Available(AvailableBlock {
|
||||
@@ -395,11 +380,7 @@ impl<T: BeaconChainTypes> DataAvailabilityChecker<T> {
|
||||
|
||||
// verify kzg for all blobs at once
|
||||
if !all_blobs.is_empty() {
|
||||
let kzg = self
|
||||
.kzg
|
||||
.as_ref()
|
||||
.ok_or(AvailabilityCheckError::KzgNotInitialized)?;
|
||||
verify_kzg_for_blob_list(all_blobs.iter(), kzg)?;
|
||||
verify_kzg_for_blob_list(all_blobs.iter(), &self.kzg)?;
|
||||
}
|
||||
|
||||
let all_data_columns = blocks
|
||||
@@ -415,11 +396,7 @@ impl<T: BeaconChainTypes> DataAvailabilityChecker<T> {
|
||||
|
||||
// verify kzg for all data columns at once
|
||||
if !all_data_columns.is_empty() {
|
||||
let kzg = self
|
||||
.kzg
|
||||
.as_ref()
|
||||
.ok_or(AvailabilityCheckError::KzgNotInitialized)?;
|
||||
verify_kzg_for_data_column_list(all_data_columns.iter(), kzg)?;
|
||||
verify_kzg_for_data_column_list(all_data_columns.iter(), &self.kzg)?;
|
||||
}
|
||||
|
||||
for block in blocks {
|
||||
|
||||
@@ -4,7 +4,6 @@ use types::{BeaconStateError, Hash256};
|
||||
#[derive(Debug)]
|
||||
pub enum Error {
|
||||
Kzg(KzgError),
|
||||
KzgNotInitialized,
|
||||
KzgVerificationFailed,
|
||||
KzgCommitmentMismatch {
|
||||
blob_commitment: KzgCommitment,
|
||||
@@ -36,8 +35,7 @@ pub enum ErrorCategory {
|
||||
impl Error {
|
||||
pub fn category(&self) -> ErrorCategory {
|
||||
match self {
|
||||
Error::KzgNotInitialized
|
||||
| Error::SszTypes(_)
|
||||
Error::SszTypes(_)
|
||||
| Error::MissingBlobs
|
||||
| Error::MissingCustodyColumns
|
||||
| Error::StoreError(_)
|
||||
|
||||
@@ -52,12 +52,6 @@ pub enum GossipDataColumnError {
|
||||
data_column_slot: Slot,
|
||||
parent_slot: Slot,
|
||||
},
|
||||
/// `Kzg` struct hasn't been initialized. This is an internal error.
|
||||
///
|
||||
/// ## Peer scoring
|
||||
///
|
||||
/// The peer isn't faulty, This is an internal error.
|
||||
KzgNotInitialized,
|
||||
/// The kzg verification failed.
|
||||
///
|
||||
/// ## Peer scoring
|
||||
@@ -382,12 +376,8 @@ pub fn validate_data_column_sidecar_for_gossip<T: BeaconChainTypes>(
|
||||
let parent_block = verify_parent_block_and_finalized_descendant(data_column.clone(), chain)?;
|
||||
verify_slot_higher_than_parent(&parent_block, column_slot)?;
|
||||
verify_proposer_and_signature(&data_column, &parent_block, chain)?;
|
||||
|
||||
let kzg = chain
|
||||
.kzg
|
||||
.clone()
|
||||
.ok_or(GossipDataColumnError::KzgNotInitialized)?;
|
||||
let kzg_verified_data_column = verify_kzg_for_data_column(data_column.clone(), &kzg)
|
||||
let kzg = &chain.kzg;
|
||||
let kzg_verified_data_column = verify_kzg_for_data_column(data_column.clone(), kzg)
|
||||
.map_err(GossipDataColumnError::InvalidKzgProof)?;
|
||||
|
||||
chain
|
||||
|
||||
@@ -291,7 +291,6 @@ pub enum BlockProductionError {
|
||||
TokioJoin(JoinError),
|
||||
BeaconChain(BeaconChainError),
|
||||
InvalidPayloadFork,
|
||||
TrustedSetupNotInitialized,
|
||||
InvalidBlockVariant(String),
|
||||
KzgError(kzg::Error),
|
||||
FailedToBuildBlobSidecars(String),
|
||||
|
||||
@@ -290,8 +290,7 @@ pub fn reconstruct_data_columns<E: EthSpec>(
|
||||
mod test {
|
||||
use crate::kzg_utils::{blobs_to_data_column_sidecars, reconstruct_data_columns};
|
||||
use bls::Signature;
|
||||
use eth2_network_config::TRUSTED_SETUP_BYTES;
|
||||
use kzg::{Kzg, KzgCommitment, TrustedSetup};
|
||||
use kzg::{trusted_setup::get_trusted_setup, Kzg, KzgCommitment, TrustedSetup};
|
||||
use types::{
|
||||
beacon_block_body::KzgCommitments, BeaconBlock, BeaconBlockDeneb, Blob, BlobsList,
|
||||
ChainSpec, EmptyBlock, EthSpec, MainnetEthSpec, SignedBeaconBlock,
|
||||
@@ -377,7 +376,7 @@ mod test {
|
||||
}
|
||||
|
||||
fn get_kzg() -> Kzg {
|
||||
let trusted_setup: TrustedSetup = serde_json::from_reader(TRUSTED_SETUP_BYTES)
|
||||
let trusted_setup: TrustedSetup = serde_json::from_reader(get_trusted_setup().as_slice())
|
||||
.map_err(|e| format!("Unable to read trusted setup file: {}", e))
|
||||
.expect("should have trusted setup");
|
||||
Kzg::new_from_trusted_setup_das_enabled(trusted_setup).expect("should create kzg")
|
||||
|
||||
@@ -18,7 +18,6 @@ use crate::{
|
||||
};
|
||||
use bls::get_withdrawal_credentials;
|
||||
use eth2::types::SignedBlockContentsTuple;
|
||||
use eth2_network_config::TRUSTED_SETUP_BYTES;
|
||||
use execution_layer::test_utils::generate_genesis_header;
|
||||
use execution_layer::{
|
||||
auth::JwtKey,
|
||||
@@ -31,6 +30,7 @@ use execution_layer::{
|
||||
use futures::channel::mpsc::Receiver;
|
||||
pub use genesis::{interop_genesis_state_with_eth1, DEFAULT_ETH1_BLOCK_HASH};
|
||||
use int_to_bytes::int_to_bytes32;
|
||||
use kzg::trusted_setup::get_trusted_setup;
|
||||
use kzg::{Kzg, TrustedSetup};
|
||||
use merkle_proof::MerkleTree;
|
||||
use operation_pool::ReceivedPreCapella;
|
||||
@@ -75,22 +75,40 @@ pub const FORK_NAME_ENV_VAR: &str = "FORK_NAME";
|
||||
// a different value.
|
||||
pub const DEFAULT_TARGET_AGGREGATORS: u64 = u64::MAX;
|
||||
|
||||
pub static KZG: LazyLock<Arc<Kzg>> = LazyLock::new(|| {
|
||||
let trusted_setup: TrustedSetup = serde_json::from_reader(TRUSTED_SETUP_BYTES)
|
||||
static KZG: LazyLock<Arc<Kzg>> = LazyLock::new(|| {
|
||||
let trusted_setup: TrustedSetup = serde_json::from_reader(get_trusted_setup().as_slice())
|
||||
.map_err(|e| format!("Unable to read trusted setup file: {}", e))
|
||||
.expect("should have trusted setup");
|
||||
let kzg = Kzg::new_from_trusted_setup(trusted_setup).expect("should create kzg");
|
||||
Arc::new(kzg)
|
||||
});
|
||||
|
||||
pub static KZG_PEERDAS: LazyLock<Arc<Kzg>> = LazyLock::new(|| {
|
||||
let trusted_setup: TrustedSetup = serde_json::from_reader(TRUSTED_SETUP_BYTES)
|
||||
static KZG_PEERDAS: LazyLock<Arc<Kzg>> = LazyLock::new(|| {
|
||||
let trusted_setup: TrustedSetup = serde_json::from_reader(get_trusted_setup().as_slice())
|
||||
.map_err(|e| format!("Unable to read trusted setup file: {}", e))
|
||||
.expect("should have trusted setup");
|
||||
let kzg = Kzg::new_from_trusted_setup_das_enabled(trusted_setup).expect("should create kzg");
|
||||
Arc::new(kzg)
|
||||
});
|
||||
|
||||
static KZG_NO_PRECOMP: LazyLock<Arc<Kzg>> = LazyLock::new(|| {
|
||||
let trusted_setup: TrustedSetup = serde_json::from_reader(get_trusted_setup().as_slice())
|
||||
.map_err(|e| format!("Unable to read trusted setup file: {}", e))
|
||||
.expect("should have trusted setup");
|
||||
let kzg = Kzg::new_from_trusted_setup_no_precomp(trusted_setup).expect("should create kzg");
|
||||
Arc::new(kzg)
|
||||
});
|
||||
|
||||
pub fn get_kzg(spec: &ChainSpec) -> Arc<Kzg> {
|
||||
if spec.eip7594_fork_epoch.is_some() {
|
||||
KZG_PEERDAS.clone()
|
||||
} else if spec.deneb_fork_epoch.is_some() {
|
||||
KZG.clone()
|
||||
} else {
|
||||
KZG_NO_PRECOMP.clone()
|
||||
}
|
||||
}
|
||||
|
||||
pub type BaseHarnessType<E, THotStore, TColdStore> =
|
||||
Witness<TestingSlotClock, CachingEth1Backend<E>, E, THotStore, TColdStore>;
|
||||
|
||||
@@ -522,12 +540,13 @@ where
|
||||
let validator_keypairs = self
|
||||
.validator_keypairs
|
||||
.expect("cannot build without validator keypairs");
|
||||
let kzg = spec.deneb_fork_epoch.map(|_| KZG.clone());
|
||||
|
||||
let kzg = get_kzg(&spec);
|
||||
|
||||
let validator_monitor_config = self.validator_monitor_config.unwrap_or_default();
|
||||
|
||||
let chain_config = self.chain_config.unwrap_or_default();
|
||||
let mut builder = BeaconChainBuilder::new(self.eth_spec_instance)
|
||||
let mut builder = BeaconChainBuilder::new(self.eth_spec_instance, kzg.clone())
|
||||
.logger(log.clone())
|
||||
.custom_spec(spec.clone())
|
||||
.store(self.store.expect("cannot build without store"))
|
||||
@@ -546,8 +565,7 @@ where
|
||||
log.clone(),
|
||||
5,
|
||||
)))
|
||||
.validator_monitor_config(validator_monitor_config)
|
||||
.kzg(kzg);
|
||||
.validator_monitor_config(validator_monitor_config);
|
||||
|
||||
builder = if let Some(mutator) = self.initial_mutator {
|
||||
mutator(builder)
|
||||
@@ -602,7 +620,7 @@ pub fn mock_execution_layer_from_parts<E: EthSpec>(
|
||||
HARNESS_GENESIS_TIME + spec.seconds_per_slot * E::slots_per_epoch() * epoch.as_u64()
|
||||
});
|
||||
|
||||
let kzg_opt = spec.deneb_fork_epoch.map(|_| KZG.clone());
|
||||
let kzg = get_kzg(spec);
|
||||
|
||||
MockExecutionLayer::new(
|
||||
task_executor,
|
||||
@@ -612,7 +630,7 @@ pub fn mock_execution_layer_from_parts<E: EthSpec>(
|
||||
prague_time,
|
||||
Some(JwtKey::from_slice(&DEFAULT_JWT_SECRET).unwrap()),
|
||||
spec.clone(),
|
||||
kzg_opt,
|
||||
Some(kzg),
|
||||
)
|
||||
}
|
||||
|
||||
@@ -2842,9 +2860,10 @@ pub fn generate_rand_block_and_data_columns<E: EthSpec>(
|
||||
SignedBeaconBlock<E, FullPayload<E>>,
|
||||
Vec<Arc<DataColumnSidecar<E>>>,
|
||||
) {
|
||||
let kzg = get_kzg(spec);
|
||||
let (block, blobs) = generate_rand_block_and_blobs(fork_name, num_blobs, rng);
|
||||
let blob: BlobsList<E> = blobs.into_iter().map(|b| b.blob).collect::<Vec<_>>().into();
|
||||
let data_columns = blobs_to_data_column_sidecars(&blob, &block, &KZG_PEERDAS, spec).unwrap();
|
||||
let data_columns = blobs_to_data_column_sidecars(&blob, &block, &kzg, spec).unwrap();
|
||||
|
||||
(block, data_columns)
|
||||
}
|
||||
|
||||
@@ -25,7 +25,7 @@ async fn blob_sidecar_event_on_process_gossip_blob() {
|
||||
let mut blob_event_receiver = event_handler.subscribe_blob_sidecar();
|
||||
|
||||
// build and process a gossip verified blob
|
||||
let kzg = harness.chain.kzg.as_ref().unwrap();
|
||||
let kzg = harness.chain.kzg.as_ref();
|
||||
let mut rng = StdRng::seed_from_u64(0xDEADBEEF0BAD5EEDu64);
|
||||
let sidecar = BlobSidecar::random_valid(&mut rng, kzg)
|
||||
.map(Arc::new)
|
||||
@@ -59,7 +59,7 @@ async fn blob_sidecar_event_on_process_rpc_blobs() {
|
||||
let mut blob_event_receiver = event_handler.subscribe_blob_sidecar();
|
||||
|
||||
// build and process multiple rpc blobs
|
||||
let kzg = harness.chain.kzg.as_ref().unwrap();
|
||||
let kzg = harness.chain.kzg.as_ref();
|
||||
let mut rng = StdRng::seed_from_u64(0xDEADBEEF0BAD5EEDu64);
|
||||
|
||||
let mut blob_1 = BlobSidecar::random_valid(&mut rng, kzg).unwrap();
|
||||
|
||||
@@ -7,8 +7,8 @@ use beacon_chain::data_availability_checker::AvailableBlock;
|
||||
use beacon_chain::schema_change::migrate_schema;
|
||||
use beacon_chain::test_utils::SyncCommitteeStrategy;
|
||||
use beacon_chain::test_utils::{
|
||||
mock_execution_layer_from_parts, test_spec, AttestationStrategy, BeaconChainHarness,
|
||||
BlockStrategy, DiskHarnessType, KZG,
|
||||
get_kzg, mock_execution_layer_from_parts, test_spec, AttestationStrategy, BeaconChainHarness,
|
||||
BlockStrategy, DiskHarnessType,
|
||||
};
|
||||
use beacon_chain::{
|
||||
data_availability_checker::MaybeAvailableBlock, historical_blocks::HistoricalBlockError,
|
||||
@@ -164,7 +164,7 @@ async fn light_client_bootstrap_test() {
|
||||
.unwrap()
|
||||
.unwrap();
|
||||
|
||||
let kzg = spec.deneb_fork_epoch.map(|_| KZG.clone());
|
||||
let kzg = get_kzg(&spec);
|
||||
|
||||
let mock =
|
||||
mock_execution_layer_from_parts(&harness.spec, harness.runtime.task_executor.clone());
|
||||
@@ -180,7 +180,7 @@ async fn light_client_bootstrap_test() {
|
||||
|
||||
let (shutdown_tx, _shutdown_rx) = futures::channel::mpsc::channel(1);
|
||||
|
||||
let beacon_chain = BeaconChainBuilder::<DiskHarnessType<E>>::new(MinimalEthSpec)
|
||||
let beacon_chain = BeaconChainBuilder::<DiskHarnessType<E>>::new(MinimalEthSpec, kzg)
|
||||
.store(store.clone())
|
||||
.custom_spec(test_spec::<E>())
|
||||
.task_executor(harness.chain.task_executor.clone())
|
||||
@@ -203,7 +203,6 @@ async fn light_client_bootstrap_test() {
|
||||
1,
|
||||
)))
|
||||
.execution_layer(Some(mock.el))
|
||||
.kzg(kzg)
|
||||
.build()
|
||||
.expect("should build");
|
||||
|
||||
@@ -299,7 +298,7 @@ async fn light_client_updates_test() {
|
||||
.unwrap()
|
||||
.unwrap();
|
||||
|
||||
let kzg = spec.deneb_fork_epoch.map(|_| KZG.clone());
|
||||
let kzg = get_kzg(&spec);
|
||||
|
||||
let mock =
|
||||
mock_execution_layer_from_parts(&harness.spec, harness.runtime.task_executor.clone());
|
||||
@@ -324,7 +323,7 @@ async fn light_client_updates_test() {
|
||||
|
||||
let (shutdown_tx, _shutdown_rx) = futures::channel::mpsc::channel(1);
|
||||
|
||||
let beacon_chain = BeaconChainBuilder::<DiskHarnessType<E>>::new(MinimalEthSpec)
|
||||
let beacon_chain = BeaconChainBuilder::<DiskHarnessType<E>>::new(MinimalEthSpec, kzg)
|
||||
.store(store.clone())
|
||||
.custom_spec(test_spec::<E>())
|
||||
.task_executor(harness.chain.task_executor.clone())
|
||||
@@ -347,7 +346,6 @@ async fn light_client_updates_test() {
|
||||
1,
|
||||
)))
|
||||
.execution_layer(Some(mock.el))
|
||||
.kzg(kzg)
|
||||
.build()
|
||||
.expect("should build");
|
||||
|
||||
@@ -2680,7 +2678,8 @@ async fn weak_subjectivity_sync_test(slots: Vec<Slot>, checkpoint_slot: Slot) {
|
||||
let store = get_store(&temp2);
|
||||
let spec = test_spec::<E>();
|
||||
let seconds_per_slot = spec.seconds_per_slot;
|
||||
let kzg = spec.deneb_fork_epoch.map(|_| KZG.clone());
|
||||
|
||||
let kzg = get_kzg(&spec);
|
||||
|
||||
let mock =
|
||||
mock_execution_layer_from_parts(&harness.spec, harness.runtime.task_executor.clone());
|
||||
@@ -2694,7 +2693,7 @@ async fn weak_subjectivity_sync_test(slots: Vec<Slot>, checkpoint_slot: Slot) {
|
||||
);
|
||||
slot_clock.set_slot(harness.get_current_slot().as_u64());
|
||||
|
||||
let beacon_chain = BeaconChainBuilder::<DiskHarnessType<E>>::new(MinimalEthSpec)
|
||||
let beacon_chain = BeaconChainBuilder::<DiskHarnessType<E>>::new(MinimalEthSpec, kzg)
|
||||
.store(store.clone())
|
||||
.custom_spec(test_spec::<E>())
|
||||
.task_executor(harness.chain.task_executor.clone())
|
||||
@@ -2717,7 +2716,6 @@ async fn weak_subjectivity_sync_test(slots: Vec<Slot>, checkpoint_slot: Slot) {
|
||||
1,
|
||||
)))
|
||||
.execution_layer(Some(mock.el))
|
||||
.kzg(kzg)
|
||||
.build()
|
||||
.expect("should build");
|
||||
|
||||
|
||||
@@ -20,6 +20,7 @@ types = { workspace = true }
|
||||
eth2_config = { workspace = true }
|
||||
slot_clock = { workspace = true }
|
||||
serde = { workspace = true }
|
||||
serde_json = { workspace = true }
|
||||
error-chain = { workspace = true }
|
||||
slog = { workspace = true }
|
||||
tokio = { workspace = true }
|
||||
@@ -27,6 +28,7 @@ futures = { workspace = true }
|
||||
dirs = { workspace = true }
|
||||
eth1 = { workspace = true }
|
||||
eth2 = { workspace = true }
|
||||
kzg = { workspace = true }
|
||||
sensitive_url = { workspace = true }
|
||||
genesis = { workspace = true }
|
||||
task_executor = { workspace = true }
|
||||
|
||||
@@ -195,7 +195,17 @@ where
|
||||
None
|
||||
};
|
||||
|
||||
let builder = BeaconChainBuilder::new(eth_spec_instance)
|
||||
let kzg_err_msg = |e| format!("Failed to load trusted setup: {:?}", e);
|
||||
let trusted_setup = config.trusted_setup.clone();
|
||||
let kzg = if spec.is_peer_das_scheduled() {
|
||||
Kzg::new_from_trusted_setup_das_enabled(trusted_setup).map_err(kzg_err_msg)?
|
||||
} else if spec.deneb_fork_epoch.is_some() {
|
||||
Kzg::new_from_trusted_setup(trusted_setup).map_err(kzg_err_msg)?
|
||||
} else {
|
||||
Kzg::new_from_trusted_setup_no_precomp(trusted_setup).map_err(kzg_err_msg)?
|
||||
};
|
||||
|
||||
let builder = BeaconChainBuilder::new(eth_spec_instance, Arc::new(kzg))
|
||||
.logger(context.log().clone())
|
||||
.store(store)
|
||||
.task_executor(context.executor.clone())
|
||||
@@ -623,20 +633,6 @@ where
|
||||
ClientGenesis::FromStore => builder.resume_from_db().map(|v| (v, None))?,
|
||||
};
|
||||
|
||||
let beacon_chain_builder = if let Some(trusted_setup) = config.trusted_setup {
|
||||
let kzg_err_msg = |e| format!("Failed to load trusted setup: {:?}", e);
|
||||
|
||||
let kzg = if spec.is_peer_das_scheduled() {
|
||||
Kzg::new_from_trusted_setup_das_enabled(trusted_setup).map_err(kzg_err_msg)?
|
||||
} else {
|
||||
Kzg::new_from_trusted_setup(trusted_setup).map_err(kzg_err_msg)?
|
||||
};
|
||||
|
||||
beacon_chain_builder.kzg(Some(Arc::new(kzg)))
|
||||
} else {
|
||||
beacon_chain_builder
|
||||
};
|
||||
|
||||
if config.sync_eth1_chain {
|
||||
self.eth1_service = eth1_service_option;
|
||||
}
|
||||
|
||||
@@ -4,6 +4,7 @@ use beacon_chain::TrustedSetup;
|
||||
use beacon_processor::BeaconProcessorConfig;
|
||||
use directory::DEFAULT_ROOT_DIR;
|
||||
use environment::LoggerConfig;
|
||||
use kzg::trusted_setup::get_trusted_setup;
|
||||
use network::NetworkConfig;
|
||||
use sensitive_url::SensitiveUrl;
|
||||
use serde::{Deserialize, Serialize};
|
||||
@@ -75,7 +76,7 @@ pub struct Config {
|
||||
pub chain: beacon_chain::ChainConfig,
|
||||
pub eth1: eth1::Config,
|
||||
pub execution_layer: Option<execution_layer::Config>,
|
||||
pub trusted_setup: Option<TrustedSetup>,
|
||||
pub trusted_setup: TrustedSetup,
|
||||
pub http_api: http_api::Config,
|
||||
pub http_metrics: http_metrics::Config,
|
||||
pub monitoring_api: Option<monitoring_api::Config>,
|
||||
@@ -89,6 +90,9 @@ pub struct Config {
|
||||
|
||||
impl Default for Config {
|
||||
fn default() -> Self {
|
||||
let trusted_setup: TrustedSetup = serde_json::from_reader(get_trusted_setup().as_slice())
|
||||
.expect("Unable to read trusted setup file");
|
||||
|
||||
Self {
|
||||
data_dir: PathBuf::from(DEFAULT_ROOT_DIR),
|
||||
db_name: "chain_db".to_string(),
|
||||
@@ -103,7 +107,7 @@ impl Default for Config {
|
||||
sync_eth1_chain: false,
|
||||
eth1: <_>::default(),
|
||||
execution_layer: None,
|
||||
trusted_setup: None,
|
||||
trusted_setup,
|
||||
beacon_graffiti: GraffitiOrigin::default(),
|
||||
http_api: <_>::default(),
|
||||
http_metrics: <_>::default(),
|
||||
|
||||
@@ -862,8 +862,7 @@ pub fn generate_pow_block(
|
||||
#[cfg(test)]
|
||||
mod test {
|
||||
use super::*;
|
||||
use eth2_network_config::TRUSTED_SETUP_BYTES;
|
||||
use kzg::TrustedSetup;
|
||||
use kzg::{trusted_setup::get_trusted_setup, TrustedSetup};
|
||||
use types::{MainnetEthSpec, MinimalEthSpec};
|
||||
|
||||
#[test]
|
||||
@@ -951,7 +950,8 @@ mod test {
|
||||
}
|
||||
|
||||
fn load_kzg() -> Result<Kzg, String> {
|
||||
let trusted_setup: TrustedSetup = serde_json::from_reader(TRUSTED_SETUP_BYTES)
|
||||
let trusted_setup: TrustedSetup =
|
||||
serde_json::from_reader(get_trusted_setup().as_slice())
|
||||
.map_err(|e| format!("Unable to read trusted setup file: {e:?}"))?;
|
||||
Kzg::new_from_trusted_setup(trusted_setup)
|
||||
.map_err(|e| format!("Failed to load trusted setup: {e:?}"))
|
||||
|
||||
@@ -8,10 +8,13 @@ edition = { workspace = true }
|
||||
sloggers = { workspace = true }
|
||||
genesis = { workspace = true }
|
||||
matches = "0.1.8"
|
||||
serde_json = { workspace = true }
|
||||
slog-term = { workspace = true }
|
||||
slog-async = { workspace = true }
|
||||
eth2 = { workspace = true }
|
||||
gossipsub = { workspace = true }
|
||||
eth2_network_config = { workspace = true }
|
||||
kzg = { workspace = true }
|
||||
|
||||
[dependencies]
|
||||
alloy-primitives = { workspace = true }
|
||||
|
||||
@@ -696,8 +696,7 @@ impl<T: BeaconChainTypes> NetworkBeaconProcessor<T> {
|
||||
column_sidecar,
|
||||
));
|
||||
}
|
||||
GossipDataColumnError::KzgNotInitialized
|
||||
| GossipDataColumnError::PubkeyCacheTimeout
|
||||
GossipDataColumnError::PubkeyCacheTimeout
|
||||
| GossipDataColumnError::BeaconChainError(_) => {
|
||||
crit!(
|
||||
self.log,
|
||||
@@ -839,9 +838,7 @@ impl<T: BeaconChainTypes> NetworkBeaconProcessor<T> {
|
||||
blob_sidecar,
|
||||
));
|
||||
}
|
||||
GossipBlobError::KzgNotInitialized
|
||||
| GossipBlobError::PubkeyCacheTimeout
|
||||
| GossipBlobError::BeaconChainError(_) => {
|
||||
GossipBlobError::PubkeyCacheTimeout | GossipBlobError::BeaconChainError(_) => {
|
||||
crit!(
|
||||
self.log,
|
||||
"Internal error when verifying blob sidecar";
|
||||
|
||||
@@ -385,8 +385,8 @@ impl<T: BeaconChainTypes> NetworkBeaconProcessor<T> {
|
||||
data_columns: Vec<Arc<DataColumnSidecar<T::EthSpec>>>,
|
||||
_seen_timestamp: Duration,
|
||||
) -> Result<(), String> {
|
||||
let kzg = self.chain.kzg.as_ref().ok_or("Kzg not initialized")?;
|
||||
verify_kzg_for_data_column_list(data_columns.iter(), kzg).map_err(|err| format!("{err:?}"))
|
||||
verify_kzg_for_data_column_list(data_columns.iter(), &self.chain.kzg)
|
||||
.map_err(|err| format!("{err:?}"))
|
||||
}
|
||||
|
||||
/// Process a sampling completed event, inserting it into fork-choice
|
||||
@@ -561,8 +561,7 @@ impl<T: BeaconChainTypes> NetworkBeaconProcessor<T> {
|
||||
})
|
||||
.collect::<Vec<_>>(),
|
||||
Err(e) => match e {
|
||||
AvailabilityCheckError::StoreError(_)
|
||||
| AvailabilityCheckError::KzgNotInitialized => {
|
||||
AvailabilityCheckError::StoreError(_) => {
|
||||
return (
|
||||
0,
|
||||
Err(ChainSegmentFailed {
|
||||
|
||||
@@ -2,6 +2,7 @@ use super::*;
|
||||
use beacon_chain::{
|
||||
builder::{BeaconChainBuilder, Witness},
|
||||
eth1_chain::CachingEth1Backend,
|
||||
test_utils::get_kzg,
|
||||
BeaconChain,
|
||||
};
|
||||
use futures::prelude::*;
|
||||
@@ -45,12 +46,14 @@ impl TestBeaconChain {
|
||||
let store =
|
||||
HotColdDB::open_ephemeral(StoreConfig::default(), spec.clone(), log.clone()).unwrap();
|
||||
|
||||
let kzg = get_kzg(&spec);
|
||||
|
||||
let (shutdown_tx, _) = futures::channel::mpsc::channel(1);
|
||||
|
||||
let test_runtime = TestRuntime::default();
|
||||
|
||||
let chain = Arc::new(
|
||||
BeaconChainBuilder::new(MainnetEthSpec)
|
||||
BeaconChainBuilder::new(MainnetEthSpec, kzg.clone())
|
||||
.logger(log.clone())
|
||||
.custom_spec(spec.clone())
|
||||
.store(Arc::new(store))
|
||||
|
||||
@@ -396,13 +396,15 @@ pub fn get_config<E: EthSpec>(
|
||||
}
|
||||
|
||||
// 4844 params
|
||||
client_config.trusted_setup = context
|
||||
if let Some(trusted_setup) = context
|
||||
.eth2_network_config
|
||||
.as_ref()
|
||||
.and_then(|config| config.kzg_trusted_setup.as_ref())
|
||||
.map(|trusted_setup_bytes| serde_json::from_slice(trusted_setup_bytes))
|
||||
.map(|config| serde_json::from_slice(&config.kzg_trusted_setup))
|
||||
.transpose()
|
||||
.map_err(|e| format!("Unable to read trusted setup file: {}", e))?;
|
||||
.map_err(|e| format!("Unable to read trusted setup file: {}", e))?
|
||||
{
|
||||
client_config.trusted_setup = trusted_setup;
|
||||
};
|
||||
|
||||
// Override default trusted setup file if required
|
||||
if let Some(trusted_setup_file_path) = cli_args.get_one::<String>("trusted-setup-file-override")
|
||||
@@ -411,7 +413,7 @@ pub fn get_config<E: EthSpec>(
|
||||
.map_err(|e| format!("Failed to open trusted setup file: {}", e))?;
|
||||
let trusted_setup: TrustedSetup = serde_json::from_reader(file)
|
||||
.map_err(|e| format!("Unable to read trusted setup file: {}", e))?;
|
||||
client_config.trusted_setup = Some(trusted_setup);
|
||||
client_config.trusted_setup = trusted_setup;
|
||||
}
|
||||
|
||||
if let Some(freezer_dir) = cli_args.get_one::<String>("freezer-dir") {
|
||||
|
||||
@@ -28,3 +28,4 @@ sensitive_url = { workspace = true }
|
||||
slog = { workspace = true }
|
||||
logging = { workspace = true }
|
||||
bytes = { workspace = true }
|
||||
kzg = { workspace = true }
|
||||
|
||||
@@ -14,6 +14,7 @@
|
||||
use bytes::Bytes;
|
||||
use discv5::enr::{CombinedKey, Enr};
|
||||
use eth2_config::{instantiate_hardcoded_nets, HardcodedNet};
|
||||
use kzg::trusted_setup::get_trusted_setup;
|
||||
use pretty_reqwest_error::PrettyReqwestError;
|
||||
use reqwest::{Client, Error};
|
||||
use sensitive_url::SensitiveUrl;
|
||||
@@ -24,7 +25,7 @@ use std::io::{Read, Write};
|
||||
use std::path::PathBuf;
|
||||
use std::str::FromStr;
|
||||
use std::time::Duration;
|
||||
use types::{BeaconState, ChainSpec, Config, Epoch, EthSpec, EthSpecId, Hash256};
|
||||
use types::{BeaconState, ChainSpec, Config, EthSpec, EthSpecId, Hash256};
|
||||
use url::Url;
|
||||
|
||||
pub use eth2_config::GenesisStateSource;
|
||||
@@ -43,26 +44,6 @@ instantiate_hardcoded_nets!(eth2_config);
|
||||
|
||||
pub const DEFAULT_HARDCODED_NETWORK: &str = "mainnet";
|
||||
|
||||
/// Contains the bytes from the trusted setup json.
|
||||
/// The mainnet trusted setup is also reused in testnets.
|
||||
///
|
||||
/// This is done to ensure that testnets also inherit the high security and
|
||||
/// randomness of the mainnet kzg trusted setup ceremony.
|
||||
///
|
||||
/// Note: The trusted setup for both mainnet and minimal presets are the same.
|
||||
pub const TRUSTED_SETUP_BYTES: &[u8] =
|
||||
include_bytes!("../built_in_network_configs/trusted_setup.json");
|
||||
|
||||
/// Returns `Some(TrustedSetup)` if the deneb fork epoch is set and `None` otherwise.
|
||||
///
|
||||
/// Returns an error if the trusted setup parsing failed.
|
||||
fn get_trusted_setup_from_config(config: &Config) -> Option<Vec<u8>> {
|
||||
config
|
||||
.deneb_fork_epoch
|
||||
.filter(|epoch| epoch.value != Epoch::max_value())
|
||||
.map(|_| TRUSTED_SETUP_BYTES.to_vec())
|
||||
}
|
||||
|
||||
/// A simple slice-or-vec enum to avoid cloning the beacon state bytes in the
|
||||
/// binary whilst also supporting loading them from a file at runtime.
|
||||
#[derive(Clone, PartialEq, Debug)]
|
||||
@@ -104,7 +85,7 @@ pub struct Eth2NetworkConfig {
|
||||
pub genesis_state_source: GenesisStateSource,
|
||||
pub genesis_state_bytes: Option<GenesisStateBytes>,
|
||||
pub config: Config,
|
||||
pub kzg_trusted_setup: Option<Vec<u8>>,
|
||||
pub kzg_trusted_setup: Vec<u8>,
|
||||
}
|
||||
|
||||
impl Eth2NetworkConfig {
|
||||
@@ -122,7 +103,7 @@ impl Eth2NetworkConfig {
|
||||
fn from_hardcoded_net(net: &HardcodedNet) -> Result<Self, String> {
|
||||
let config: Config = serde_yaml::from_reader(net.config)
|
||||
.map_err(|e| format!("Unable to parse yaml config: {:?}", e))?;
|
||||
let kzg_trusted_setup = get_trusted_setup_from_config(&config);
|
||||
let kzg_trusted_setup = get_trusted_setup();
|
||||
Ok(Self {
|
||||
deposit_contract_deploy_block: serde_yaml::from_reader(net.deploy_block)
|
||||
.map_err(|e| format!("Unable to parse deploy block: {:?}", e))?,
|
||||
@@ -359,7 +340,7 @@ impl Eth2NetworkConfig {
|
||||
(None, GenesisStateSource::Unknown)
|
||||
};
|
||||
|
||||
let kzg_trusted_setup = get_trusted_setup_from_config(&config);
|
||||
let kzg_trusted_setup = get_trusted_setup();
|
||||
|
||||
Ok(Self {
|
||||
deposit_contract_deploy_block,
|
||||
@@ -577,7 +558,7 @@ mod tests {
|
||||
GenesisStateSource::Unknown
|
||||
};
|
||||
// With Deneb enabled by default we must set a trusted setup here.
|
||||
let kzg_trusted_setup = get_trusted_setup_from_config(&config).unwrap();
|
||||
let kzg_trusted_setup = get_trusted_setup();
|
||||
|
||||
let testnet = Eth2NetworkConfig {
|
||||
deposit_contract_deploy_block,
|
||||
@@ -588,7 +569,7 @@ mod tests {
|
||||
.map(Encode::as_ssz_bytes)
|
||||
.map(Into::into),
|
||||
config,
|
||||
kzg_trusted_setup: Some(kzg_trusted_setup),
|
||||
kzg_trusted_setup,
|
||||
};
|
||||
|
||||
testnet
|
||||
|
||||
@@ -18,11 +18,11 @@ hex = { workspace = true }
|
||||
ethereum_hashing = { workspace = true }
|
||||
c-kzg = { workspace = true }
|
||||
rust_eth_kzg = { workspace = true }
|
||||
serde_json = { workspace = true }
|
||||
|
||||
[dev-dependencies]
|
||||
criterion = { workspace = true }
|
||||
serde_json = { workspace = true }
|
||||
eth2_network_config = { workspace = true }
|
||||
|
||||
[[bench]]
|
||||
name = "benchmark"
|
||||
|
||||
@@ -1,11 +1,10 @@
|
||||
use c_kzg::KzgSettings;
|
||||
use criterion::{criterion_group, criterion_main, Criterion};
|
||||
use eth2_network_config::TRUSTED_SETUP_BYTES;
|
||||
use kzg::TrustedSetup;
|
||||
use kzg::{trusted_setup::get_trusted_setup, TrustedSetup};
|
||||
use rust_eth_kzg::{DASContext, TrustedSetup as PeerDASTrustedSetup};
|
||||
|
||||
pub fn bench_init_context(c: &mut Criterion) {
|
||||
let trusted_setup: TrustedSetup = serde_json::from_reader(TRUSTED_SETUP_BYTES)
|
||||
let trusted_setup: TrustedSetup = serde_json::from_reader(get_trusted_setup().as_slice())
|
||||
.map_err(|e| format!("Unable to read trusted setup file: {}", e))
|
||||
.expect("should have trusted setup");
|
||||
|
||||
@@ -22,7 +21,8 @@ pub fn bench_init_context(c: &mut Criterion) {
|
||||
});
|
||||
c.bench_function(&format!("Initialize context c-kzg (4844)"), |b| {
|
||||
b.iter(|| {
|
||||
let trusted_setup: TrustedSetup = serde_json::from_reader(TRUSTED_SETUP_BYTES)
|
||||
let trusted_setup: TrustedSetup =
|
||||
serde_json::from_reader(get_trusted_setup().as_slice())
|
||||
.map_err(|e| format!("Unable to read trusted setup file: {}", e))
|
||||
.expect("should have trusted setup");
|
||||
KzgSettings::load_trusted_setup(&trusted_setup.g1_points(), &trusted_setup.g2_points())
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
mod kzg_commitment;
|
||||
mod kzg_proof;
|
||||
mod trusted_setup;
|
||||
pub mod trusted_setup;
|
||||
|
||||
use rust_eth_kzg::{CellIndex, DASContext};
|
||||
use std::fmt::Debug;
|
||||
@@ -51,18 +51,41 @@ impl From<c_kzg::Error> for Error {
|
||||
#[derive(Debug)]
|
||||
pub struct Kzg {
|
||||
trusted_setup: KzgSettings,
|
||||
context: Option<DASContext>,
|
||||
context: DASContext,
|
||||
}
|
||||
|
||||
impl Kzg {
|
||||
/// Load the kzg trusted setup parameters from a vec of G1 and G2 points.
|
||||
pub fn new_from_trusted_setup(trusted_setup: TrustedSetup) -> Result<Self, Error> {
|
||||
pub fn new_from_trusted_setup_no_precomp(trusted_setup: TrustedSetup) -> Result<Self, Error> {
|
||||
let peerdas_trusted_setup = PeerDASTrustedSetup::from(&trusted_setup);
|
||||
|
||||
let context = DASContext::new(&peerdas_trusted_setup, rust_eth_kzg::UsePrecomp::No);
|
||||
|
||||
Ok(Self {
|
||||
trusted_setup: KzgSettings::load_trusted_setup(
|
||||
&trusted_setup.g1_points(),
|
||||
&trusted_setup.g2_points(),
|
||||
)?,
|
||||
context: None,
|
||||
context,
|
||||
})
|
||||
}
|
||||
|
||||
/// Load the kzg trusted setup parameters from a vec of G1 and G2 points.
|
||||
pub fn new_from_trusted_setup(trusted_setup: TrustedSetup) -> Result<Self, Error> {
|
||||
let peerdas_trusted_setup = PeerDASTrustedSetup::from(&trusted_setup);
|
||||
|
||||
let context = DASContext::new(
|
||||
&peerdas_trusted_setup,
|
||||
rust_eth_kzg::UsePrecomp::Yes {
|
||||
width: rust_eth_kzg::constants::RECOMMENDED_PRECOMP_WIDTH,
|
||||
},
|
||||
);
|
||||
|
||||
Ok(Self {
|
||||
trusted_setup: KzgSettings::load_trusted_setup(
|
||||
&trusted_setup.g1_points(),
|
||||
&trusted_setup.g2_points(),
|
||||
)?,
|
||||
context,
|
||||
})
|
||||
}
|
||||
|
||||
@@ -88,12 +111,12 @@ impl Kzg {
|
||||
&trusted_setup.g1_points(),
|
||||
&trusted_setup.g2_points(),
|
||||
)?,
|
||||
context: Some(context),
|
||||
context,
|
||||
})
|
||||
}
|
||||
|
||||
fn context(&self) -> Result<&DASContext, Error> {
|
||||
self.context.as_ref().ok_or(Error::DASContextUninitialized)
|
||||
fn context(&self) -> &DASContext {
|
||||
&self.context
|
||||
}
|
||||
|
||||
/// Compute the kzg proof given a blob and its kzg commitment.
|
||||
@@ -200,7 +223,7 @@ impl Kzg {
|
||||
blob: KzgBlobRef<'_>,
|
||||
) -> Result<CellsAndKzgProofs, Error> {
|
||||
let (cells, proofs) = self
|
||||
.context()?
|
||||
.context()
|
||||
.compute_cells_and_kzg_proofs(blob)
|
||||
.map_err(Error::PeerDASKZG)?;
|
||||
|
||||
@@ -226,7 +249,7 @@ impl Kzg {
|
||||
.iter()
|
||||
.map(|commitment| commitment.as_ref())
|
||||
.collect();
|
||||
let verification_result = self.context()?.verify_cell_kzg_proof_batch(
|
||||
let verification_result = self.context().verify_cell_kzg_proof_batch(
|
||||
commitments.to_vec(),
|
||||
columns,
|
||||
cells.to_vec(),
|
||||
@@ -247,7 +270,7 @@ impl Kzg {
|
||||
cells: &[CellRef<'_>],
|
||||
) -> Result<CellsAndKzgProofs, Error> {
|
||||
let (cells, proofs) = self
|
||||
.context()?
|
||||
.context()
|
||||
.recover_cells_and_kzg_proofs(cell_ids.to_vec(), cells.to_vec())
|
||||
.map_err(Error::PeerDASKZG)?;
|
||||
|
||||
|
||||
@@ -5,6 +5,12 @@ use serde::{
|
||||
Deserialize, Serialize,
|
||||
};
|
||||
|
||||
pub const TRUSTED_SETUP_BYTES: &[u8] = include_bytes!("../trusted_setup.json");
|
||||
|
||||
pub fn get_trusted_setup() -> Vec<u8> {
|
||||
TRUSTED_SETUP_BYTES.into()
|
||||
}
|
||||
|
||||
/// Wrapper over a BLS G1 point's byte representation.
|
||||
#[derive(Debug, Clone, PartialEq)]
|
||||
struct G1Point([u8; BYTES_PER_G1_POINT]);
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
use super::*;
|
||||
use crate::case_result::compare_result;
|
||||
use beacon_chain::kzg_utils::validate_blob;
|
||||
use eth2_network_config::TRUSTED_SETUP_BYTES;
|
||||
use kzg::trusted_setup::get_trusted_setup;
|
||||
use kzg::{Cell, Error as KzgError, Kzg, KzgCommitment, KzgProof, TrustedSetup};
|
||||
use serde::Deserialize;
|
||||
use std::marker::PhantomData;
|
||||
@@ -10,7 +10,7 @@ use std::sync::LazyLock;
|
||||
use types::Blob;
|
||||
|
||||
static KZG: LazyLock<Arc<Kzg>> = LazyLock::new(|| {
|
||||
let trusted_setup: TrustedSetup = serde_json::from_reader(TRUSTED_SETUP_BYTES)
|
||||
let trusted_setup: TrustedSetup = serde_json::from_reader(get_trusted_setup().as_slice())
|
||||
.map_err(|e| Error::InternalError(format!("Failed to initialize trusted setup: {:?}", e)))
|
||||
.expect("failed to initialize trusted setup");
|
||||
let kzg = Kzg::new_from_trusted_setup_das_enabled(trusted_setup)
|
||||
|
||||
@@ -19,3 +19,4 @@ rayon = { workspace = true }
|
||||
sensitive_url = { path = "../../common/sensitive_url" }
|
||||
eth2_network_config = { workspace = true }
|
||||
serde_json = { workspace = true }
|
||||
kzg = { workspace = true }
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
use crate::checks::epoch_delay;
|
||||
use eth2_network_config::TRUSTED_SETUP_BYTES;
|
||||
use kzg::trusted_setup::get_trusted_setup;
|
||||
use node_test_rig::{
|
||||
environment::RuntimeContext,
|
||||
eth2::{types::StateId, BeaconNodeHttpClient},
|
||||
@@ -46,8 +46,8 @@ fn default_client_config(network_params: LocalNetworkParams, genesis_time: u64)
|
||||
beacon_config.chain.enable_light_client_server = true;
|
||||
beacon_config.http_api.enable_light_client_server = true;
|
||||
beacon_config.chain.optimistic_finalized_sync = false;
|
||||
beacon_config.trusted_setup =
|
||||
serde_json::from_reader(TRUSTED_SETUP_BYTES).expect("Trusted setup bytes should be valid");
|
||||
beacon_config.trusted_setup = serde_json::from_reader(get_trusted_setup().as_slice())
|
||||
.expect("Trusted setup bytes should be valid");
|
||||
|
||||
let el_config = execution_layer::Config {
|
||||
execution_endpoint: Some(
|
||||
|
||||
Reference in New Issue
Block a user