Fix mempool transactions disappearing if a parent tx is confirmed.
This commit is contained in:
parent
4b7206b54f
commit
912a8d8301
2 changed files with 20 additions and 16 deletions
|
@ -1215,11 +1215,11 @@ func (b *blockManager) handleNotifyMsg(notification *blockchain.Notification) {
|
||||||
// connected block from the transaction pool. Secondly, remove any
|
// connected block from the transaction pool. Secondly, remove any
|
||||||
// transactions which are now double spends as a result of these
|
// transactions which are now double spends as a result of these
|
||||||
// new transactions. Finally, remove any transaction that is
|
// new transactions. Finally, remove any transaction that is
|
||||||
// no longer an orphan. Note that removing a transaction from
|
// no longer an orphan. Transactions which depend on a confirmed
|
||||||
// pool also removes any transactions which depend on it,
|
// transaction are NOT removed recursively because they are still
|
||||||
// recursively.
|
// valid.
|
||||||
for _, tx := range block.Transactions()[1:] {
|
for _, tx := range block.Transactions()[1:] {
|
||||||
b.server.txMemPool.RemoveTransaction(tx)
|
b.server.txMemPool.RemoveTransaction(tx, false)
|
||||||
b.server.txMemPool.RemoveDoubleSpends(tx)
|
b.server.txMemPool.RemoveDoubleSpends(tx)
|
||||||
b.server.txMemPool.RemoveOrphan(tx.Sha())
|
b.server.txMemPool.RemoveOrphan(tx.Sha())
|
||||||
b.server.txMemPool.ProcessOrphans(tx.Sha())
|
b.server.txMemPool.ProcessOrphans(tx.Sha())
|
||||||
|
@ -1261,7 +1261,7 @@ func (b *blockManager) handleNotifyMsg(notification *blockchain.Notification) {
|
||||||
// Remove the transaction and all transactions
|
// Remove the transaction and all transactions
|
||||||
// that depend on it if it wasn't accepted into
|
// that depend on it if it wasn't accepted into
|
||||||
// the transaction pool.
|
// the transaction pool.
|
||||||
b.server.txMemPool.RemoveTransaction(tx)
|
b.server.txMemPool.RemoveTransaction(tx, true)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
26
mempool.go
26
mempool.go
|
@ -398,13 +398,15 @@ func (mp *txMemPool) HaveTransaction(hash *wire.ShaHash) bool {
|
||||||
// RemoveTransaction. See the comment for RemoveTransaction for more details.
|
// RemoveTransaction. See the comment for RemoveTransaction for more details.
|
||||||
//
|
//
|
||||||
// This function MUST be called with the mempool lock held (for writes).
|
// This function MUST be called with the mempool lock held (for writes).
|
||||||
func (mp *txMemPool) removeTransaction(tx *btcutil.Tx) {
|
func (mp *txMemPool) removeTransaction(tx *btcutil.Tx, removeRedeemers bool) {
|
||||||
// Remove any transactions which rely on this one.
|
|
||||||
txHash := tx.Sha()
|
txHash := tx.Sha()
|
||||||
for i := uint32(0); i < uint32(len(tx.MsgTx().TxOut)); i++ {
|
if removeRedeemers {
|
||||||
outpoint := wire.NewOutPoint(txHash, i)
|
// Remove any transactions which rely on this one.
|
||||||
if txRedeemer, exists := mp.outpoints[*outpoint]; exists {
|
for i := uint32(0); i < uint32(len(tx.MsgTx().TxOut)); i++ {
|
||||||
mp.removeTransaction(txRedeemer)
|
outpoint := wire.NewOutPoint(txHash, i)
|
||||||
|
if txRedeemer, exists := mp.outpoints[*outpoint]; exists {
|
||||||
|
mp.removeTransaction(txRedeemer, true)
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -466,16 +468,18 @@ func (mp *txMemPool) removeScriptFromAddrIndex(pkScript []byte, tx *btcutil.Tx)
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
// RemoveTransaction removes the passed transaction and any transactions which
|
// RemoveTransaction removes the passed transaction from the mempool. If
|
||||||
// depend on it from the memory pool.
|
// removeRedeemers flag is set, any transactions that redeem outputs from the
|
||||||
|
// removed transaction will also be removed recursively from the mempool, as
|
||||||
|
// they would otherwise become orphan.
|
||||||
//
|
//
|
||||||
// This function is safe for concurrent access.
|
// This function is safe for concurrent access.
|
||||||
func (mp *txMemPool) RemoveTransaction(tx *btcutil.Tx) {
|
func (mp *txMemPool) RemoveTransaction(tx *btcutil.Tx, removeRedeemers bool) {
|
||||||
// Protect concurrent access.
|
// Protect concurrent access.
|
||||||
mp.Lock()
|
mp.Lock()
|
||||||
defer mp.Unlock()
|
defer mp.Unlock()
|
||||||
|
|
||||||
mp.removeTransaction(tx)
|
mp.removeTransaction(tx, removeRedeemers)
|
||||||
}
|
}
|
||||||
|
|
||||||
// RemoveDoubleSpends removes all transactions which spend outputs spent by the
|
// RemoveDoubleSpends removes all transactions which spend outputs spent by the
|
||||||
|
@ -493,7 +497,7 @@ func (mp *txMemPool) RemoveDoubleSpends(tx *btcutil.Tx) {
|
||||||
for _, txIn := range tx.MsgTx().TxIn {
|
for _, txIn := range tx.MsgTx().TxIn {
|
||||||
if txRedeemer, ok := mp.outpoints[txIn.PreviousOutPoint]; ok {
|
if txRedeemer, ok := mp.outpoints[txIn.PreviousOutPoint]; ok {
|
||||||
if !txRedeemer.Sha().IsEqual(tx.Sha()) {
|
if !txRedeemer.Sha().IsEqual(tx.Sha()) {
|
||||||
mp.removeTransaction(txRedeemer)
|
mp.removeTransaction(txRedeemer, true)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in a new issue