Update discv5 (#3171)

## Issue Addressed

Updates discv5

Pending on
- [x] #3547 
- [x] Alex upgrades his deps

## Proposed Changes

updates discv5 and the enr crate. The only relevant change would be some clear indications of ipv4 usage in lighthouse

## Additional Info

Functionally, this should be equivalent to the prev version.
As draft pending a discv5 release
This commit is contained in:
Divma 2022-10-28 05:40:06 +00:00
parent 5bd1501cb1
commit 46fbf5b98b
16 changed files with 270 additions and 452 deletions

618
Cargo.lock generated

File diff suppressed because it is too large Load Diff

View File

@ -37,11 +37,11 @@ rand = "0.8.5"
zeroize = { version = "1.4.2", features = ["zeroize_derive"] } zeroize = { version = "1.4.2", features = ["zeroize_derive"] }
lighthouse_metrics = { path = "../../common/lighthouse_metrics" } lighthouse_metrics = { path = "../../common/lighthouse_metrics" }
lazy_static = "1.4.0" lazy_static = "1.4.0"
ethers-core = { git = "https://github.com/gakonst/ethers-rs", rev = "02ad93a1cfb7b62eb051c77c61dc4c0218428e4a" } ethers-core = "0.17.0"
builder_client = { path = "../builder_client" } builder_client = { path = "../builder_client" }
fork_choice = { path = "../../consensus/fork_choice" } fork_choice = { path = "../../consensus/fork_choice" }
mev-build-rs = {git = "https://github.com/ralexstokes/mev-rs", rev = "a088806575805c00d63fa59c002abc5eb1dc7709"} mev-build-rs = { git = "https://github.com/ralexstokes/mev-rs", rev = "6c99b0fbdc0427b1625469d2e575303ce08de5b8" }
ethereum-consensus = {git = "https://github.com/ralexstokes/ethereum-consensus", rev = "e1188b1" } ethereum-consensus = { git = "https://github.com/ralexstokes/ethereum-consensus", rev = "a8110af76d97bf2bf27fb987a671808fcbdf1834" }
ssz-rs = {git = "https://github.com/ralexstokes/ssz-rs", rev = "cb08f1" } ssz-rs = { git = "https://github.com/ralexstokes/ssz-rs", rev = "cb08f1" }
tokio-stream = { version = "0.1.9", features = [ "sync" ] } tokio-stream = { version = "0.1.9", features = [ "sync" ] }
strum = "0.24.0" strum = "0.24.0"

View File

@ -5,7 +5,7 @@ authors = ["Sigma Prime <contact@sigmaprime.io>"]
edition = "2021" edition = "2021"
[dependencies] [dependencies]
discv5 = { version = "0.1.0-beta.13", features = ["libp2p"] } discv5 = { version = "0.1.0", features = ["libp2p"] }
unsigned-varint = { version = "0.6.0", features = ["codec"] } unsigned-varint = { version = "0.6.0", features = ["codec"] }
types = { path = "../../consensus/types" } types = { path = "../../consensus/types" }
eth2_ssz_types = "0.2.2" eth2_ssz_types = "0.2.2"
@ -26,7 +26,7 @@ smallvec = "1.6.1"
tokio-io-timeout = "1.1.1" tokio-io-timeout = "1.1.1"
lru = "0.7.1" lru = "0.7.1"
parking_lot = "0.12.0" parking_lot = "0.12.0"
sha2 = "0.9.1" sha2 = "0.10"
snap = "1.0.1" snap = "1.0.1"
hex = "0.4.2" hex = "0.4.2"
tokio-util = { version = "0.6.2", features = ["codec", "compat", "time"] } tokio-util = { version = "0.6.2", features = ["codec", "compat", "time"] }

View File

@ -176,7 +176,7 @@ impl Default for Config {
.filter_rate_limiter(filter_rate_limiter) .filter_rate_limiter(filter_rate_limiter)
.filter_max_bans_per_ip(Some(5)) .filter_max_bans_per_ip(Some(5))
.filter_max_nodes_per_ip(Some(10)) .filter_max_nodes_per_ip(Some(10))
.table_filter(|enr| enr.ip().map_or(false, |ip| is_global(&ip))) // Filter non-global IPs .table_filter(|enr| enr.ip4().map_or(false, |ip| is_global(&ip))) // Filter non-global IPs
.ban_duration(Some(Duration::from_secs(3600))) .ban_duration(Some(Duration::from_secs(3600)))
.ping_interval(Duration::from_secs(300)) .ping_interval(Duration::from_secs(300))
.build(); .build();

View File

@ -149,12 +149,12 @@ pub fn create_enr_builder_from_config<T: EnrKey>(
builder.ip(enr_address); builder.ip(enr_address);
} }
if let Some(udp_port) = config.enr_udp_port { if let Some(udp_port) = config.enr_udp_port {
builder.udp(udp_port); builder.udp4(udp_port);
} }
// we always give it our listening tcp port // we always give it our listening tcp port
if enable_tcp { if enable_tcp {
let tcp_port = config.enr_tcp_port.unwrap_or(config.libp2p_port); let tcp_port = config.enr_tcp_port.unwrap_or(config.libp2p_port);
builder.tcp(tcp_port); builder.tcp4(tcp_port);
} }
builder builder
} }
@ -189,13 +189,13 @@ pub fn build_enr<T: EthSpec>(
/// If this function returns true, we use the `disk_enr`. /// If this function returns true, we use the `disk_enr`.
fn compare_enr(local_enr: &Enr, disk_enr: &Enr) -> bool { fn compare_enr(local_enr: &Enr, disk_enr: &Enr) -> bool {
// take preference over disk_enr address if one is not specified // take preference over disk_enr address if one is not specified
(local_enr.ip().is_none() || local_enr.ip() == disk_enr.ip()) (local_enr.ip4().is_none() || local_enr.ip4() == disk_enr.ip4())
// tcp ports must match // tcp ports must match
&& local_enr.tcp() == disk_enr.tcp() && local_enr.tcp4() == disk_enr.tcp4()
// must match on the same fork // must match on the same fork
&& local_enr.get(ETH2_ENR_KEY) == disk_enr.get(ETH2_ENR_KEY) && local_enr.get(ETH2_ENR_KEY) == disk_enr.get(ETH2_ENR_KEY)
// take preference over disk udp port if one is not specified // take preference over disk udp port if one is not specified
&& (local_enr.udp().is_none() || local_enr.udp() == disk_enr.udp()) && (local_enr.udp4().is_none() || local_enr.udp4() == disk_enr.udp4())
// we need the ATTESTATION_BITFIELD_ENR_KEY and SYNC_COMMITTEE_BITFIELD_ENR_KEY key to match, // we need the ATTESTATION_BITFIELD_ENR_KEY and SYNC_COMMITTEE_BITFIELD_ENR_KEY key to match,
// otherwise we use a new ENR. This will likely only be true for non-validating nodes // otherwise we use a new ENR. This will likely only be true for non-validating nodes
&& local_enr.get(ATTESTATION_BITFIELD_ENR_KEY) == disk_enr.get(ATTESTATION_BITFIELD_ENR_KEY) && local_enr.get(ATTESTATION_BITFIELD_ENR_KEY) == disk_enr.get(ATTESTATION_BITFIELD_ENR_KEY)

View File

@ -48,14 +48,14 @@ impl EnrExt for Enr {
/// The vector remains empty if these fields are not defined. /// The vector remains empty if these fields are not defined.
fn multiaddr(&self) -> Vec<Multiaddr> { fn multiaddr(&self) -> Vec<Multiaddr> {
let mut multiaddrs: Vec<Multiaddr> = Vec::new(); let mut multiaddrs: Vec<Multiaddr> = Vec::new();
if let Some(ip) = self.ip() { if let Some(ip) = self.ip4() {
if let Some(udp) = self.udp() { if let Some(udp) = self.udp4() {
let mut multiaddr: Multiaddr = ip.into(); let mut multiaddr: Multiaddr = ip.into();
multiaddr.push(Protocol::Udp(udp)); multiaddr.push(Protocol::Udp(udp));
multiaddrs.push(multiaddr); multiaddrs.push(multiaddr);
} }
if let Some(tcp) = self.tcp() { if let Some(tcp) = self.tcp4() {
let mut multiaddr: Multiaddr = ip.into(); let mut multiaddr: Multiaddr = ip.into();
multiaddr.push(Protocol::Tcp(tcp)); multiaddr.push(Protocol::Tcp(tcp));
multiaddrs.push(multiaddr); multiaddrs.push(multiaddr);
@ -84,15 +84,15 @@ impl EnrExt for Enr {
fn multiaddr_p2p(&self) -> Vec<Multiaddr> { fn multiaddr_p2p(&self) -> Vec<Multiaddr> {
let peer_id = self.peer_id(); let peer_id = self.peer_id();
let mut multiaddrs: Vec<Multiaddr> = Vec::new(); let mut multiaddrs: Vec<Multiaddr> = Vec::new();
if let Some(ip) = self.ip() { if let Some(ip) = self.ip4() {
if let Some(udp) = self.udp() { if let Some(udp) = self.udp4() {
let mut multiaddr: Multiaddr = ip.into(); let mut multiaddr: Multiaddr = ip.into();
multiaddr.push(Protocol::Udp(udp)); multiaddr.push(Protocol::Udp(udp));
multiaddr.push(Protocol::P2p(peer_id.into())); multiaddr.push(Protocol::P2p(peer_id.into()));
multiaddrs.push(multiaddr); multiaddrs.push(multiaddr);
} }
if let Some(tcp) = self.tcp() { if let Some(tcp) = self.tcp4() {
let mut multiaddr: Multiaddr = ip.into(); let mut multiaddr: Multiaddr = ip.into();
multiaddr.push(Protocol::Tcp(tcp)); multiaddr.push(Protocol::Tcp(tcp));
multiaddr.push(Protocol::P2p(peer_id.into())); multiaddr.push(Protocol::P2p(peer_id.into()));
@ -124,8 +124,8 @@ impl EnrExt for Enr {
fn multiaddr_p2p_tcp(&self) -> Vec<Multiaddr> { fn multiaddr_p2p_tcp(&self) -> Vec<Multiaddr> {
let peer_id = self.peer_id(); let peer_id = self.peer_id();
let mut multiaddrs: Vec<Multiaddr> = Vec::new(); let mut multiaddrs: Vec<Multiaddr> = Vec::new();
if let Some(ip) = self.ip() { if let Some(ip) = self.ip4() {
if let Some(tcp) = self.tcp() { if let Some(tcp) = self.tcp4() {
let mut multiaddr: Multiaddr = ip.into(); let mut multiaddr: Multiaddr = ip.into();
multiaddr.push(Protocol::Tcp(tcp)); multiaddr.push(Protocol::Tcp(tcp));
multiaddr.push(Protocol::P2p(peer_id.into())); multiaddr.push(Protocol::P2p(peer_id.into()));
@ -150,8 +150,8 @@ impl EnrExt for Enr {
fn multiaddr_p2p_udp(&self) -> Vec<Multiaddr> { fn multiaddr_p2p_udp(&self) -> Vec<Multiaddr> {
let peer_id = self.peer_id(); let peer_id = self.peer_id();
let mut multiaddrs: Vec<Multiaddr> = Vec::new(); let mut multiaddrs: Vec<Multiaddr> = Vec::new();
if let Some(ip) = self.ip() { if let Some(ip) = self.ip4() {
if let Some(udp) = self.udp() { if let Some(udp) = self.udp4() {
let mut multiaddr: Multiaddr = ip.into(); let mut multiaddr: Multiaddr = ip.into();
multiaddr.push(Protocol::Udp(udp)); multiaddr.push(Protocol::Udp(udp));
multiaddr.push(Protocol::P2p(peer_id.into())); multiaddr.push(Protocol::P2p(peer_id.into()));
@ -173,8 +173,8 @@ impl EnrExt for Enr {
/// The vector remains empty if these fields are not defined. /// The vector remains empty if these fields are not defined.
fn multiaddr_tcp(&self) -> Vec<Multiaddr> { fn multiaddr_tcp(&self) -> Vec<Multiaddr> {
let mut multiaddrs: Vec<Multiaddr> = Vec::new(); let mut multiaddrs: Vec<Multiaddr> = Vec::new();
if let Some(ip) = self.ip() { if let Some(ip) = self.ip4() {
if let Some(tcp) = self.tcp() { if let Some(tcp) = self.tcp4() {
let mut multiaddr: Multiaddr = ip.into(); let mut multiaddr: Multiaddr = ip.into();
multiaddr.push(Protocol::Tcp(tcp)); multiaddr.push(Protocol::Tcp(tcp));
multiaddrs.push(multiaddr); multiaddrs.push(multiaddr);
@ -232,6 +232,7 @@ impl CombinedKeyExt for CombinedKey {
.expect("libp2p key must be valid"); .expect("libp2p key must be valid");
Ok(CombinedKey::from(ed_keypair)) Ok(CombinedKey::from(ed_keypair))
} }
Keypair::Ecdsa(_) => Err("Ecdsa keypairs not supported"),
} }
} }
} }
@ -265,6 +266,10 @@ pub fn peer_id_to_node_id(peer_id: &PeerId) -> Result<discv5::enr::NodeId, Strin
hasher.finalize(&mut output); hasher.finalize(&mut output);
Ok(discv5::enr::NodeId::parse(&output).expect("Must be correct length")) Ok(discv5::enr::NodeId::parse(&output).expect("Must be correct length"))
} }
PublicKey::Ecdsa(_) => Err(format!(
"Unsupported public key (Ecdsa) from peer {}",
peer_id
)),
} }
} }

View File

@ -197,7 +197,9 @@ impl<TSpec: EthSpec> Discovery<TSpec> {
let local_enr = network_globals.local_enr.read().clone(); let local_enr = network_globals.local_enr.read().clone();
info!(log, "ENR Initialised"; "enr" => local_enr.to_base64(), "seq" => local_enr.seq(), "id"=> %local_enr.node_id(), "ip" => ?local_enr.ip(), "udp"=> ?local_enr.udp(), "tcp" => ?local_enr.tcp()); info!(log, "ENR Initialised"; "enr" => local_enr.to_base64(), "seq" => local_enr.seq(), "id"=> %local_enr.node_id(),
"ip4" => ?local_enr.ip4(), "udp4"=> ?local_enr.udp4(), "tcp4" => ?local_enr.tcp6()
);
let listen_socket = SocketAddr::new(config.listen_address, config.discovery_port); let listen_socket = SocketAddr::new(config.listen_address, config.discovery_port);
@ -214,9 +216,9 @@ impl<TSpec: EthSpec> Discovery<TSpec> {
"Adding node to routing table"; "Adding node to routing table";
"node_id" => %bootnode_enr.node_id(), "node_id" => %bootnode_enr.node_id(),
"peer_id" => %bootnode_enr.peer_id(), "peer_id" => %bootnode_enr.peer_id(),
"ip" => ?bootnode_enr.ip(), "ip" => ?bootnode_enr.ip4(),
"udp" => ?bootnode_enr.udp(), "udp" => ?bootnode_enr.udp4(),
"tcp" => ?bootnode_enr.tcp() "tcp" => ?bootnode_enr.tcp4()
); );
let repr = bootnode_enr.to_string(); let repr = bootnode_enr.to_string();
let _ = discv5.add_enr(bootnode_enr).map_err(|e| { let _ = discv5.add_enr(bootnode_enr).map_err(|e| {
@ -268,9 +270,9 @@ impl<TSpec: EthSpec> Discovery<TSpec> {
"Adding node to routing table"; "Adding node to routing table";
"node_id" => %enr.node_id(), "node_id" => %enr.node_id(),
"peer_id" => %enr.peer_id(), "peer_id" => %enr.peer_id(),
"ip" => ?enr.ip(), "ip" => ?enr.ip4(),
"udp" => ?enr.udp(), "udp" => ?enr.udp4(),
"tcp" => ?enr.tcp() "tcp" => ?enr.tcp4()
); );
let _ = discv5.add_enr(enr).map_err(|e| { let _ = discv5.add_enr(enr).map_err(|e| {
error!( error!(
@ -763,7 +765,7 @@ impl<TSpec: EthSpec> Discovery<TSpec> {
// we can connect to peers who aren't compatible with an upcoming fork. // we can connect to peers who aren't compatible with an upcoming fork.
// `fork_digest` **must** be same. // `fork_digest` **must** be same.
enr.eth2().map(|e| e.fork_digest) == Ok(enr_fork_id.fork_digest) enr.eth2().map(|e| e.fork_digest) == Ok(enr_fork_id.fork_digest)
&& (enr.tcp().is_some() || enr.tcp6().is_some()) && (enr.tcp4().is_some() || enr.tcp6().is_some())
}; };
// General predicate // General predicate
@ -1040,7 +1042,8 @@ impl<TSpec: EthSpec> NetworkBehaviour for Discovery<TSpec> {
} }
Discv5Event::EnrAdded { .. } Discv5Event::EnrAdded { .. }
| Discv5Event::TalkRequest(_) | Discv5Event::TalkRequest(_)
| Discv5Event::NodeInserted { .. } => {} // Ignore all other discv5 server events | Discv5Event::NodeInserted { .. }
| Discv5Event::SessionEstablished { .. } => {} // Ignore all other discv5 server events
} }
} }
} }

View File

@ -130,7 +130,7 @@ impl<TSpec: EthSpec> NetworkBehaviour for PeerManager<TSpec> {
} }
// Check NAT if metrics are enabled // Check NAT if metrics are enabled
if self.network_globals.local_enr.read().udp().is_some() { if self.network_globals.local_enr.read().udp4().is_some() {
metrics::check_nat(); metrics::check_nat();
} }

View File

@ -11,7 +11,10 @@ use types::EthSpec;
pub async fn run<T: EthSpec>(config: BootNodeConfig<T>, log: slog::Logger) { pub async fn run<T: EthSpec>(config: BootNodeConfig<T>, log: slog::Logger) {
// Print out useful information about the generated ENR // Print out useful information about the generated ENR
let enr_socket = config.local_enr.udp_socket().expect("Enr has a UDP socket"); let enr_socket = config
.local_enr
.udp4_socket()
.expect("Enr has a UDP socket");
let eth2_field = config let eth2_field = config
.local_enr .local_enr
.eth2() .eth2()
@ -39,7 +42,7 @@ pub async fn run<T: EthSpec>(config: BootNodeConfig<T>, log: slog::Logger) {
info!( info!(
log, log,
"Adding bootnode"; "Adding bootnode";
"address" => ?enr.udp_socket(), "address" => ?enr.udp4_socket(),
"peer_id" => enr.peer_id().to_string(), "peer_id" => enr.peer_id().to_string(),
"node_id" => enr.node_id().to_string() "node_id" => enr.node_id().to_string()
); );
@ -89,11 +92,12 @@ pub async fn run<T: EthSpec>(config: BootNodeConfig<T>, log: slog::Logger) {
// Ignore these events here // Ignore these events here
} }
Discv5Event::EnrAdded { .. } => {} // Ignore Discv5Event::EnrAdded { .. } => {} // Ignore
Discv5Event::TalkRequest(_) => {} // Ignore Discv5Event::TalkRequest(_) => {} // Ignore
Discv5Event::NodeInserted { .. } => {} // Ignore Discv5Event::NodeInserted { .. } => {} // Ignore
Discv5Event::SocketUpdated(socket_addr) => { Discv5Event::SocketUpdated(socket_addr) => {
info!(log, "External socket address updated"; "socket_addr" => format!("{:?}", socket_addr)); info!(log, "External socket address updated"; "socket_addr" => format!("{:?}", socket_addr));
} }
Discv5Event::SessionEstablished{ .. } => {} // Ignore
} }
} }
} }

View File

@ -9,7 +9,7 @@ build = "build.rs"
[build-dependencies] [build-dependencies]
reqwest = { version = "0.11.0", features = ["blocking", "json", "native-tls-vendored"] } reqwest = { version = "0.11.0", features = ["blocking", "json", "native-tls-vendored"] }
serde_json = "1.0.58" serde_json = "1.0.58"
sha2 = "0.9.1" sha2 = "0.10"
hex = "0.4.2" hex = "0.4.2"
[dependencies] [dependencies]

View File

@ -18,4 +18,4 @@ serde_yaml = "0.8.13"
types = { path = "../../consensus/types"} types = { path = "../../consensus/types"}
eth2_ssz = "0.4.1" eth2_ssz = "0.4.1"
eth2_config = { path = "../eth2_config"} eth2_config = { path = "../eth2_config"}
enr = { version = "0.5.1", features = ["ed25519", "k256"] } enr = { version = "0.6.2", features = ["ed25519", "k256"] }

View File

@ -10,7 +10,7 @@ description = "Hashing primitives used in Ethereum 2.0"
lazy_static = { version = "1.4.0", optional = true } lazy_static = { version = "1.4.0", optional = true }
cpufeatures = { version = "0.2.5", optional = true } cpufeatures = { version = "0.2.5", optional = true }
ring = "0.16.19" ring = "0.16.19"
sha2 = "0.10.2" sha2 = "0.10"
[dev-dependencies] [dev-dependencies]
rustc-hex = "2.1.0" rustc-hex = "2.1.0"

View File

@ -7,7 +7,7 @@ edition = "2021"
# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html # See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html
[dependencies] [dependencies]
sha2 = "0.9.1" sha2 = "0.10"
zeroize = { version = "1.4.2", features = ["zeroize_derive"] } zeroize = { version = "1.4.2", features = ["zeroize_derive"] }
num-bigint-dig = { version = "0.6.0", features = ["zeroize"] } num-bigint-dig = { version = "0.6.0", features = ["zeroize"] }
ring = "0.16.19" ring = "0.16.19"

View File

@ -11,7 +11,7 @@ rand = "0.8.5"
hmac = "0.11.0" hmac = "0.11.0"
pbkdf2 = { version = "0.8.0", default-features = false } pbkdf2 = { version = "0.8.0", default-features = false }
scrypt = { version = "0.7.0", default-features = false } scrypt = { version = "0.7.0", default-features = false }
sha2 = "0.9.1" sha2 = "0.9.2"
uuid = { version = "0.8.1", features = ["serde", "v4"] } uuid = { version = "0.8.1", features = ["serde", "v4"] }
zeroize = { version = "1.4.2", features = ["zeroize_derive"] } zeroize = { version = "1.4.2", features = ["zeroize_derive"] }
serde = "1.0.116" serde = "1.0.116"

View File

@ -56,7 +56,7 @@ impl CommandLineTestExec for CommandLineTest {
fn enr_address_arg() { fn enr_address_arg() {
let mut test = CommandLineTest::new(); let mut test = CommandLineTest::new();
test.run_with_ip().with_config(|config| { test.run_with_ip().with_config(|config| {
assert_eq!(config.local_enr.ip(), Some(IP_ADDRESS.parse().unwrap())); assert_eq!(config.local_enr.ip4(), Some(IP_ADDRESS.parse().unwrap()));
}); });
} }
@ -127,7 +127,7 @@ fn enr_port_flag() {
.flag("enr-port", Some(port.to_string().as_str())) .flag("enr-port", Some(port.to_string().as_str()))
.run_with_ip() .run_with_ip()
.with_config(|config| { .with_config(|config| {
assert_eq!(config.local_enr.udp(), Some(port)); assert_eq!(config.local_enr.udp4(), Some(port));
}) })
} }

View File

@ -15,8 +15,8 @@ execution_layer = { path = "../../beacon_node/execution_layer" }
sensitive_url = { path = "../../common/sensitive_url" } sensitive_url = { path = "../../common/sensitive_url" }
types = { path = "../../consensus/types" } types = { path = "../../consensus/types" }
unused_port = { path = "../../common/unused_port" } unused_port = { path = "../../common/unused_port" }
ethers-core = { git = "https://github.com/gakonst/ethers-rs", rev = "02ad93a1cfb7b62eb051c77c61dc4c0218428e4a" } ethers-core = "0.17.0"
ethers-providers = { git = "https://github.com/gakonst/ethers-rs", rev = "02ad93a1cfb7b62eb051c77c61dc4c0218428e4a" } ethers-providers = "0.17.0"
deposit_contract = { path = "../../common/deposit_contract" } deposit_contract = { path = "../../common/deposit_contract" }
reqwest = { version = "0.11.0", features = ["json"] } reqwest = { version = "0.11.0", features = ["json"] }
hex = "0.4.2" hex = "0.4.2"