diff --git a/beacon_chain/beacon_node.nim b/beacon_chain/beacon_node.nim index 7a9c41889..50f894214 100644 --- a/beacon_chain/beacon_node.nim +++ b/beacon_chain/beacon_node.nim @@ -49,6 +49,7 @@ type netKeys: DiscKeyPair requestManager: RequestManager bootstrapNodes: seq[ENode] + bootstrapEnrs: seq[enr.Record] db: BeaconChainDB config: BeaconNodeConf attachedValidators: ValidatorPool @@ -178,12 +179,13 @@ proc init*(T: type BeaconNode, conf: BeaconNodeConf): Future[BeaconNode] {.async mainchainMonitor.start() var bootNodes: seq[ENode] - for node in conf.bootstrapNodes: bootNodes.addBootstrapNode(node) - bootNodes.loadBootstrapFile(string conf.bootstrapNodesFile) + var bootEnrs: seq[enr.Record] + for node in conf.bootstrapNodes: addBootstrapNode(node, bootNodes, bootEnrs) + loadBootstrapFile(string conf.bootstrapNodesFile, bootNodes, bootEnrs) let persistentBootstrapFile = conf.dataDir / "bootstrap_nodes.txt" if fileExists(persistentBootstrapFile): - bootNodes.loadBootstrapFile(persistentBootstrapFile) + loadBootstrapFile(persistentBootstrapFile, bootNodes, bootEnrs) bootNodes = filterIt(bootNodes, it.pubkey != netKeys.pubkey) @@ -199,6 +201,7 @@ proc init*(T: type BeaconNode, conf: BeaconNodeConf): Future[BeaconNode] {.async netKeys: netKeys, requestManager: RequestManager.init(network), bootstrapNodes: bootNodes, + bootstrapEnrs: bootEnrs, db: db, config: conf, attachedValidators: ValidatorPool.init(), @@ -240,7 +243,8 @@ proc connectToNetwork(node: BeaconNode) {.async.} = else: info "Waiting for connections" - await node.network.connectToNetwork(node.bootstrapNodes) + await node.network.connectToNetwork(node.bootstrapNodes, + node.bootstrapEnrs) template findIt(s: openarray, predicate: untyped): int = var res = -1 diff --git a/beacon_chain/eth2_discovery.nim b/beacon_chain/eth2_discovery.nim index 09ce4dda4..ea4b9176c 100644 --- a/beacon_chain/eth2_discovery.nim +++ b/beacon_chain/eth2_discovery.nim @@ -73,7 +73,7 @@ proc toMultiAddressStr*(enode: ENode): string = skkey: enode.pubkey)) &"/ip4/{enode.address.ip}/tcp/{enode.address.tcpPort}/p2p/{peerId.pretty}" -proc parseBootstrapAddress*(address: TaintedString): Result[ENode, cstring] = +proc parseBootstrapAddress*(address: TaintedString): Result[enr.Record, cstring] = if address.len == 0: return err "an empty string is not a valid bootstrap node" @@ -81,17 +81,21 @@ proc parseBootstrapAddress*(address: TaintedString): Result[ENode, cstring] = address = string(address) if address[0] == '/': + return err "MultiAddress bootstrap addresses are not supported" + #[ try: let ma = MultiAddress.init(address) - return toENode(ma) except CatchableError: return err "Invalid bootstrap multiaddress" + ]# else: let lowerCaseAddress = toLowerAscii(string address) if lowerCaseAddress.startsWith("enr:"): var enrRec: enr.Record if enrRec.fromURI(string address): + return ok enrRec + #[[ try: # TODO: handle IPv6 let ipBytes = enrRec.get("ip", seq[byte]) @@ -109,36 +113,42 @@ proc parseBootstrapAddress*(address: TaintedString): Result[ENode, cstring] = except CatchableError: # This will continue to the failure path below discard + ]]# return err "Invalid ENR bootstrap record" elif lowerCaseAddress.startsWith("enode:"): + return err "ENode bootstrap addresses are not supported" + #[ try: return ok initEnode(string address) except CatchableError as err: return err "Ignoring invalid enode bootstrap address" + ]# else: return err "Ignoring unrecognized bootstrap address type" -proc addBootstrapNode*(bootNodes: var seq[ENode], - bootstrapAddr: string) = +proc addBootstrapNode*(bootstrapAddr: string, + bootNodes: var seq[ENode], + bootEnrs: var seq[enr.Record]) = let enodeRes = parseBootstrapAddress(bootstrapAddr) if enodeRes.isOk: - bootNodes.add enodeRes.value + bootEnrs.add enodeRes.value else: warn "Ignoring invalid bootstrap address", bootstrapAddr, reason = enodeRes.error -proc loadBootstrapFile*(bootNodes: var seq[ENode], - bootstrapFile: string) = +proc loadBootstrapFile*(bootstrapFile: string, + bootNodes: var seq[ENode], + bootEnrs: var seq[enr.Record]) = if bootstrapFile.len == 0: return let ext = splitFile(bootstrapFile).ext if cmpIgnoreCase(ext, ".txt") == 0: for ln in lines(bootstrapFile): - bootNodes.addBootstrapNode(ln) + addBootstrapNode(ln, bootNodes, bootEnrs) elif cmpIgnoreCase(ext, ".yaml") == 0: # TODO. This is very ugly, but let's try to negotiate the # removal of YAML metadata. for ln in lines(bootstrapFile): - bootNodes.addBootstrapNode(string(ln[3..^2])) + addBootstrapNode(string(ln[3..^2]), bootNodes, bootEnrs) else: error "Unknown bootstrap file format", ext quit 1 diff --git a/beacon_chain/eth2_network.nim b/beacon_chain/eth2_network.nim index c5d759e5a..aa23b709f 100644 --- a/beacon_chain/eth2_network.nim +++ b/beacon_chain/eth2_network.nim @@ -203,7 +203,8 @@ when networkBackend in [libp2p, libp2pDaemon]: return PeerInfo(peer: peerId, addresses: addresses) proc connectToNetwork*(node: Eth2Node, - bootstrapNodes: seq[ENode]) {.async.} = + bootstrapNodes: seq[ENode], + bootstrapEnrs: seq[enr.Record]) {.async.} = when networkBackend == libp2pDaemon: var connected = false for bootstrapNode in bootstrapNodes: @@ -225,7 +226,8 @@ when networkBackend in [libp2p, libp2pDaemon]: fatal "Failed to connect to any bootstrap node. Quitting." quit 1 elif networkBackend == libp2p: - for bootstrapNode in bootstrapNodes: + for bootstrapNode in bootstrapEnrs: + debug "Adding known peer", peer = bootstrapNode node.addKnownPeer bootstrapNode await node.start() diff --git a/beacon_chain/libp2p_backend.nim b/beacon_chain/libp2p_backend.nim index e54374057..f314a3e9a 100644 --- a/beacon_chain/libp2p_backend.nim +++ b/beacon_chain/libp2p_backend.nim @@ -225,7 +225,7 @@ proc init*(T: type Eth2Node, conf: BeaconNodeConf, if msg.protocolMounter != nil: msg.protocolMounter result -proc addKnownPeer*(node: Eth2Node, peer: ENode) = +template addKnownPeer*(node: Eth2Node, peer: ENode|enr.Record) = node.discovery.addNode peer proc start*(node: Eth2Node) {.async.} = diff --git a/vendor/nim-eth b/vendor/nim-eth index 019df303b..31a4e8f95 160000 --- a/vendor/nim-eth +++ b/vendor/nim-eth @@ -1 +1 @@ -Subproject commit 019df303b437f082e01a173a280ee3c5dc10844d +Subproject commit 31a4e8f959c1ce7de0ef5544753009d3b6b46e25