From dbaa9ffb468e06c8b3a0ce7578147523a5c03f91 Mon Sep 17 00:00:00 2001 From: Alon-Lukatch-Starkware Date: Sun, 11 Aug 2024 10:05:01 +0300 Subject: [PATCH] fix(network): add chain id to Kademlia discovery protocol --- Cargo.lock | 1 + config/papyrus/default_config.json | 5 +++++ crates/papyrus_network/Cargo.toml | 1 + crates/papyrus_network/src/bin_utils/mod.rs | 2 +- crates/papyrus_network/src/discovery/flow_test.rs | 9 +++++++-- crates/papyrus_network/src/e2e_broadcast_test.rs | 8 +++++++- crates/papyrus_network/src/lib.rs | 9 +++++++++ crates/papyrus_network/src/mixed_behaviour.rs | 15 +++++++++++++-- crates/papyrus_network/src/network_manager/mod.rs | 2 ++ crates/papyrus_node/src/config/pointers.rs | 2 +- ..._config__config_test__dump_default_config.snap | 5 +++++ 11 files changed, 52 insertions(+), 7 deletions(-) diff --git a/Cargo.lock b/Cargo.lock index acb844e32a..7bdb1093b7 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -6409,6 +6409,7 @@ dependencies = [ "pretty_assertions", "replace_with", "serde", + "starknet_api", "thiserror", "tokio", "tokio-retry", diff --git a/config/papyrus/default_config.json b/config/papyrus/default_config.json index 896aea4db4..67d6a0427d 100644 --- a/config/papyrus/default_config.json +++ b/config/papyrus/default_config.json @@ -169,6 +169,11 @@ "privacy": "TemporaryValue", "value": true }, + "network.chain_id": { + "description": "The chain to follow. For more details see https://docs.starknet.io/documentation/architecture_and_concepts/Blocks/transactions/#chain-id.", + "pointer_target": "chain_id", + "privacy": "Public" + }, "network.idle_connection_timeout": { "description": "Amount of time in seconds that a connection with no active sessions will stay alive.", "privacy": "Public", diff --git a/crates/papyrus_network/Cargo.toml b/crates/papyrus_network/Cargo.toml index 2f034110d7..b1d2029345 100644 --- a/crates/papyrus_network/Cargo.toml +++ b/crates/papyrus_network/Cargo.toml @@ -31,6 +31,7 @@ papyrus_common.workspace = true papyrus_config.workspace = true replace_with.workspace = true serde = { workspace = true, features = ["derive"] } +starknet_api = { path = "../starknet_api", version = "0.13.0-rc.0" } thiserror.workspace = true tokio = { workspace = true, features = ["full", "sync"] } tokio-retry.workspace = true diff --git a/crates/papyrus_network/src/bin_utils/mod.rs b/crates/papyrus_network/src/bin_utils/mod.rs index 89bff5b0a9..dfe9ea105f 100644 --- a/crates/papyrus_network/src/bin_utils/mod.rs +++ b/crates/papyrus_network/src/bin_utils/mod.rs @@ -10,7 +10,7 @@ pub fn build_swarm( listen_addresses: Vec, idle_connection_timeout: Duration, secret_key: Option>, - behaviour: impl Fn(Keypair) -> Behaviour, + behaviour: impl FnOnce(Keypair) -> Behaviour, ) -> Swarm where { diff --git a/crates/papyrus_network/src/discovery/flow_test.rs b/crates/papyrus_network/src/discovery/flow_test.rs index 43f01ca7c1..f799c240dc 100644 --- a/crates/papyrus_network/src/discovery/flow_test.rs +++ b/crates/papyrus_network/src/discovery/flow_test.rs @@ -9,6 +9,7 @@ use libp2p::swarm::behaviour::toggle::Toggle; use libp2p::swarm::{NetworkBehaviour, SwarmEvent}; use libp2p::{identify, kad, Multiaddr, Swarm}; use libp2p_swarm_test::SwarmExt; +use starknet_api::core::ChainId; use super::Behaviour; use crate::mixed_behaviour; @@ -24,8 +25,12 @@ struct DiscoveryMixedBehaviour { impl DiscoveryMixedBehaviour { pub fn new(key: Keypair, bootstrap_peer_multiaddr: Option) -> Self { - let mixed_behaviour = - MixedBehaviour::new(key, bootstrap_peer_multiaddr, Default::default()); + let mixed_behaviour = MixedBehaviour::new( + key, + bootstrap_peer_multiaddr, + Default::default(), + ChainId::Mainnet, + ); Self { identify: mixed_behaviour.identify, kademlia: mixed_behaviour.kademlia, diff --git a/crates/papyrus_network/src/e2e_broadcast_test.rs b/crates/papyrus_network/src/e2e_broadcast_test.rs index e3ac20fec5..5895427e65 100644 --- a/crates/papyrus_network/src/e2e_broadcast_test.rs +++ b/crates/papyrus_network/src/e2e_broadcast_test.rs @@ -5,6 +5,7 @@ use libp2p::core::multiaddr::Protocol; use libp2p::swarm::SwarmEvent; use libp2p::{Multiaddr, Swarm}; use libp2p_swarm_test::SwarmExt; +use starknet_api::core::ChainId; use crate::gossipsub_impl::Topic; use crate::mixed_behaviour::MixedBehaviour; @@ -16,7 +17,12 @@ const TIMEOUT: Duration = Duration::from_secs(1); async fn create_swarm(bootstrap_peer_multiaddr: Option) -> Swarm { let mut swarm = Swarm::new_ephemeral(|keypair| { - MixedBehaviour::new(keypair.clone(), bootstrap_peer_multiaddr, sqmr::Config::default()) + MixedBehaviour::new( + keypair.clone(), + bootstrap_peer_multiaddr, + sqmr::Config::default(), + ChainId::Mainnet, + ) }); // Not using SwarmExt::listen because it panics if the swarm emits other events let expected_listener_id = swarm.listen_on(Protocol::Memory(0).into()).unwrap(); diff --git a/crates/papyrus_network/src/lib.rs b/crates/papyrus_network/src/lib.rs index a24ecd35eb..696118710e 100644 --- a/crates/papyrus_network/src/lib.rs +++ b/crates/papyrus_network/src/lib.rs @@ -28,6 +28,7 @@ use papyrus_config::dumping::{ser_optional_param, ser_param, SerializeConfig}; use papyrus_config::validators::validate_vec_u256; use papyrus_config::{ParamPath, ParamPrivacyInput, SerializedParam}; use serde::{Deserialize, Serialize}; +use starknet_api::core::ChainId; use validator::Validate; // TODO: add peer manager config to the network config @@ -43,6 +44,7 @@ pub struct NetworkConfig { #[validate(custom = "validate_vec_u256")] #[serde(deserialize_with = "deserialize_optional_vec_u8")] pub(crate) secret_key: Option>, + pub chain_id: ChainId, } impl SerializeConfig for NetworkConfig { @@ -73,6 +75,12 @@ impl SerializeConfig for NetworkConfig { alive.", ParamPrivacyInput::Public, ), + ser_param( + "chain_id", + &self.chain_id, + "The chain to follow. For more details see https://docs.starknet.io/documentation/architecture_and_concepts/Blocks/transactions/#chain-id.", + ParamPrivacyInput::Public, + ), ]); config.extend(ser_optional_param( &self.bootstrap_peer_multiaddr, @@ -101,6 +109,7 @@ impl Default for NetworkConfig { idle_connection_timeout: Duration::from_secs(120), bootstrap_peer_multiaddr: None, secret_key: None, + chain_id: ChainId::Mainnet, } } } diff --git a/crates/papyrus_network/src/mixed_behaviour.rs b/crates/papyrus_network/src/mixed_behaviour.rs index c99db5dfc9..1509e0c0aa 100644 --- a/crates/papyrus_network/src/mixed_behaviour.rs +++ b/crates/papyrus_network/src/mixed_behaviour.rs @@ -5,7 +5,8 @@ use libp2p::kad::store::MemoryStore; use libp2p::swarm::behaviour::toggle::Toggle; use libp2p::swarm::dial_opts::DialOpts; use libp2p::swarm::NetworkBehaviour; -use libp2p::{gossipsub, identify, kad, Multiaddr, PeerId}; +use libp2p::{gossipsub, identify, kad, Multiaddr, PeerId, StreamProtocol}; +use starknet_api::core::ChainId; use crate::discovery::identify_impl::{IdentifyToOtherBehaviourEvent, IDENTIFY_PROTOCOL_VERSION}; use crate::discovery::kad_impl::KadToOtherBehaviourEvent; @@ -61,9 +62,15 @@ impl MixedBehaviour { keypair: Keypair, bootstrap_peer_multiaddr: Option, streamed_bytes_config: sqmr::Config, + chain_id: ChainId, ) -> Self { let public_key = keypair.public(); let local_peer_id = PeerId::from_public_key(&public_key); + let mut kademlia_config = kad::Config::default(); + kademlia_config.set_protocol_names(vec![ + StreamProtocol::try_from_owned(format!("/starknet/kad/{}/1.0.0", chain_id)) + .expect("Failed to create StreamProtocol from a string that starts with /"), + ]); Self { peer_manager: peer_manager::PeerManager::new(PeerManagerConfig::default()), discovery: bootstrap_peer_multiaddr @@ -82,7 +89,11 @@ impl MixedBehaviour { public_key, )), // TODO: change kademlia protocol name - kademlia: kad::Behaviour::new(local_peer_id, MemoryStore::new(local_peer_id)), + kademlia: kad::Behaviour::with_config( + local_peer_id, + MemoryStore::new(local_peer_id), + kademlia_config, + ), sqmr: sqmr::Behaviour::new(streamed_bytes_config), gossipsub: gossipsub::Behaviour::new( gossipsub::MessageAuthenticity::Signed(keypair), diff --git a/crates/papyrus_network/src/network_manager/mod.rs b/crates/papyrus_network/src/network_manager/mod.rs index c4b850655b..94b3fd5e11 100644 --- a/crates/papyrus_network/src/network_manager/mod.rs +++ b/crates/papyrus_network/src/network_manager/mod.rs @@ -549,6 +549,7 @@ impl NetworkManager { idle_connection_timeout, bootstrap_peer_multiaddr, secret_key, + chain_id, } = config; let listen_addresses = vec![ @@ -561,6 +562,7 @@ impl NetworkManager { key, bootstrap_peer_multiaddr.clone(), sqmr::Config { session_timeout }, + chain_id, ) }); Self::generic_new(swarm) diff --git a/crates/papyrus_node/src/config/pointers.rs b/crates/papyrus_node/src/config/pointers.rs index b4f1bf2bba..0cee496fce 100644 --- a/crates/papyrus_node/src/config/pointers.rs +++ b/crates/papyrus_node/src/config/pointers.rs @@ -51,7 +51,7 @@ lazy_static! { &ChainId::Mainnet, "The chain to follow. For more details see https://docs.starknet.io/documentation/architecture_and_concepts/Blocks/transactions/#chain-id.", ), - vec!["storage.db_config.chain_id".to_owned(), "rpc.chain_id".to_owned()], + vec!["storage.db_config.chain_id".to_owned(), "rpc.chain_id".to_owned(), "network.chain_id".to_owned()], ), ( ser_pointer_target_param( diff --git a/crates/papyrus_node/src/config/snapshots/papyrus_node__config__config_test__dump_default_config.snap b/crates/papyrus_node/src/config/snapshots/papyrus_node__config__config_test__dump_default_config.snap index 727cef9bc4..8329b8ee61 100644 --- a/crates/papyrus_node/src/config/snapshots/papyrus_node__config__config_test__dump_default_config.snap +++ b/crates/papyrus_node/src/config/snapshots/papyrus_node__config__config_test__dump_default_config.snap @@ -193,6 +193,11 @@ expression: dumped_default_config "value": true, "privacy": "TemporaryValue" }, + "network.chain_id": { + "description": "The chain to follow. For more details see https://docs.starknet.io/documentation/architecture_and_concepts/Blocks/transactions/#chain-id.", + "value": "SN_MAIN", + "privacy": "Public" + }, "network.idle_connection_timeout": { "description": "Amount of time in seconds that a connection with no active sessions will stay alive.", "value": {