Skip to content

Commit

Permalink
Enhanced IPv6 support (discovery) (#8410)
Browse files Browse the repository at this point in the history
  • Loading branch information
StefanBratanov authored Jul 1, 2024
1 parent 51a0488 commit 69bf93f
Show file tree
Hide file tree
Showing 18 changed files with 217 additions and 61 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -49,7 +49,7 @@ void setup() {
when(eth2P2PNetwork.getNodeId()).thenReturn(node1);
when(eth2P2PNetwork.getEnr()).thenReturn(Optional.of(enr));
when(eth2P2PNetwork.getNodeAddresses()).thenReturn(List.of(address));
when(eth2P2PNetwork.getDiscoveryAddress()).thenReturn(Optional.of(discoveryAddress));
when(eth2P2PNetwork.getDiscoveryAddresses()).thenReturn(Optional.of(List.of(discoveryAddress)));
}

@Test
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -62,8 +62,7 @@ public List<String> getListeningAddresses() {
}

public List<String> getDiscoveryAddresses() {
Optional<String> discoveryAddressOptional = network.getDiscoveryAddress();
return discoveryAddressOptional.map(List::of).orElseGet(List::of);
return network.getDiscoveryAddresses().orElseGet(List::of);
}

public MetadataMessage getMetadata() {
Expand Down
2 changes: 1 addition & 1 deletion gradle/versions.gradle
Original file line number Diff line number Diff line change
Expand Up @@ -157,7 +157,7 @@ dependencyManagement {

// discovery includes tuweni libraries under a different name so version resolution doesn't work
// exclude them here and leave them to be included on the classpath by the version we use
dependency('tech.pegasys.discovery:discovery:22.12.0') {
dependency('tech.pegasys.discovery:discovery:24.6.0') {
exclude 'org.apache.tuweni:bytes'
exclude 'org.apache.tuweni:crypto'
exclude 'org.apache.tuweni:units'
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,7 @@
import java.io.UncheckedIOException;
import java.net.Inet6Address;
import java.net.InetAddress;
import java.net.InetSocketAddress;
import java.net.UnknownHostException;

public class IPVersionResolver {
Expand All @@ -39,12 +40,16 @@ public static IPVersion resolve(final String address) {
try {
final InetAddress inetAddress = InetAddress.getByName(address);
return resolve(inetAddress);
} catch (UnknownHostException ex) {
} catch (final UnknownHostException ex) {
throw new UncheckedIOException(ex);
}
}

public static IPVersion resolve(final InetAddress inetAddress) {
return inetAddress instanceof Inet6Address ? IPVersion.IP_V6 : IPVersion.IP_V4;
}

public static IPVersion resolve(final InetSocketAddress inetSocketAddress) {
return resolve(inetSocketAddress.getAddress());
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -200,7 +200,10 @@ public P2PConfig build() {

final NetworkConfig networkConfig = this.networkConfig.build();
discoveryConfig.listenUdpPortDefault(networkConfig.getListenPort());
discoveryConfig.listenUdpPortIpv6Default(networkConfig.getListenPortIpv6());
discoveryConfig.advertisedUdpPortDefault(OptionalInt.of(networkConfig.getAdvertisedPort()));
discoveryConfig.advertisedUdpPortIpv6Default(
OptionalInt.of(networkConfig.getAdvertisedPortIpv6()));

return new P2PConfig(
spec,
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,7 @@

import static com.google.common.base.Preconditions.checkNotNull;
import static tech.pegasys.teku.networking.p2p.network.config.NetworkConfig.DEFAULT_P2P_PORT;
import static tech.pegasys.teku.networking.p2p.network.config.NetworkConfig.DEFAULT_P2P_PORT_IPV6;

import java.util.Collections;
import java.util.List;
Expand All @@ -31,7 +32,9 @@ public class DiscoveryConfig {

private final boolean isDiscoveryEnabled;
private final int listenUdpPort;
private final int listenUpdPortIpv6;
private final OptionalInt advertisedUdpPort;
private final OptionalInt advertisedUdpPortIpv6;
private final List<String> staticPeers;
private final List<String> bootnodes;
private final int minPeers;
Expand All @@ -42,7 +45,9 @@ public class DiscoveryConfig {
private DiscoveryConfig(
final boolean isDiscoveryEnabled,
final int listenUdpPort,
final int listenUpdPortIpv6,
final OptionalInt advertisedUdpPort,
final OptionalInt advertisedUdpPortIpv6,
final List<String> staticPeers,
final List<String> bootnodes,
final int minPeers,
Expand All @@ -51,7 +56,9 @@ private DiscoveryConfig(
final boolean siteLocalAddressesEnabled) {
this.isDiscoveryEnabled = isDiscoveryEnabled;
this.listenUdpPort = listenUdpPort;
this.listenUpdPortIpv6 = listenUpdPortIpv6;
this.advertisedUdpPort = advertisedUdpPort;
this.advertisedUdpPortIpv6 = advertisedUdpPortIpv6;
this.staticPeers = staticPeers;
this.bootnodes = bootnodes;
this.minPeers = minPeers;
Expand All @@ -72,10 +79,18 @@ public int getListenUdpPort() {
return listenUdpPort;
}

public int getListenUpdPortIpv6() {
return listenUpdPortIpv6;
}

public int getAdvertisedUdpPort() {
return advertisedUdpPort.orElse(listenUdpPort);
}

public int getAdvertisedUdpPortIpv6() {
return advertisedUdpPortIpv6.orElse(listenUpdPortIpv6);
}

public List<String> getStaticPeers() {
return staticPeers;
}
Expand Down Expand Up @@ -108,7 +123,9 @@ public static class Builder {
private int maxPeers = DEFAULT_P2P_PEERS_UPPER_BOUND;
private OptionalInt minRandomlySelectedPeers = OptionalInt.empty();
private OptionalInt listenUdpPort = OptionalInt.empty();
private OptionalInt listenUdpPortIpv6 = OptionalInt.empty();
private OptionalInt advertisedUdpPort = OptionalInt.empty();
private OptionalInt advertisedUdpPortIpv6 = OptionalInt.empty();
private boolean siteLocalAddressesEnabled = DEFAULT_SITE_LOCAL_ADDRESSES_ENABLED;

private Builder() {}
Expand All @@ -119,7 +136,9 @@ public DiscoveryConfig build() {
return new DiscoveryConfig(
isDiscoveryEnabled,
listenUdpPort.orElseThrow(),
listenUdpPortIpv6.orElseThrow(),
advertisedUdpPort,
advertisedUdpPortIpv6,
staticPeers,
bootnodes == null ? Collections.emptyList() : bootnodes,
minPeers,
Expand All @@ -139,6 +158,9 @@ private void initMissingDefaults() {
if (listenUdpPort.isEmpty()) {
listenUdpPort = OptionalInt.of(DEFAULT_P2P_PORT);
}
if (listenUdpPortIpv6.isEmpty()) {
listenUdpPortIpv6 = OptionalInt.of(DEFAULT_P2P_PORT_IPV6);
}
}

public Builder isDiscoveryEnabled(final Boolean discoveryEnabled) {
Expand All @@ -148,32 +170,37 @@ public Builder isDiscoveryEnabled(final Boolean discoveryEnabled) {
}

public Builder listenUdpPort(final int listenUdpPort) {
if (!PortAvailability.isPortValid(listenUdpPort)) {
throw new InvalidConfigurationException(
String.format("Invalid listenUdpPort: %d", listenUdpPort));
}
validatePort(listenUdpPort, "--p2p-udp-port");
this.listenUdpPort = OptionalInt.of(listenUdpPort);
return this;
}

public Builder listenUdpPortDefault(final int listenUdpPort) {
if (!PortAvailability.isPortValid(listenUdpPort)) {
throw new InvalidConfigurationException(
String.format("Invalid listenUdpPortDefault: %d", listenUdpPort));
}
validatePort(listenUdpPort, "--p2p-udp-port");
if (this.listenUdpPort.isEmpty()) {
this.listenUdpPort = OptionalInt.of(listenUdpPort);
}
return this;
}

public Builder listenUdpPortIpv6(final int listenUdpPortIpv6) {
validatePort(listenUdpPortIpv6, "--Xp2p-udp-port-ipv6");
this.listenUdpPortIpv6 = OptionalInt.of(listenUdpPortIpv6);
return this;
}

public Builder listenUdpPortIpv6Default(final int listenUdpPortIpv6) {
validatePort(listenUdpPortIpv6, "--Xp2p-udp-port-ipv6");
if (this.listenUdpPortIpv6.isEmpty()) {
this.listenUdpPortIpv6 = OptionalInt.of(listenUdpPortIpv6);
}
return this;
}

public Builder advertisedUdpPort(final OptionalInt advertisedUdpPort) {
checkNotNull(advertisedUdpPort);
if (advertisedUdpPort.isPresent()) {
if (!PortAvailability.isPortValid(advertisedUdpPort.getAsInt())) {
throw new InvalidConfigurationException(
String.format("Invalid advertisedUdpPort: %d", advertisedUdpPort.getAsInt()));
}
validatePort(advertisedUdpPort.getAsInt(), "--p2p-advertised-udp-port");
}
this.advertisedUdpPort = advertisedUdpPort;
return this;
Expand All @@ -182,17 +209,34 @@ public Builder advertisedUdpPort(final OptionalInt advertisedUdpPort) {
public Builder advertisedUdpPortDefault(final OptionalInt advertisedUdpPort) {
checkNotNull(advertisedUdpPort);
if (advertisedUdpPort.isPresent()) {
if (!PortAvailability.isPortValid(advertisedUdpPort.getAsInt())) {
throw new InvalidConfigurationException(
String.format("Invalid advertisedUdpPortDefault: %d", advertisedUdpPort.getAsInt()));
}
validatePort(advertisedUdpPort.getAsInt(), "--p2p-advertised-udp-port");
}
if (this.advertisedUdpPort.isEmpty()) {
this.advertisedUdpPort = advertisedUdpPort;
}
return this;
}

public Builder advertisedUdpPortIpv6(final OptionalInt advertisedUdpPortIpv6) {
checkNotNull(advertisedUdpPortIpv6);
if (advertisedUdpPortIpv6.isPresent()) {
validatePort(advertisedUdpPortIpv6.getAsInt(), "--Xp2p-advertised-udp-port-ipv6");
}
this.advertisedUdpPortIpv6 = advertisedUdpPortIpv6;
return this;
}

public Builder advertisedUdpPortIpv6Default(final OptionalInt advertisedUdpPortIpv6) {
checkNotNull(advertisedUdpPortIpv6);
if (advertisedUdpPortIpv6.isPresent()) {
validatePort(advertisedUdpPortIpv6.getAsInt(), "--Xp2p-advertised-udp-port-ipv6");
}
if (this.advertisedUdpPortIpv6.isEmpty()) {
this.advertisedUdpPortIpv6 = advertisedUdpPortIpv6;
}
return this;
}

public Builder staticPeers(final List<String> staticPeers) {
checkNotNull(staticPeers);
this.staticPeers = staticPeers;
Expand Down Expand Up @@ -245,5 +289,11 @@ public Builder siteLocalAddressesEnabled(final boolean siteLocalAddressesEnabled
this.siteLocalAddressesEnabled = siteLocalAddressesEnabled;
return this;
}

private void validatePort(final int port, final String cliOption) {
if (!PortAvailability.isPortValid(port)) {
throw new InvalidConfigurationException(String.format("Invalid %s: %d", cliOption, port));
}
}
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,7 @@
package tech.pegasys.teku.networking.p2p.discovery;

import java.math.BigInteger;
import java.util.List;
import java.util.Optional;
import java.util.stream.Stream;
import org.apache.logging.log4j.LogManager;
Expand Down Expand Up @@ -115,8 +116,8 @@ public Optional<UInt256> getDiscoveryNodeId() {
}

@Override
public Optional<String> getDiscoveryAddress() {
return discoveryService.getDiscoveryAddress();
public Optional<List<String>> getDiscoveryAddresses() {
return discoveryService.getDiscoveryAddresses();
}

public void setLongTermAttestationSubnetSubscriptions(final Iterable<Integer> subnetIds) {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,7 @@
package tech.pegasys.teku.networking.p2p.discovery;

import java.util.Collection;
import java.util.List;
import java.util.Optional;
import java.util.stream.Stream;
import org.apache.tuweni.bytes.Bytes;
Expand All @@ -36,7 +37,7 @@ public interface DiscoveryService {

Optional<Bytes> getNodeId();

Optional<String> getDiscoveryAddress();
Optional<List<String>> getDiscoveryAddresses();

void updateCustomENRField(String fieldName, Bytes value);
}
Loading

0 comments on commit 69bf93f

Please sign in to comment.