From b08fc05390aece83a35639298662a390d3c18c4b Mon Sep 17 00:00:00 2001 From: "Johan T. Halseth" Date: Tue, 27 Mar 2018 13:50:24 +0200 Subject: [PATCH 1/2] chainntnfs/btcd: move NotifySpent to after recording the outpoint This commit moves the call to the btcd backend to start watching an outpoint for spentness to after we have recorded the outpoint in our list of clients. This is done to avoid a race that could occur if btcd quicly sent a spend notification before we had been able to record it in our map, essentially losing it. --- chainntnfs/btcdnotify/btcd.go | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/chainntnfs/btcdnotify/btcd.go b/chainntnfs/btcdnotify/btcd.go index 2f77e308b..a93726e24 100644 --- a/chainntnfs/btcdnotify/btcd.go +++ b/chainntnfs/btcdnotify/btcd.go @@ -508,10 +508,6 @@ type spendCancel struct { func (b *BtcdNotifier) RegisterSpendNtfn(outpoint *wire.OutPoint, _ uint32) (*chainntnfs.SpendEvent, error) { - if err := b.chainConn.NotifySpent([]*wire.OutPoint{outpoint}); err != nil { - return nil, err - } - ntfn := &spendNotification{ targetOutpoint: outpoint, spendChan: make(chan *chainntnfs.SpendDetail, 1), @@ -524,6 +520,10 @@ func (b *BtcdNotifier) RegisterSpendNtfn(outpoint *wire.OutPoint, case b.notificationRegistry <- ntfn: } + if err := b.chainConn.NotifySpent([]*wire.OutPoint{outpoint}); err != nil { + return nil, err + } + // The following conditional checks to ensure that when a spend notification // is registered, the output hasn't already been spent. If the output // is no longer in the UTXO set, the chain will be rescanned from the point From 13be19c9ec0217b779e5ef3b0b2fcd063cd28436 Mon Sep 17 00:00:00 2001 From: "Johan T. Halseth" Date: Wed, 28 Mar 2018 10:22:41 +0200 Subject: [PATCH 2/2] chainntnfs/bitcoind: move NotifySpent to after recording the outpoint This commit moves the call to the bitcoind backend to start watching an outpoint for spentness to after we have recorded the outpoint in our list of clients. This is done to avoid a race that we saw using the btcd backend, and it is probable that it can also happen using bitcoind. --- chainntnfs/bitcoindnotify/bitcoind.go | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/chainntnfs/bitcoindnotify/bitcoind.go b/chainntnfs/bitcoindnotify/bitcoind.go index 9fd15b03c..5897d06f5 100644 --- a/chainntnfs/bitcoindnotify/bitcoind.go +++ b/chainntnfs/bitcoindnotify/bitcoind.go @@ -488,10 +488,6 @@ type spendCancel struct { func (b *BitcoindNotifier) RegisterSpendNtfn(outpoint *wire.OutPoint, _ uint32) (*chainntnfs.SpendEvent, error) { - if err := b.chainConn.NotifySpent([]*wire.OutPoint{outpoint}); err != nil { - return nil, err - } - ntfn := &spendNotification{ targetOutpoint: outpoint, spendChan: make(chan *chainntnfs.SpendDetail, 1), @@ -504,6 +500,10 @@ func (b *BitcoindNotifier) RegisterSpendNtfn(outpoint *wire.OutPoint, case b.notificationRegistry <- ntfn: } + if err := b.chainConn.NotifySpent([]*wire.OutPoint{outpoint}); err != nil { + return nil, err + } + // The following conditional checks to ensure that when a spend notification // is registered, the output hasn't already been spent. If the output // is no longer in the UTXO set, the chain will be rescanned from the point