Export GetOrphanRoot.
This commit exposes GetOrphanRoot to callers. It also modifies the code to allow the function to be called in a concurrent safe manner. This allows the information to be safely obtained from multiple goroutines.
This commit is contained in:
parent
f4bae7dc41
commit
9d5f855580
2 changed files with 22 additions and 3 deletions
23
chain.go
23
chain.go
|
@ -13,6 +13,7 @@ import (
|
||||||
"github.com/conformal/btcwire"
|
"github.com/conformal/btcwire"
|
||||||
"math/big"
|
"math/big"
|
||||||
"sort"
|
"sort"
|
||||||
|
"sync"
|
||||||
"time"
|
"time"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
@ -152,6 +153,7 @@ type BlockChain struct {
|
||||||
orphans map[btcwire.ShaHash]*orphanBlock
|
orphans map[btcwire.ShaHash]*orphanBlock
|
||||||
prevOrphans map[btcwire.ShaHash][]*orphanBlock
|
prevOrphans map[btcwire.ShaHash][]*orphanBlock
|
||||||
oldestOrphan *orphanBlock
|
oldestOrphan *orphanBlock
|
||||||
|
orphanLock sync.RWMutex
|
||||||
blockCache map[btcwire.ShaHash]*btcutil.Block
|
blockCache map[btcwire.ShaHash]*btcutil.Block
|
||||||
noVerify bool
|
noVerify bool
|
||||||
noCheckpoints bool
|
noCheckpoints bool
|
||||||
|
@ -166,9 +168,16 @@ func (b *BlockChain) DisableVerify(disable bool) {
|
||||||
b.noVerify = disable
|
b.noVerify = disable
|
||||||
}
|
}
|
||||||
|
|
||||||
// getOrphanRoot returns the head of the chain for the provided hash from the
|
// GetOrphanRoot returns the head of the chain for the provided hash from the
|
||||||
// map of orphan blocks.
|
// map of orphan blocks.
|
||||||
func (b *BlockChain) getOrphanRoot(hash *btcwire.ShaHash) *btcwire.ShaHash {
|
//
|
||||||
|
// This function is safe for concurrent access.
|
||||||
|
func (b *BlockChain) GetOrphanRoot(hash *btcwire.ShaHash) *btcwire.ShaHash {
|
||||||
|
// Protect concurrent access. Using a read lock only so multiple
|
||||||
|
// readers can query without blocking each other.
|
||||||
|
b.orphanLock.RLock()
|
||||||
|
defer b.orphanLock.RUnlock()
|
||||||
|
|
||||||
// Keep looping while the parent of each orphaned block is
|
// Keep looping while the parent of each orphaned block is
|
||||||
// known and is an orphan itself.
|
// known and is an orphan itself.
|
||||||
orphanRoot := hash
|
orphanRoot := hash
|
||||||
|
@ -188,6 +197,10 @@ func (b *BlockChain) getOrphanRoot(hash *btcwire.ShaHash) *btcwire.ShaHash {
|
||||||
// removeOrphanBlock removes the passed orphan block from the orphan pool and
|
// removeOrphanBlock removes the passed orphan block from the orphan pool and
|
||||||
// previous orphan index.
|
// previous orphan index.
|
||||||
func (b *BlockChain) removeOrphanBlock(orphan *orphanBlock) {
|
func (b *BlockChain) removeOrphanBlock(orphan *orphanBlock) {
|
||||||
|
// Protect concurrent access.
|
||||||
|
b.orphanLock.Lock()
|
||||||
|
defer b.orphanLock.Unlock()
|
||||||
|
|
||||||
// Remove the orphan block from the orphan pool. It's safe to ignore
|
// Remove the orphan block from the orphan pool. It's safe to ignore
|
||||||
// the error on Sha since it's cached.
|
// the error on Sha since it's cached.
|
||||||
orphanHash, _ := orphan.block.Sha()
|
orphanHash, _ := orphan.block.Sha()
|
||||||
|
@ -249,6 +262,12 @@ func (b *BlockChain) addOrphanBlock(block *btcutil.Block) {
|
||||||
// errors would've been caught prior to calling this function.
|
// errors would've been caught prior to calling this function.
|
||||||
blockSha, _ := block.Sha()
|
blockSha, _ := block.Sha()
|
||||||
|
|
||||||
|
// Protect concurrent access. This is intentionally done here instead
|
||||||
|
// of near the top since removeOrphanBlock does its own locking and
|
||||||
|
// the range iterator is not invalidated by removing map entries.
|
||||||
|
b.orphanLock.Lock()
|
||||||
|
b.orphanLock.Unlock()
|
||||||
|
|
||||||
// Insert the block into the orphan map with an expiration time
|
// Insert the block into the orphan map with an expiration time
|
||||||
// 1 hour from now.
|
// 1 hour from now.
|
||||||
expiration := time.Now().Add(time.Hour)
|
expiration := time.Now().Add(time.Hour)
|
||||||
|
|
|
@ -151,7 +151,7 @@ func (b *BlockChain) ProcessBlock(block *btcutil.Block) error {
|
||||||
// Get the hash for the head of the orphaned block chain for
|
// Get the hash for the head of the orphaned block chain for
|
||||||
// this block and notify the caller so it can request missing
|
// this block and notify the caller so it can request missing
|
||||||
// blocks.
|
// blocks.
|
||||||
orphanRoot := b.getOrphanRoot(blockHash)
|
orphanRoot := b.GetOrphanRoot(blockHash)
|
||||||
b.sendNotification(NTOrphanBlock, orphanRoot)
|
b.sendNotification(NTOrphanBlock, orphanRoot)
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
Loading…
Add table
Reference in a new issue