From db705bb45db2c3b698ea90fe3d0060170a47f87d Mon Sep 17 00:00:00 2001 From: Felix Lange Date: Thu, 6 Feb 2020 22:14:13 +0100 Subject: [PATCH] eth: integrate p2p/dnsdisc --- eth/backend.go | 8 ++++++++ eth/config.go | 4 ++++ eth/{enr_entry.go => discovery.go} | 29 +++++++++++++++++++++++++++++ 3 files changed, 41 insertions(+) rename eth/{enr_entry.go => discovery.go} (59%) diff --git a/eth/backend.go b/eth/backend.go index adde609de0..bda307d95b 100644 --- a/eth/backend.go +++ b/eth/backend.go @@ -47,6 +47,7 @@ import ( "github.com/ethereum/go-ethereum/miner" "github.com/ethereum/go-ethereum/node" "github.com/ethereum/go-ethereum/p2p" + "github.com/ethereum/go-ethereum/p2p/enode" "github.com/ethereum/go-ethereum/p2p/enr" "github.com/ethereum/go-ethereum/params" "github.com/ethereum/go-ethereum/rlp" @@ -74,6 +75,7 @@ type Ethereum struct { blockchain *core.BlockChain protocolManager *ProtocolManager lesServer LesServer + dialCandiates enode.Iterator // DB interfaces chainDb ethdb.Database // Block chain database @@ -220,6 +222,11 @@ func New(ctx *node.ServiceContext, config *Config) (*Ethereum, error) { } eth.APIBackend.gpo = gasprice.NewOracle(eth.APIBackend, gpoParams) + eth.dialCandiates, err = eth.setupDiscovery(&ctx.Config.P2P) + if err != nil { + return nil, err + } + return eth, nil } @@ -510,6 +517,7 @@ func (s *Ethereum) Protocols() []p2p.Protocol { for i, vsn := range ProtocolVersions { protos[i] = s.protocolManager.makeProtocol(vsn) protos[i].Attributes = []enr.Entry{s.currentEthEntry()} + protos[i].DialCandidates = s.dialCandiates } if s.lesServer != nil { protos = append(protos, s.lesServer.Protocols()...) diff --git a/eth/config.go b/eth/config.go index 8240391114..aff2b170cc 100644 --- a/eth/config.go +++ b/eth/config.go @@ -95,6 +95,10 @@ type Config struct { NetworkId uint64 // Network ID to use for selecting peers to connect to SyncMode downloader.SyncMode + // Discovery options + DisableDNSDiscovery bool + DiscoveryURLs []string + NoPruning bool // Whether to disable pruning and flush everything to disk NoPrefetch bool // Whether to disable prefetching and only load state on demand diff --git a/eth/enr_entry.go b/eth/discovery.go similarity index 59% rename from eth/enr_entry.go rename to eth/discovery.go index d9e7b95784..e0e539b7d8 100644 --- a/eth/enr_entry.go +++ b/eth/discovery.go @@ -17,12 +17,23 @@ package eth import ( + "github.com/ethereum/go-ethereum/common" "github.com/ethereum/go-ethereum/core" "github.com/ethereum/go-ethereum/core/forkid" + "github.com/ethereum/go-ethereum/p2p" + "github.com/ethereum/go-ethereum/p2p/dnsdisc" "github.com/ethereum/go-ethereum/p2p/enode" + "github.com/ethereum/go-ethereum/params" "github.com/ethereum/go-ethereum/rlp" ) +var knownDNSNetworks = map[common.Hash]string{ + params.MainnetGenesisHash: "enrtree://AMBMWDM3J6UY3M32TMMROUNLX6Y3YTLVC3DC6HN2AVG5NHNSAXDW6@all.mainnet.nodes.ethflare.xyz", + params.TestnetGenesisHash: "enrtree://AMBMWDM3J6UY3M32TMMROUNLX6Y3YTLVC3DC6HN2AVG5NHNSAXDW6@all.ropsten.nodes.ethflare.xyz", + params.RinkebyGenesisHash: "enrtree://AMBMWDM3J6UY3M32TMMROUNLX6Y3YTLVC3DC6HN2AVG5NHNSAXDW6@all.rinkeby.nodes.ethflare.xyz", + params.GoerliGenesisHash: "enrtree://AMBMWDM3J6UY3M32TMMROUNLX6Y3YTLVC3DC6HN2AVG5NHNSAXDW6@all.goerli.nodes.ethflare.xyz", +} + // ethEntry is the "eth" ENR entry which advertises eth protocol // on the discovery network. type ethEntry struct { @@ -37,6 +48,7 @@ func (e ethEntry) ENRKey() string { return "eth" } +// startEthEntryUpdate starts the ENR updater loop. func (eth *Ethereum) startEthEntryUpdate(ln *enode.LocalNode) { var newHead = make(chan core.ChainHeadEvent, 10) sub := eth.blockchain.SubscribeChainHeadEvent(newHead) @@ -59,3 +71,20 @@ func (eth *Ethereum) startEthEntryUpdate(ln *enode.LocalNode) { func (eth *Ethereum) currentEthEntry() *ethEntry { return ðEntry{ForkID: forkid.NewID(eth.blockchain)} } + +// setupDiscovery creates the node discovery source for the eth protocol. +func (eth *Ethereum) setupDiscovery(cfg *p2p.Config) (enode.Iterator, error) { + if cfg.NoDiscovery || eth.config.DisableDNSDiscovery { + return nil, nil + } + known := knownDNSNetworks[eth.blockchain.Genesis().Hash()] + urls := eth.config.DiscoveryURLs + if len(urls) == 0 { + if known == "" { + return nil, nil + } + urls = []string{known} + } + client := dnsdisc.NewClient(dnsdisc.Config{}) + return client.NewIterator(urls...) +}