本文整理汇总了Golang中github.com/btcsuite/btcutil.Block.Sha方法的典型用法代码示例。如果您正苦于以下问题:Golang Block.Sha方法的具体用法?Golang Block.Sha怎么用?Golang Block.Sha使用的例子?那么恭喜您, 这里精选的方法代码示例或许可以为您提供帮助。您也可以进一步了解该方法所在类github.com/btcsuite/btcutil.Block
的用法示例。
在下文中一共展示了Block.Sha方法的15个代码示例,这些例子默认根据受欢迎程度排序。您可以为喜欢或者感觉有用的代码点赞,您的评价将有助于系统推荐出更棒的Golang代码示例。
示例1: dbIndexDisconnectBlock
// dbIndexDisconnectBlock removes all of the index entries associated with the
// given block using the provided indexer and updates the tip of the indexer
// accordingly. An error will be returned if the current tip for the indexer is
// not the passed block.
func dbIndexDisconnectBlock(dbTx database.Tx, indexer Indexer, block *btcutil.Block, view *blockchain.UtxoViewpoint) error {
// Assert that the block being disconnected is the current tip of the
// index.
idxKey := indexer.Key()
curTipHash, _, err := dbFetchIndexerTip(dbTx, idxKey)
if err != nil {
return err
}
if !curTipHash.IsEqual(block.Sha()) {
return AssertError(fmt.Sprintf("dbIndexDisconnectBlock must "+
"be called with the block at the current index tip "+
"(%s, tip %s, block %s)", indexer.Name(),
curTipHash, block.Sha()))
}
// Notify the indexer with the disconnected block so it can remove all
// of the appropriate entries.
if err := indexer.DisconnectBlock(dbTx, block, view); err != nil {
return err
}
// Update the current index tip.
prevHash := &block.MsgBlock().Header.PrevBlock
return dbPutIndexerTip(dbTx, idxKey, prevHash, block.Height()-1)
}
示例2: ConnectBlock
// ConnectBlock is invoked by the index manager when a new block has been
// connected to the main chain. This indexer adds a mapping for each address
// the transactions in the block involve.
//
// This is part of the Indexer interface.
func (idx *AddrIndex) ConnectBlock(dbTx database.Tx, block *btcutil.Block, view *blockchain.UtxoViewpoint) error {
// The offset and length of the transactions within the serialized
// block.
txLocs, err := block.TxLoc()
if err != nil {
return err
}
// Get the internal block ID associated with the block.
blockID, err := dbFetchBlockIDByHash(dbTx, block.Sha())
if err != nil {
return err
}
// Build all of the address to transaction mappings in a local map.
addrsToTxns := make(writeIndexData)
idx.indexBlock(addrsToTxns, block, view)
// Add all of the index entries for each address.
addrIdxBucket := dbTx.Metadata().Bucket(addrIndexKey)
for addrKey, txIdxs := range addrsToTxns {
for _, txIdx := range txIdxs {
err := dbPutAddrIndexEntry(addrIdxBucket, addrKey,
blockID, txLocs[txIdx])
if err != nil {
return err
}
}
}
return nil
}
示例3: checkProofOfWork
// checkProofOfWork ensures the block header bits which indicate the target
// difficulty is in min/max range and that the block hash is less than the
// target difficulty as claimed.
//
//
// The flags modify the behavior of this function as follows:
// - BFNoPoWCheck: The check to ensure the block hash is less than the target
// difficulty is not performed.
func checkProofOfWork(block *btcutil.Block, powLimit *big.Int, flags BehaviorFlags) error {
// The target difficulty must be larger than zero.
target := CompactToBig(block.MsgBlock().Header.Bits)
if target.Sign() <= 0 {
str := fmt.Sprintf("block target difficulty of %064x is too low",
target)
return ruleError(ErrUnexpectedDifficulty, str)
}
// The target difficulty must be less than the maximum allowed.
if target.Cmp(powLimit) > 0 {
str := fmt.Sprintf("block target difficulty of %064x is "+
"higher than max of %064x", target, powLimit)
return ruleError(ErrUnexpectedDifficulty, str)
}
// The block hash must be less than the claimed target unless the flag
// to avoid proof of work checks is set.
if flags&BFNoPoWCheck != BFNoPoWCheck {
// The block hash must be less than the claimed target.
blockHash, err := block.Sha()
if err != nil {
return err
}
hashNum := ShaHashToBig(blockHash)
if hashNum.Cmp(target) > 0 {
str := fmt.Sprintf("block hash of %064x is higher than "+
"expected max of %064x", hashNum, target)
return ruleError(ErrHighHash, str)
}
}
return nil
}
示例4: CheckConnectBlock
// CheckConnectBlock performs several checks to confirm connecting the passed
// block to the main chain does not violate any rules. An example of some of
// the checks performed are ensuring connecting the block would not cause any
// duplicate transaction hashes for old transactions that aren't already fully
// spent, double spends, exceeding the maximum allowed signature operations
// per block, invalid values in relation to the expected block subsidy, or fail
// transaction script validation.
//
// This function is NOT safe for concurrent access.
func (b *BlockChain) CheckConnectBlock(block *btcutil.Block) error {
prevNode := b.bestChain
newNode := newBlockNode(&block.MsgBlock().Header, block.Sha(),
block.Height())
if prevNode != nil {
newNode.parent = prevNode
newNode.workSum.Add(prevNode.workSum, newNode.workSum)
}
return b.checkConnectBlock(newNode, block)
}
示例5: connectTransactions
// connectTransactions updates the view by adding all new utxos created by all
// of the transactions in the passed block, marking all utxos the transactions
// spend as spent, and setting the best hash for the view to the passed block.
// In addition, when the 'stxos' argument is not nil, it will be updated to
// append an entry for each spent txout.
func (view *UtxoViewpoint) connectTransactions(block *btcutil.Block, stxos *[]spentTxOut) error {
for _, tx := range block.Transactions() {
err := view.connectTransaction(tx, block.Height(), stxos)
if err != nil {
return err
}
}
// Update the best hash for view to include this block since all of its
// transactions have been connected.
view.SetBestHash(block.Sha())
return nil
}
示例6: DisconnectBlock
// DisconnectBlock is invoked by the index manager when a block has been
// disconnected from the main chain. This indexer removes the
// hash-to-transaction mapping for every transaction in the block.
//
// This is part of the Indexer interface.
func (idx *TxIndex) DisconnectBlock(dbTx database.Tx, block *btcutil.Block, view *blockchain.UtxoViewpoint) error {
// Remove all of the transactions in the block from the index.
if err := dbRemoveTxIndexEntries(dbTx, block); err != nil {
return err
}
// Remove the block ID index entry for the block being disconnected and
// decrement the current internal block ID to account for it.
if err := dbRemoveBlockIDIndexEntry(dbTx, block.Sha()); err != nil {
return err
}
idx.curBlockID--
return nil
}
示例7: CheckConnectBlock
// CheckConnectBlock performs several checks to confirm connecting the passed
// block to the main chain does not violate any rules. An example of some of
// the checks performed are ensuring connecting the block would not cause any
// duplicate transaction hashes for old transactions that aren't already fully
// spent, double spends, exceeding the maximum allowed signature operations
// per block, invalid values in relation to the expected block subsidy, or fail
// transaction script validation.
//
// This function is safe for concurrent access.
func (b *BlockChain) CheckConnectBlock(block *btcutil.Block) error {
b.chainLock.Lock()
defer b.chainLock.Unlock()
prevNode := b.bestNode
newNode := newBlockNode(&block.MsgBlock().Header, block.Sha(),
prevNode.height+1)
newNode.parent = prevNode
newNode.workSum.Add(prevNode.workSum, newNode.workSum)
// Leave the spent txouts entry nil in the state since the information
// is not needed and thus extra work can be avoided.
view := NewUtxoViewpoint()
view.SetBestHash(prevNode.hash)
return b.checkConnectBlock(newNode, block, view, nil)
}
示例8: addOrphanBlock
// addOrphanBlock adds the passed block (which is already determined to be
// an orphan prior calling this function) to the orphan pool. It lazily cleans
// up any expired blocks so a separate cleanup poller doesn't need to be run.
// It also imposes a maximum limit on the number of outstanding orphan
// blocks and will remove the oldest received orphan block if the limit is
// exceeded.
func (b *BlockChain) addOrphanBlock(block *btcutil.Block) {
// Remove expired orphan blocks.
for _, oBlock := range b.orphans {
if time.Now().After(oBlock.expiration) {
b.removeOrphanBlock(oBlock)
continue
}
// Update the oldest orphan block pointer so it can be discarded
// in case the orphan pool fills up.
if b.oldestOrphan == nil || oBlock.expiration.Before(b.oldestOrphan.expiration) {
b.oldestOrphan = oBlock
}
}
// Limit orphan blocks to prevent memory exhaustion.
if len(b.orphans)+1 > maxOrphanBlocks {
// Remove the oldest orphan to make room for the new one.
b.removeOrphanBlock(b.oldestOrphan)
b.oldestOrphan = nil
}
// Get the block sha. It is safe to ignore the error here since any
// errors would've been caught prior to calling this function.
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()
defer b.orphanLock.Unlock()
// Insert the block into the orphan map with an expiration time
// 1 hour from now.
expiration := time.Now().Add(time.Hour)
oBlock := &orphanBlock{
block: block,
expiration: expiration,
}
b.orphans[*blockSha] = oBlock
// Add to previous hash lookup index for faster dependency lookups.
prevHash := &block.MsgBlock().Header.PrevBlock
b.prevOrphans[*prevHash] = append(b.prevOrphans[*prevHash], oBlock)
return
}
示例9: ConnectBlock
// ConnectBlock is invoked by the index manager when a new block has been
// connected to the main chain. This indexer adds a hash-to-transaction mapping
// for every transaction in the passed block.
//
// This is part of the Indexer interface.
func (idx *TxIndex) ConnectBlock(dbTx database.Tx, block *btcutil.Block, view *blockchain.UtxoViewpoint) error {
// Increment the internal block ID to use for the block being connected
// and add all of the transactions in the block to the index.
newBlockID := idx.curBlockID + 1
if err := dbAddTxIndexEntries(dbTx, block, newBlockID); err != nil {
return err
}
// Add the new block ID index entry for the block being connected and
// update the current internal block ID accordingly.
err := dbPutBlockIDIndexEntry(dbTx, block.Sha(), newBlockID)
if err != nil {
return err
}
idx.curBlockID = newBlockID
return nil
}
示例10: submitBlock
// submitBlock submits the passed block to network after ensuring it passes all
// of the consensus validation rules.
func (m *CPUMiner) submitBlock(block *btcutil.Block) bool {
m.submitBlockLock.Lock()
defer m.submitBlockLock.Unlock()
// Ensure the block is not stale since a new block could have shown up
// while the solution was being found. Typically that condition is
// detected and all work on the stale block is halted to start work on
// a new block, but the check only happens periodically, so it is
// possible a block was found and submitted in between.
latestHash, _ := m.server.blockManager.chainState.Best()
msgBlock := block.MsgBlock()
if !msgBlock.Header.PrevBlock.IsEqual(latestHash) {
minrLog.Debugf("Block submitted via CPU miner with previous "+
"block %s is stale", msgBlock.Header.PrevBlock)
return false
}
// Process this block using the same rules as blocks coming from other
// nodes. This will in turn relay it to the network like normal.
isOrphan, err := m.server.blockManager.ProcessBlock(block, blockchain.BFNone)
if err != nil {
// Anything other than a rule violation is an unexpected error,
// so log that error as an internal error.
if _, ok := err.(blockchain.RuleError); !ok {
minrLog.Errorf("Unexpected error while processing "+
"block submitted via CPU miner: %v", err)
return false
}
minrLog.Debugf("Block submitted via CPU miner rejected: %v", err)
return false
}
if isOrphan {
minrLog.Debugf("Block submitted via CPU miner is an orphan")
return false
}
// The block was accepted.
blockSha, _ := block.Sha()
coinbaseTx := block.MsgBlock().Transactions[0].TxOut[0]
minrLog.Infof("Block submitted via CPU miner accepted (hash %s, "+
"amount %v)", blockSha, btcutil.Amount(coinbaseTx.Value))
return true
}
示例11: dbFetchSpendJournalEntry
// dbFetchSpendJournalEntry fetches the spend journal entry for the passed
// block and deserializes it into a slice of spent txout entries. The provided
// view MUST have the utxos referenced by all of the transactions available for
// the passed block since that information is required to reconstruct the spent
// txouts.
func dbFetchSpendJournalEntry(dbTx database.Tx, block *btcutil.Block, view *UtxoViewpoint) ([]spentTxOut, error) {
// Exclude the coinbase transaction since it can't spend anything.
spendBucket := dbTx.Metadata().Bucket(spendJournalBucketName)
serialized := spendBucket.Get(block.Sha()[:])
blockTxns := block.MsgBlock().Transactions[1:]
stxos, err := deserializeSpendJournalEntry(serialized, blockTxns, view)
if err != nil {
// Ensure any deserialization errors are returned as database
// corruption errors.
if isDeserializeErr(err) {
return nil, database.Error{
ErrorCode: database.ErrCorruption,
Description: fmt.Sprintf("corrupt spend "+
"information for %v: %v", block.Sha(),
err),
}
}
return nil, err
}
return stxos, nil
}
示例12: dbIndexConnectBlock
// dbIndexConnectBlock adds all of the index entries associated with the
// given block using the provided indexer and updates the tip of the indexer
// accordingly. An error will be returned if the current tip for the indexer is
// not the previous block for the passed block.
func dbIndexConnectBlock(dbTx database.Tx, indexer Indexer, block *btcutil.Block, view *blockchain.UtxoViewpoint) error {
// Assert that the block being connected properly connects to the
// current tip of the index.
idxKey := indexer.Key()
curTipHash, _, err := dbFetchIndexerTip(dbTx, idxKey)
if err != nil {
return err
}
if !curTipHash.IsEqual(&block.MsgBlock().Header.PrevBlock) {
return AssertError(fmt.Sprintf("dbIndexConnectBlock must be "+
"called with a block that extends the current index "+
"tip (%s, tip %s, block %s)", indexer.Name(),
curTipHash, block.Sha()))
}
// Notify the indexer with the connected block so it can index it.
if err := indexer.ConnectBlock(dbTx, block, view); err != nil {
return err
}
// Update the current index tip.
return dbPutIndexerTip(dbTx, idxKey, block.Sha(), block.Height())
}
示例13: IsCheckpointCandidate
// IsCheckpointCandidate returns whether or not the passed block is a good
// checkpoint candidate.
//
// The factors used to determine a good checkpoint are:
// - The block must be in the main chain
// - The block must be at least 'CheckpointConfirmations' blocks prior to the
// current end of the main chain
// - The timestamps for the blocks before and after the checkpoint must have
// timestamps which are also before and after the checkpoint, respectively
// (due to the median time allowance this is not always the case)
// - The block must not contain any strange transaction such as those with
// nonstandard scripts
//
// The intent is that candidates are reviewed by a developer to make the final
// decision and then manually added to the list of checkpoints for a network.
func (b *BlockChain) IsCheckpointCandidate(block *btcutil.Block) (bool, error) {
// Checkpoints must be enabled.
if b.noCheckpoints {
return false, fmt.Errorf("checkpoints are disabled")
}
// A checkpoint must be in the main chain.
exists, err := b.db.ExistsSha(block.Sha())
if err != nil {
return false, err
}
if !exists {
return false, nil
}
// A checkpoint must be at least CheckpointConfirmations blocks before
// the end of the main chain.
blockHeight := block.Height()
_, mainChainHeight, err := b.db.NewestSha()
if err != nil {
return false, err
}
if blockHeight > (mainChainHeight - CheckpointConfirmations) {
return false, nil
}
// Get the previous block.
prevHash := &block.MsgBlock().Header.PrevBlock
prevBlock, err := b.db.FetchBlockBySha(prevHash)
if err != nil {
return false, err
}
// Get the next block.
nextHash, err := b.db.FetchBlockShaByHeight(blockHeight + 1)
if err != nil {
return false, err
}
nextBlock, err := b.db.FetchBlockBySha(nextHash)
if err != nil {
return false, err
}
// A checkpoint must have timestamps for the block and the blocks on
// either side of it in order (due to the median time allowance this is
// not always the case).
prevTime := prevBlock.MsgBlock().Header.Timestamp
curTime := block.MsgBlock().Header.Timestamp
nextTime := nextBlock.MsgBlock().Header.Timestamp
if prevTime.After(curTime) || nextTime.Before(curTime) {
return false, nil
}
// A checkpoint must have transactions that only contain standard
// scripts.
for _, tx := range block.Transactions() {
if isNonstandardTransaction(tx) {
return false, nil
}
}
return true, nil
}
示例14: connectBestChain
// connectBestChain handles connecting the passed block to the chain while
// respecting proper chain selection according to the chain with the most
// proof of work. In the typical case, the new block simply extends the main
// chain. However, it may also be extending (or creating) a side chain (fork)
// which may or may not end up becoming the main chain depending on which fork
// cumulatively has the most proof of work.
//
// The flags modify the behavior of this function as follows:
// - BFFastAdd: Avoids the call to checkConnectBlock which does several
// expensive transaction validation operations.
// - BFDryRun: Prevents the block from being connected and avoids modifying the
// state of the memory chain index. Also, any log messages related to
// modifying the state are avoided.
func (b *BlockChain) connectBestChain(node *blockNode, block *btcutil.Block, flags BehaviorFlags) error {
fastAdd := flags&BFFastAdd == BFFastAdd
dryRun := flags&BFDryRun == BFDryRun
// We haven't selected a best chain yet or we are extending the main
// (best) chain with a new block. This is the most common case.
if b.bestChain == nil || node.parent.hash.IsEqual(b.bestChain.hash) {
// Perform several checks to verify the block can be connected
// to the main chain (including whatever reorganization might
// be necessary to get this node to the main chain) without
// violating any rules and without actually connecting the
// block.
if !fastAdd {
err := b.checkConnectBlock(node, block)
if err != nil {
return err
}
}
// Don't connect the block if performing a dry run.
if dryRun {
return nil
}
// Connect the block to the main chain.
err := b.connectBlock(node, block)
if err != nil {
return err
}
// Connect the parent node to this node.
if node.parent != nil {
node.parent.children = append(node.parent.children, node)
}
return nil
}
if fastAdd {
log.Warnf("fastAdd set in the side chain case? %v\n",
block.Sha())
}
// We're extending (or creating) a side chain which may or may not
// become the main chain, but in either case we need the block stored
// for future processing, so add the block to the side chain holding
// cache.
if !dryRun {
log.Debugf("Adding block %v to side chain cache", node.hash)
}
b.blockCache[*node.hash] = block
b.index[*node.hash] = node
// Connect the parent node to this node.
node.inMainChain = false
node.parent.children = append(node.parent.children, node)
// Remove the block from the side chain cache and disconnect it from the
// parent node when the function returns when running in dry run mode.
if dryRun {
defer func() {
children := node.parent.children
children = removeChildNode(children, node)
node.parent.children = children
delete(b.index, *node.hash)
delete(b.blockCache, *node.hash)
}()
}
// We're extending (or creating) a side chain, but the cumulative
// work for this new side chain is not enough to make it the new chain.
if node.workSum.Cmp(b.bestChain.workSum) <= 0 {
// Skip Logging info when the dry run flag is set.
if dryRun {
return nil
}
// Find the fork point.
fork := node
for ; fork.parent != nil; fork = fork.parent {
if fork.inMainChain {
break
}
}
// Log information about how the block is forking the chain.
if fork.hash.IsEqual(node.parent.hash) {
//.........这里部分代码省略.........
示例15: IsCheckpointCandidate
// IsCheckpointCandidate returns whether or not the passed block is a good
// checkpoint candidate.
//
// The factors used to determine a good checkpoint are:
// - The block must be in the main chain
// - The block must be at least 'CheckpointConfirmations' blocks prior to the
// current end of the main chain
// - The timestamps for the blocks before and after the checkpoint must have
// timestamps which are also before and after the checkpoint, respectively
// (due to the median time allowance this is not always the case)
// - The block must not contain any strange transaction such as those with
// nonstandard scripts
//
// The intent is that candidates are reviewed by a developer to make the final
// decision and then manually added to the list of checkpoints for a network.
//
// This function is safe for concurrent access.
func (b *BlockChain) IsCheckpointCandidate(block *btcutil.Block) (bool, error) {
b.chainLock.RLock()
defer b.chainLock.RUnlock()
// Checkpoints must be enabled.
if b.noCheckpoints {
return false, fmt.Errorf("checkpoints are disabled")
}
var isCandidate bool
err := b.db.View(func(dbTx database.Tx) error {
// A checkpoint must be in the main chain.
blockHeight, err := dbFetchHeightByHash(dbTx, block.Sha())
if err != nil {
// Only return an error if it's not due to the block not
// being in the main chain.
if !isNotInMainChainErr(err) {
return err
}
return nil
}
// Ensure the height of the passed block and the entry for the
// block in the main chain match. This should always be the
// case unless the caller provided an invalid block.
if blockHeight != block.Height() {
return fmt.Errorf("passed block height of %d does not "+
"match the main chain height of %d",
block.Height(), blockHeight)
}
// A checkpoint must be at least CheckpointConfirmations blocks
// before the end of the main chain.
mainChainHeight := b.bestNode.height
if blockHeight > (mainChainHeight - CheckpointConfirmations) {
return nil
}
// Get the previous block header.
prevHash := &block.MsgBlock().Header.PrevBlock
prevHeader, err := dbFetchHeaderByHash(dbTx, prevHash)
if err != nil {
return err
}
// Get the next block header.
nextHeader, err := dbFetchHeaderByHeight(dbTx, blockHeight+1)
if err != nil {
return err
}
// A checkpoint must have timestamps for the block and the
// blocks on either side of it in order (due to the median time
// allowance this is not always the case).
prevTime := prevHeader.Timestamp
curTime := block.MsgBlock().Header.Timestamp
nextTime := nextHeader.Timestamp
if prevTime.After(curTime) || nextTime.Before(curTime) {
return nil
}
// A checkpoint must have transactions that only contain
// standard scripts.
for _, tx := range block.Transactions() {
if isNonstandardTransaction(tx) {
return nil
}
}
// All of the checks passed, so the block is a candidate.
isCandidate = true
return nil
})
return isCandidate, err
}