From 40f97e6c4701456ce5f6a46d4289643ef7d65be3 Mon Sep 17 00:00:00 2001 From: Wilmer Paulino Date: Tue, 31 Mar 2020 10:35:02 -0700 Subject: [PATCH] peer: send local node announcement upon establishing peer connections We'll only do so when we have at least one confirmed advertised channel with the remote peer. This ensures that our node announcement can propagate throughout the network even for nodes that were offline when we initially broadcast it. --- peer.go | 44 ++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 44 insertions(+) diff --git a/peer.go b/peer.go index df77c4fd..fd1dac55 100644 --- a/peer.go +++ b/peer.go @@ -425,6 +425,19 @@ func (p *peer) Start() error { } } + // Node announcements don't propagate very well throughout the network + // as there isn't a way to efficiently query for them through their + // timestamp, mostly affecting nodes that were offline during the time + // of broadcast. We'll resend our node announcement to the remote peer + // as a best-effort delivery such that it can also propagate to their + // peers. To ensure they can successfully process it in most cases, + // we'll only resend it as long as we have at least one confirmed + // advertised channel with the remote peer. + // + // TODO(wilmer): Remove this once we're able to query for node + // announcements through their timestamps. + p.maybeSendNodeAnn(activeChans) + return nil } @@ -688,6 +701,37 @@ func (p *peer) addLink(chanPoint *wire.OutPoint, return p.server.htlcSwitch.AddLink(link) } +// maybeSendNodeAnn sends our node announcement to the remote peer if at least +// one confirmed advertised channel exists with them. +func (p *peer) maybeSendNodeAnn(channels []*channeldb.OpenChannel) { + hasConfirmedPublicChan := false + for _, channel := range channels { + if channel.IsPending { + continue + } + if channel.ChannelFlags&lnwire.FFAnnounceChannel == 0 { + continue + } + + hasConfirmedPublicChan = true + break + } + if !hasConfirmedPublicChan { + return + } + + ourNodeAnn, err := p.server.genNodeAnnouncement(false) + if err != nil { + srvrLog.Debugf("Unable to retrieve node announcement: %v", err) + return + } + + if err := p.SendMessageLazy(false, &ourNodeAnn); err != nil { + srvrLog.Debugf("Unable to resend node announcement to %x: %v", + p.pubKeyBytes, err) + } +} + // WaitForDisconnect waits until the peer has disconnected. A peer may be // disconnected if the local or remote side terminating the connection, or an // irrecoverable protocol error has been encountered. This method will only