fix: use enrforkid in dns (#7900)

Co-authored-by: Emilia Hane <elsaemiliaevahane@gmail.com>
This commit is contained in:
Matthias Seitz
2024-04-26 11:24:26 +02:00
committed by GitHub
parent 57d09e84be
commit 6425064d07
6 changed files with 45 additions and 33 deletions

View File

@ -115,6 +115,32 @@ pub struct ForkId {
pub next: u64,
}
/// Represents a forward-compatible ENR entry for including the forkid in a node record via
/// EIP-868. Forward compatibility is achieved by allowing trailing fields.
///
/// See:
/// <https://github.com/ethereum/devp2p/blob/master/enr-entries/eth.md#entry-format>
///
/// for how geth implements ForkId values and forward compatibility.
#[derive(Debug, Clone, PartialEq, Eq, RlpEncodable, RlpDecodable)]
#[rlp(trailing)]
pub struct EnrForkIdEntry {
/// The inner forkid
pub fork_id: ForkId,
}
impl From<ForkId> for EnrForkIdEntry {
fn from(fork_id: ForkId) -> Self {
Self { fork_id }
}
}
impl From<EnrForkIdEntry> for ForkId {
fn from(entry: EnrForkIdEntry) -> Self {
entry.fork_id
}
}
/// Reason for rejecting provided `ForkId`.
#[derive(Clone, Copy, Debug, Error, PartialEq, Eq, Hash)]
pub enum ValidationError {

View File

@ -20,7 +20,9 @@ mod forkid;
mod hardfork;
mod head;
pub use forkid::{ForkFilter, ForkFilterKey, ForkHash, ForkId, ForkTransition, ValidationError};
pub use forkid::{
EnrForkIdEntry, ForkFilter, ForkFilterKey, ForkHash, ForkId, ForkTransition, ValidationError,
};
pub use hardfork::Hardfork;
pub use head::Head;

View File

@ -28,7 +28,6 @@ use crate::{
error::{DecodePacketError, Discv4Error},
proto::{FindNode, Message, Neighbours, Packet, Ping, Pong},
};
use alloy_rlp::{RlpDecodable, RlpEncodable};
use discv5::{
kbucket,
kbucket::{
@ -2174,33 +2173,13 @@ pub enum DiscoveryUpdate {
Batch(Vec<DiscoveryUpdate>),
}
/// Represents a forward-compatible ENR entry for including the forkid in a node record via
/// EIP-868. Forward compatibility is achieved by allowing trailing fields.
///
/// See:
/// <https://github.com/ethereum/go-ethereum/blob/9244d5cd61f3ea5a7645fdf2a1a96d53421e412f/eth/protocols/eth/discovery.go#L27-L38>
///
/// for how geth implements ForkId values and forward compatibility.
#[derive(Debug, Clone, PartialEq, Eq, RlpEncodable, RlpDecodable)]
#[rlp(trailing)]
pub struct EnrForkIdEntry {
/// The inner forkid
pub fork_id: ForkId,
}
impl From<ForkId> for EnrForkIdEntry {
fn from(fork_id: ForkId) -> Self {
Self { fork_id }
}
}
#[cfg(test)]
mod tests {
use super::*;
use crate::test_utils::{create_discv4, create_discv4_with_config, rng_endpoint, rng_record};
use alloy_rlp::{Decodable, Encodable};
use rand::{thread_rng, Rng};
use reth_primitives::{hex, mainnet_nodes, ForkHash};
use reth_primitives::{hex, mainnet_nodes, EnrForkIdEntry, ForkHash};
use std::future::poll_fn;
#[tokio::test]

View File

@ -1,11 +1,11 @@
//! Discovery v4 protocol implementation.
use crate::{error::DecodePacketError, EnrForkIdEntry, PeerId, MAX_PACKET_SIZE, MIN_PACKET_SIZE};
use crate::{error::DecodePacketError, PeerId, MAX_PACKET_SIZE, MIN_PACKET_SIZE};
use alloy_rlp::{Decodable, Encodable, Error as RlpError, Header, RlpDecodable, RlpEncodable};
use enr::Enr;
use reth_primitives::{
bytes::{Buf, BufMut, Bytes, BytesMut},
keccak256, pk2id, ForkId, NodeRecord, B256,
keccak256, pk2id, EnrForkIdEntry, ForkId, NodeRecord, B256,
};
use secp256k1::{
ecdsa::{RecoverableSignature, RecoveryId},
@ -261,7 +261,7 @@ impl EnrResponse {
/// See also <https://github.com/ethereum/go-ethereum/blob/9244d5cd61f3ea5a7645fdf2a1a96d53421e412f/eth/protocols/eth/discovery.go#L36>
pub fn eth_fork_id(&self) -> Option<ForkId> {
let mut maybe_fork_id = self.enr.get_raw_rlp(b"eth")?;
EnrForkIdEntry::decode(&mut maybe_fork_id).ok().map(|entry| entry.fork_id)
EnrForkIdEntry::decode(&mut maybe_fork_id).ok().map(Into::into)
}
}

View File

@ -22,7 +22,7 @@ use crate::{
pub use config::DnsDiscoveryConfig;
use enr::Enr;
use error::ParseDnsEntryError;
use reth_primitives::{pk2id, ForkId, NodeRecord};
use reth_primitives::{pk2id, EnrForkIdEntry, ForkId, NodeRecord};
use schnellru::{ByLength, LruMap};
use secp256k1::SecretKey;
use std::{
@ -400,7 +400,8 @@ fn convert_enr_node_record(enr: &Enr<SecretKey>) -> Option<DnsNodeRecordUpdate>
}
.into_ipv4_mapped();
let fork_id = enr.get_decodable::<ForkId>(b"eth").transpose().ok()?;
let fork_id =
enr.get_decodable::<EnrForkIdEntry>(b"eth").transpose().ok().flatten().map(Into::into);
Some(DnsNodeRecordUpdate { node_record, fork_id, enr: enr.clone() })
}
@ -423,7 +424,7 @@ mod tests {
.ip("127.0.0.1".parse().unwrap())
.udp4(9000)
.tcp4(30303)
.add_value(b"eth", &MAINNET.latest_fork_id())
.add_value(b"eth", &EnrForkIdEntry::from(MAINNET.latest_fork_id()))
.build(&secret_key)
.unwrap();
@ -446,7 +447,7 @@ mod tests {
.ip("127.0.0.1".parse().unwrap())
.udp4(9000)
.tcp4(30303)
.add_value(b"eth", &MAINNET.latest_fork_id())
.add_value(b"eth", &EnrForkIdEntry::from(MAINNET.latest_fork_id()))
.add_value(b"opstack", &ForkId { hash: ForkHash(rand::random()), next: rand::random() })
.build(&secret_key)
.unwrap();
@ -510,7 +511,11 @@ mod tests {
let mut builder = Enr::builder();
let fork_id = MAINNET.hardfork_fork_id(Hardfork::Frontier).unwrap();
builder.ip4(Ipv4Addr::LOCALHOST).udp4(30303).tcp4(30303).add_value(b"eth", &fork_id);
builder
.ip4(Ipv4Addr::LOCALHOST)
.udp4(30303)
.tcp4(30303)
.add_value(b"eth", &EnrForkIdEntry::from(fork_id));
let enr = builder.build(&secret_key).unwrap();
resolver.insert(format!("{}.{}", root.enr_root.clone(), link.domain), enr.to_base64());

View File

@ -7,12 +7,12 @@ use crate::{
};
use enr::Enr;
use futures::StreamExt;
use reth_discv4::{DiscoveryUpdate, Discv4, Discv4Config, EnrForkIdEntry};
use reth_discv4::{DiscoveryUpdate, Discv4, Discv4Config};
use reth_discv5::{DiscoveredPeer, Discv5};
use reth_dns_discovery::{
DnsDiscoveryConfig, DnsDiscoveryHandle, DnsDiscoveryService, DnsNodeRecordUpdate, DnsResolver,
};
use reth_primitives::{ForkId, NodeRecord, PeerId};
use reth_primitives::{EnrForkIdEntry, ForkId, NodeRecord, PeerId};
use secp256k1::SecretKey;
use std::{
collections::VecDeque,