From ac83b8ae06c3e5e765a2b67284692011406856e4 Mon Sep 17 00:00:00 2001 From: Olaoluwa Osuntokun Date: Thu, 16 Mar 2017 19:45:10 -0700 Subject: [PATCH] peer: fix bug in handshake wherein RevokeAndAck would be sent first MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit This commit fixes a bug in the opening handshake between to peers. The bug would arise when on or many channels were active between a node establishing a new connection. The htlcManager goroutines will immediately attempt to extend the revocation window once they’re active. However, at this time, the init message may not yet have been sent as the two executions are in distinct goroutines. We fix this bug by manually writing the init message directly to the socket, rather than traveling through the queueHandler goroutine. With this, we ensure that the init message is _always_ sent first. --- peer.go | 24 +++++++++++------------- 1 file changed, 11 insertions(+), 13 deletions(-) diff --git a/peer.go b/peer.go index 02d76f36..8c46c986 100644 --- a/peer.go +++ b/peer.go @@ -287,18 +287,15 @@ func (p *peer) Start() error { peerLog.Tracef("peer %v starting", p) - p.wg.Add(2) - go p.queueHandler() - go p.writeHandler() - - // Exchange local and global features, the init message should be - // very first between two nodes. + // Exchange local and global features, the init message should be very + // first between two nodes. if err := p.sendInitMsg(); err != nil { return err } - // Should wait for peers to compare their feature vectors - // and only then start message exchanges. + // Before we launch any of the helper goroutines off the peer struct, + // we'll first ensure proper adherance to the p2p protocl. The init + // message MUST be sent before any other message. msg, _, err := p.readNextMessage() if err != nil { return err @@ -313,7 +310,9 @@ func (p *peer) Start() error { "must be init message") } - p.wg.Add(3) + p.wg.Add(5) + go p.queueHandler() + go p.writeHandler() go p.readHandler() go p.channelManager() go p.pingHandler() @@ -1236,16 +1235,15 @@ func (p *peer) handleInitMsg(msg *lnwire.Init) error { return nil } -// sendInitMsg sends init message to remote peer which represent our -// features local and global vectors. +// sendInitMsg sends init message to remote peer which contains our currently +// supported local and global features. func (p *peer) sendInitMsg() error { msg := lnwire.NewInitMessage( p.server.globalFeatures, p.server.localFeatures, ) - p.queueMsg(msg, nil) - return nil + return p.writeMessage(msg) } // handleDownStreamPkt processes an HTLC packet sent from the downstream HTLC