diff --git a/lncfg/chain.go b/lncfg/chain.go index 7eab2b9e..4feeab29 100644 --- a/lncfg/chain.go +++ b/lncfg/chain.go @@ -26,6 +26,7 @@ type Chain struct { BaseFee lnwire.MilliSatoshi `long:"basefee" description:"The base fee in millisatoshi we will charge for forwarding payments on our channels"` FeeRate lnwire.MilliSatoshi `long:"feerate" description:"The fee rate used when forwarding payments on our channels. The total fee charged is basefee + (amount * feerate / 1000000), where amount is the forwarded amount."` TimeLockDelta uint32 `long:"timelockdelta" description:"The CLTV delta we will subtract from a forwarded HTLC's timelock value"` + DNSSeeds []string `long:"dnsseed" description:"The seed DNS server(s) to use for initial peer discovery. Must be specified as a '[,]' tuple where the SOA address is needed for DNS resolution through Tor but is optional for clearnet users. Multiple tuples can be specified, will overwrite the default seed servers."` } // Validate performs validation on our chain config. diff --git a/sample-lnd.conf b/sample-lnd.conf index f2bc5486..2cc665db 100644 --- a/sample-lnd.conf +++ b/sample-lnd.conf @@ -417,6 +417,21 @@ bitcoin.node=btcd ; The CLTV delta we will subtract from a forwarded HTLC's timelock value. ; bitcoin.timelockdelta=40 +; The seed DNS server(s) to use for initial peer discovery. Must be specified as +; a '[,]' tuple where the SOA address is needed +; for DNS resolution through Tor but is optional for clearnet users. Multiple +; tuples can be specified, will overwrite the default seed servers. +; The default seed servers are: +; mainnet: +; bitcoin.dnsseed=nodes.lightning.directory,soa.nodes.lightning.directory +; bitcoin.dnsseed=lseed.bitcoinstats.com +; testnet: +; bitcoin.dnsseed=test.nodes.lightning.directory,soa.nodes.lightning.directory +; +; Example for custom DNS servers: +; bitcoin.dnsseed=seed1.test.lightning +; bitcoin.dnsseed=seed2.test.lightning,soa.seed2.test.lightning + ; Used to help identify ourselves to other bitcoin peers (default: neutrino). ; neutrino.useragentname=neutrino @@ -589,6 +604,18 @@ litecoin.node=ltcd ; The CLTV delta we will subtract from a forwarded HTLC's timelock value. ; litecoin.timelockdelta=576 +; The seed DNS server(s) to use for initial peer discovery. Must be specified as +; a '[,]' tuple where the SOA address is needed +; for DNS resolution through Tor but is optional for clearnet users. Multiple +; tuples can be specified, will overwrite the default seed servers. +; The default seed servers are: +; mainnet: +; litecoin.dnsseed=ltc.nodes.lightning.directory,soa.nodes.lightning.directory +; +; Example for custom DNS servers: +; litecoin.dnsseed=seed1.test-ltc.lightning +; litecoin.dnsseed=seed2.test-ltc.lightning,soa.seed2.test-ltc.lightning + [Ltcd] ; The base directory that contains the node's data, logs, configuration file, diff --git a/server.go b/server.go index a20d6cf5..25f6d650 100644 --- a/server.go +++ b/server.go @@ -13,6 +13,7 @@ import ( "path/filepath" "regexp" "strconv" + "strings" "sync" "sync/atomic" "time" @@ -1536,6 +1537,57 @@ func (s *server) Start() error { return } + // setSeedList is a helper function that turns multiple DNS seed + // server tuples from the command line or config file into the + // data structure we need and does a basic formal sanity check + // in the process. + setSeedList := func(tuples []string, genesisHash chainhash.Hash) { + if len(tuples) == 0 { + return + } + + result := make([][2]string, len(tuples)) + for idx, tuple := range tuples { + tuple = strings.TrimSpace(tuple) + if len(tuple) == 0 { + return + } + + servers := strings.Split(tuple, ",") + if len(servers) > 2 || len(servers) == 0 { + srvrLog.Warnf("Ignoring invalid DNS "+ + "seed tuple: %v", servers) + return + } + + copy(result[idx][:], servers) + } + + chainreg.ChainDNSSeeds[genesisHash] = result + } + + // Let users overwrite the DNS seed nodes. We only allow them + // for bitcoin mainnet/testnet and litecoin mainnet, all other + // combinations will just be ignored. + if s.cfg.Bitcoin.Active && s.cfg.Bitcoin.MainNet { + setSeedList( + s.cfg.Bitcoin.DNSSeeds, + chainreg.BitcoinMainnetGenesis, + ) + } + if s.cfg.Bitcoin.Active && s.cfg.Bitcoin.TestNet3 { + setSeedList( + s.cfg.Bitcoin.DNSSeeds, + chainreg.BitcoinTestnetGenesis, + ) + } + if s.cfg.Litecoin.Active && s.cfg.Litecoin.MainNet { + setSeedList( + s.cfg.Litecoin.DNSSeeds, + chainreg.LitecoinMainnetGenesis, + ) + } + // If network bootstrapping hasn't been disabled, then we'll // configure the set of active bootstrappers, and launch a // dedicated goroutine to maintain a set of persistent