mirror of
https://github.com/kaspanet/kaspad.git
synced 2025-11-24 14:35:53 +00:00
Merge branch 'dev' into testnet-dnsseeder
This commit is contained in:
commit
ade36c328d
@ -159,7 +159,7 @@ func (msg *MsgTx) IsCoinBase() bool {
|
|||||||
|
|
||||||
// TxHash generates the Hash for the transaction.
|
// TxHash generates the Hash for the transaction.
|
||||||
func (msg *MsgTx) TxHash() *externalapi.DomainHash {
|
func (msg *MsgTx) TxHash() *externalapi.DomainHash {
|
||||||
return consensushashing.TransactionHash(MsgTxToDomainTransaction(msg), false)
|
return consensushashing.TransactionHash(MsgTxToDomainTransaction(msg))
|
||||||
}
|
}
|
||||||
|
|
||||||
// TxID generates the Hash for the transaction without the signature script, gas and payload fields.
|
// TxID generates the Hash for the transaction without the signature script, gas and payload fields.
|
||||||
|
|||||||
@ -133,7 +133,7 @@ func TestTx(t *testing.T) {
|
|||||||
|
|
||||||
// TestTxHash tests the ability to generate the hash of a transaction accurately.
|
// TestTxHash tests the ability to generate the hash of a transaction accurately.
|
||||||
func TestTxHashAndID(t *testing.T) {
|
func TestTxHashAndID(t *testing.T) {
|
||||||
txHash1Str := "93663e597f6c968d32d229002f76408edf30d6a0151ff679fc729812d8cb2acc"
|
txHash1Str := "b06f8b650115b5cf4d59499e10764a9312742930cb43c9b4ff6495d76f332ed7"
|
||||||
txID1Str := "e20225c3d065ee41743607ee627db44d01ef396dc9779b05b2caf55bac50e12d"
|
txID1Str := "e20225c3d065ee41743607ee627db44d01ef396dc9779b05b2caf55bac50e12d"
|
||||||
wantTxID1, err := transactionid.FromString(txID1Str)
|
wantTxID1, err := transactionid.FromString(txID1Str)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
@ -185,7 +185,7 @@ func TestTxHashAndID(t *testing.T) {
|
|||||||
spew.Sprint(tx1ID), spew.Sprint(wantTxID1))
|
spew.Sprint(tx1ID), spew.Sprint(wantTxID1))
|
||||||
}
|
}
|
||||||
|
|
||||||
hash2Str := "8dafd1bec24527d8e3b443ceb0a3b92fffc0d60026317f890b2faf5e9afc177a"
|
hash2Str := "fa16a8ce88d52ca1ff45187bbba0d33044e9f5fe309e8d0b22d4812dcf1782b7"
|
||||||
wantHash2, err := externalapi.NewDomainHashFromString(hash2Str)
|
wantHash2, err := externalapi.NewDomainHashFromString(hash2Str)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
t.Errorf("NewTxIDFromStr: %v", err)
|
t.Errorf("NewTxIDFromStr: %v", err)
|
||||||
|
|||||||
@ -25,7 +25,7 @@ func (flow *handleIBDFlow) ibdWithHeadersProof(
|
|||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
log.Infof("IBD with pruning proof from %s was unsuccessful. Deleting the staging consensus.", flow.peer)
|
log.Infof("IBD with pruning proof from %s was unsuccessful. Deleting the staging consensus. (%s)", flow.peer, err)
|
||||||
deleteStagingConsensusErr := flow.Domain().DeleteStagingConsensus()
|
deleteStagingConsensusErr := flow.Domain().DeleteStagingConsensus()
|
||||||
if deleteStagingConsensusErr != nil {
|
if deleteStagingConsensusErr != nil {
|
||||||
return deleteStagingConsensusErr
|
return deleteStagingConsensusErr
|
||||||
|
|||||||
@ -123,19 +123,9 @@ func (ctx *Context) PopulateTransactionWithVerboseData(
|
|||||||
|
|
||||||
ctx.Domain.Consensus().PopulateMass(domainTransaction)
|
ctx.Domain.Consensus().PopulateMass(domainTransaction)
|
||||||
|
|
||||||
var daaScore uint64
|
|
||||||
if domainBlockHeader != nil {
|
|
||||||
daaScore = domainBlockHeader.DAAScore()
|
|
||||||
} else {
|
|
||||||
daaScore, err = ctx.Domain.Consensus().GetVirtualDAAScore()
|
|
||||||
if err != nil {
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
transaction.VerboseData = &appmessage.RPCTransactionVerboseData{
|
transaction.VerboseData = &appmessage.RPCTransactionVerboseData{
|
||||||
TransactionID: consensushashing.TransactionID(domainTransaction).String(),
|
TransactionID: consensushashing.TransactionID(domainTransaction).String(),
|
||||||
Hash: consensushashing.TransactionHash(domainTransaction, daaScore >= ctx.Config.NetParams().HFDAAScore).String(),
|
Hash: consensushashing.TransactionHash(domainTransaction).String(),
|
||||||
Mass: domainTransaction.Mass,
|
Mass: domainTransaction.Mass,
|
||||||
}
|
}
|
||||||
if domainBlockHeader != nil {
|
if domainBlockHeader != nil {
|
||||||
|
|||||||
@ -78,6 +78,11 @@ func create(conf *createConfig) error {
|
|||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
|
err = file.TryLock()
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
err = file.Save()
|
err = file.Save()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
|
|||||||
@ -77,6 +77,11 @@ func Start(params *dagconfig.Params, listen, rpcServer string, keysFilePath stri
|
|||||||
return (errors.Wrapf(err, "Error reading keys file %s", keysFilePath))
|
return (errors.Wrapf(err, "Error reading keys file %s", keysFilePath))
|
||||||
}
|
}
|
||||||
|
|
||||||
|
err = keysFile.TryLock()
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
serverInstance := &server{
|
serverInstance := &server{
|
||||||
rpcClient: rpcClient,
|
rpcClient: rpcClient,
|
||||||
params: params,
|
params: params,
|
||||||
|
|||||||
@ -158,7 +158,7 @@ func (s *server) splitAndInputPerSplitCounts(transaction *serialization.Partiall
|
|||||||
// to calculate how much mass do all the inputs have
|
// to calculate how much mass do all the inputs have
|
||||||
transactionWithoutInputs := transaction.Tx.Clone()
|
transactionWithoutInputs := transaction.Tx.Clone()
|
||||||
transactionWithoutInputs.Inputs = []*externalapi.DomainTransactionInput{}
|
transactionWithoutInputs.Inputs = []*externalapi.DomainTransactionInput{}
|
||||||
massWithoutInputs := s.txMassCalculator.CalculateTransactionMass(transactionWithoutInputs, true)
|
massWithoutInputs := s.txMassCalculator.CalculateTransactionMass(transactionWithoutInputs)
|
||||||
|
|
||||||
massOfAllInputs := transactionMass - massWithoutInputs
|
massOfAllInputs := transactionMass - massWithoutInputs
|
||||||
|
|
||||||
@ -177,7 +177,7 @@ func (s *server) splitAndInputPerSplitCounts(transaction *serialization.Partiall
|
|||||||
return 0, 0, err
|
return 0, 0, err
|
||||||
}
|
}
|
||||||
massForEverythingExceptInputsInSplitTransaction :=
|
massForEverythingExceptInputsInSplitTransaction :=
|
||||||
s.txMassCalculator.CalculateTransactionMass(splitTransactionWithoutInputs.Tx, true)
|
s.txMassCalculator.CalculateTransactionMass(splitTransactionWithoutInputs.Tx)
|
||||||
massForInputsInSplitTransaction := mempool.MaximumStandardTransactionMass - massForEverythingExceptInputsInSplitTransaction
|
massForInputsInSplitTransaction := mempool.MaximumStandardTransactionMass - massForEverythingExceptInputsInSplitTransaction
|
||||||
|
|
||||||
inputsPerSplitCount = int(massForInputsInSplitTransaction / massPerInput)
|
inputsPerSplitCount = int(massForInputsInSplitTransaction / massPerInput)
|
||||||
@ -245,7 +245,7 @@ func (s *server) estimateMassAfterSignatures(transaction *serialization.Partiall
|
|||||||
return 0, err
|
return 0, err
|
||||||
}
|
}
|
||||||
|
|
||||||
return s.txMassCalculator.CalculateTransactionMass(transactionWithSignatures, true), nil
|
return s.txMassCalculator.CalculateTransactionMass(transactionWithSignatures), nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func (s *server) moreUTXOsForMergeTransaction(alreadySelectedUTXOs []*libkaspawallet.UTXO, requiredAmount uint64) (
|
func (s *server) moreUTXOsForMergeTransaction(alreadySelectedUTXOs []*libkaspawallet.UTXO, requiredAmount uint64) (
|
||||||
|
|||||||
@ -58,7 +58,7 @@ func TestEstimateMassAfterSignatures(t *testing.T) {
|
|||||||
t.Fatalf("ExtractTransaction: %+v", err)
|
t.Fatalf("ExtractTransaction: %+v", err)
|
||||||
}
|
}
|
||||||
|
|
||||||
actualMassAfterSignatures := serverInstance.txMassCalculator.CalculateTransactionMass(extractedSignedTx, true)
|
actualMassAfterSignatures := serverInstance.txMassCalculator.CalculateTransactionMass(extractedSignedTx)
|
||||||
|
|
||||||
if estimatedMassAfterSignatures != actualMassAfterSignatures {
|
if estimatedMassAfterSignatures != actualMassAfterSignatures {
|
||||||
t.Errorf("Estimated mass after signatures: %d but actually got %d",
|
t.Errorf("Estimated mass after signatures: %d but actually got %d",
|
||||||
|
|||||||
@ -6,6 +6,7 @@ import (
|
|||||||
"encoding/hex"
|
"encoding/hex"
|
||||||
"encoding/json"
|
"encoding/json"
|
||||||
"fmt"
|
"fmt"
|
||||||
|
"github.com/gofrs/flock"
|
||||||
"os"
|
"os"
|
||||||
"path/filepath"
|
"path/filepath"
|
||||||
"runtime"
|
"runtime"
|
||||||
@ -400,3 +401,28 @@ func decryptMnemonic(numThreads uint8, encryptedPrivateKey *EncryptedMnemonic, p
|
|||||||
|
|
||||||
return string(decrypted), nil
|
return string(decrypted), nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// flockMap is a map that holds all lock file handlers. This map guarantees that
|
||||||
|
// the associated locked file handler will never get cleaned by the GC, because
|
||||||
|
// once they are cleaned the associated file will be unlocked.
|
||||||
|
var flockMap = make(map[string]*flock.Flock)
|
||||||
|
|
||||||
|
// TryLock tries to acquire an exclusive lock for the file.
|
||||||
|
func (d *File) TryLock() error {
|
||||||
|
if _, ok := flockMap[d.path]; ok {
|
||||||
|
return errors.Errorf("file %s is already locked", d.path)
|
||||||
|
}
|
||||||
|
|
||||||
|
lockFile := flock.New(d.path + ".lock")
|
||||||
|
flockMap[d.path] = lockFile
|
||||||
|
|
||||||
|
success, err := lockFile.TryLock()
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
if !success {
|
||||||
|
return errors.Errorf("%s is locked and cannot be used. Make sure that no other active wallet command is using it.", d.path)
|
||||||
|
}
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|||||||
@ -3,6 +3,8 @@ package main
|
|||||||
import (
|
import (
|
||||||
"context"
|
"context"
|
||||||
"fmt"
|
"fmt"
|
||||||
|
"os"
|
||||||
|
"strings"
|
||||||
|
|
||||||
"github.com/kaspanet/kaspad/cmd/kaspawallet/daemon/client"
|
"github.com/kaspanet/kaspad/cmd/kaspawallet/daemon/client"
|
||||||
"github.com/kaspanet/kaspad/cmd/kaspawallet/daemon/pb"
|
"github.com/kaspanet/kaspad/cmd/kaspawallet/daemon/pb"
|
||||||
@ -49,6 +51,10 @@ func send(conf *sendConfig) error {
|
|||||||
}
|
}
|
||||||
mnemonics, err := keysFile.DecryptMnemonics(conf.Password)
|
mnemonics, err := keysFile.DecryptMnemonics(conf.Password)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
|
if strings.Contains(err.Error(), "message authentication failed") {
|
||||||
|
fmt.Fprintf(os.Stderr, "Password decryption failed. Sometimes this is a result of not "+
|
||||||
|
"specifying the same keys file used by the wallet daemon process.\n")
|
||||||
|
}
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@ -184,7 +184,7 @@ func createSplitTransactionsWithSchnorrPrivteKey(
|
|||||||
ScriptPublicKey: scriptPublicKey,
|
ScriptPublicKey: scriptPublicKey,
|
||||||
}
|
}
|
||||||
|
|
||||||
if massCalculater.CalculateTransactionMass(currentTx, true)+extraMass >= mempool.MaximumStandardTransactionMass {
|
if massCalculater.CalculateTransactionMass(currentTx)+extraMass >= mempool.MaximumStandardTransactionMass {
|
||||||
|
|
||||||
//in this loop we assume a transaction with one input and one output cannot violate max transaction mass, hence a sanity check.
|
//in this loop we assume a transaction with one input and one output cannot violate max transaction mass, hence a sanity check.
|
||||||
if len(currentTx.Inputs) == 1 {
|
if len(currentTx.Inputs) == 1 {
|
||||||
|
|||||||
@ -21,7 +21,6 @@ type consensus struct {
|
|||||||
|
|
||||||
genesisBlock *externalapi.DomainBlock
|
genesisBlock *externalapi.DomainBlock
|
||||||
genesisHash *externalapi.DomainHash
|
genesisHash *externalapi.DomainHash
|
||||||
hfDAAScore uint64
|
|
||||||
|
|
||||||
expectedDAAWindowDurationInMilliseconds int64
|
expectedDAAWindowDurationInMilliseconds int64
|
||||||
|
|
||||||
@ -918,7 +917,7 @@ func (s *consensus) EstimateNetworkHashesPerSecond(startHash *externalapi.Domain
|
|||||||
}
|
}
|
||||||
|
|
||||||
func (s *consensus) PopulateMass(transaction *externalapi.DomainTransaction) {
|
func (s *consensus) PopulateMass(transaction *externalapi.DomainTransaction) {
|
||||||
s.transactionValidator.PopulateMass(transaction, s.hfDAAScore)
|
s.transactionValidator.PopulateMass(transaction)
|
||||||
}
|
}
|
||||||
|
|
||||||
func (s *consensus) ResolveVirtual(progressReportCallback func(uint64, uint64)) error {
|
func (s *consensus) ResolveVirtual(progressReportCallback func(uint64, uint64)) error {
|
||||||
|
|||||||
@ -216,7 +216,6 @@ func (f *factory) NewConsensus(config *Config, db infrastructuredatabase.Databas
|
|||||||
transactionValidator := transactionvalidator.New(config.BlockCoinbaseMaturity,
|
transactionValidator := transactionvalidator.New(config.BlockCoinbaseMaturity,
|
||||||
config.EnableNonNativeSubnetworks,
|
config.EnableNonNativeSubnetworks,
|
||||||
config.MaxCoinbasePayloadLength,
|
config.MaxCoinbasePayloadLength,
|
||||||
config.HFDAAScore,
|
|
||||||
config.K,
|
config.K,
|
||||||
config.CoinbasePayloadScriptPublicKeyMaxLength,
|
config.CoinbasePayloadScriptPublicKeyMaxLength,
|
||||||
dbManager,
|
dbManager,
|
||||||
@ -247,7 +246,6 @@ func (f *factory) NewConsensus(config *Config, db infrastructuredatabase.Databas
|
|||||||
config.GenesisHash,
|
config.GenesisHash,
|
||||||
config.DeflationaryPhaseDaaScore,
|
config.DeflationaryPhaseDaaScore,
|
||||||
config.DeflationaryPhaseBaseSubsidy,
|
config.DeflationaryPhaseBaseSubsidy,
|
||||||
config.HFDAAScore,
|
|
||||||
|
|
||||||
dagTraversalManager,
|
dagTraversalManager,
|
||||||
ghostdagDataStore,
|
ghostdagDataStore,
|
||||||
@ -284,7 +282,6 @@ func (f *factory) NewConsensus(config *Config, db infrastructuredatabase.Databas
|
|||||||
config.MaxBlockParents,
|
config.MaxBlockParents,
|
||||||
config.MergeSetSizeLimit,
|
config.MergeSetSizeLimit,
|
||||||
genesisHash,
|
genesisHash,
|
||||||
config.HFDAAScore,
|
|
||||||
|
|
||||||
ghostdagManager,
|
ghostdagManager,
|
||||||
dagTopologyManager,
|
dagTopologyManager,
|
||||||
@ -353,7 +350,6 @@ func (f *factory) NewConsensus(config *Config, db infrastructuredatabase.Databas
|
|||||||
config.TimestampDeviationTolerance,
|
config.TimestampDeviationTolerance,
|
||||||
config.TargetTimePerBlock,
|
config.TargetTimePerBlock,
|
||||||
config.MaxBlockLevel,
|
config.MaxBlockLevel,
|
||||||
config.HFDAAScore,
|
|
||||||
|
|
||||||
dbManager,
|
dbManager,
|
||||||
difficultyManager,
|
difficultyManager,
|
||||||
@ -401,7 +397,6 @@ func (f *factory) NewConsensus(config *Config, db infrastructuredatabase.Databas
|
|||||||
blockBuilder := blockbuilder.New(
|
blockBuilder := blockbuilder.New(
|
||||||
dbManager,
|
dbManager,
|
||||||
genesisHash,
|
genesisHash,
|
||||||
config.HFDAAScore,
|
|
||||||
|
|
||||||
difficultyManager,
|
difficultyManager,
|
||||||
pastMedianTimeManager,
|
pastMedianTimeManager,
|
||||||
@ -483,7 +478,6 @@ func (f *factory) NewConsensus(config *Config, db infrastructuredatabase.Databas
|
|||||||
|
|
||||||
genesisBlock: config.GenesisBlock,
|
genesisBlock: config.GenesisBlock,
|
||||||
genesisHash: config.GenesisHash,
|
genesisHash: config.GenesisHash,
|
||||||
hfDAAScore: config.HFDAAScore,
|
|
||||||
|
|
||||||
expectedDAAWindowDurationInMilliseconds: config.TargetTimePerBlock.Milliseconds() *
|
expectedDAAWindowDurationInMilliseconds: config.TargetTimePerBlock.Milliseconds() *
|
||||||
int64(config.DifficultyAdjustmentWindowSize),
|
int64(config.DifficultyAdjustmentWindowSize),
|
||||||
|
|||||||
@ -8,5 +8,5 @@ type CoinbaseManager interface {
|
|||||||
ExpectedCoinbaseTransaction(stagingArea *StagingArea, blockHash *externalapi.DomainHash,
|
ExpectedCoinbaseTransaction(stagingArea *StagingArea, blockHash *externalapi.DomainHash,
|
||||||
coinbaseData *externalapi.DomainCoinbaseData) (expectedTransaction *externalapi.DomainTransaction, hasRedReward bool, err error)
|
coinbaseData *externalapi.DomainCoinbaseData) (expectedTransaction *externalapi.DomainTransaction, hasRedReward bool, err error)
|
||||||
CalcBlockSubsidy(stagingArea *StagingArea, blockHash *externalapi.DomainHash) (uint64, error)
|
CalcBlockSubsidy(stagingArea *StagingArea, blockHash *externalapi.DomainHash) (uint64, error)
|
||||||
ExtractCoinbaseDataBlueScoreAndSubsidy(coinbaseTx *externalapi.DomainTransaction, postHF bool) (blueScore uint64, coinbaseData *externalapi.DomainCoinbaseData, subsidy uint64, err error)
|
ExtractCoinbaseDataBlueScoreAndSubsidy(coinbaseTx *externalapi.DomainTransaction) (blueScore uint64, coinbaseData *externalapi.DomainCoinbaseData, subsidy uint64, err error)
|
||||||
}
|
}
|
||||||
|
|||||||
@ -12,5 +12,5 @@ type TransactionValidator interface {
|
|||||||
povBlockHash *externalapi.DomainHash, povBlockPastMedianTime int64) error
|
povBlockHash *externalapi.DomainHash, povBlockPastMedianTime int64) error
|
||||||
ValidateTransactionInContextAndPopulateFee(stagingArea *StagingArea,
|
ValidateTransactionInContextAndPopulateFee(stagingArea *StagingArea,
|
||||||
tx *externalapi.DomainTransaction, povBlockHash *externalapi.DomainHash) error
|
tx *externalapi.DomainTransaction, povBlockHash *externalapi.DomainHash) error
|
||||||
PopulateMass(transaction *externalapi.DomainTransaction, daaScore uint64)
|
PopulateMass(transaction *externalapi.DomainTransaction)
|
||||||
}
|
}
|
||||||
|
|||||||
@ -20,7 +20,6 @@ import (
|
|||||||
type blockBuilder struct {
|
type blockBuilder struct {
|
||||||
databaseContext model.DBManager
|
databaseContext model.DBManager
|
||||||
genesisHash *externalapi.DomainHash
|
genesisHash *externalapi.DomainHash
|
||||||
hfDAAScore uint64
|
|
||||||
|
|
||||||
difficultyManager model.DifficultyManager
|
difficultyManager model.DifficultyManager
|
||||||
pastMedianTimeManager model.PastMedianTimeManager
|
pastMedianTimeManager model.PastMedianTimeManager
|
||||||
@ -43,7 +42,6 @@ type blockBuilder struct {
|
|||||||
func New(
|
func New(
|
||||||
databaseContext model.DBManager,
|
databaseContext model.DBManager,
|
||||||
genesisHash *externalapi.DomainHash,
|
genesisHash *externalapi.DomainHash,
|
||||||
hfDAAScore uint64,
|
|
||||||
|
|
||||||
difficultyManager model.DifficultyManager,
|
difficultyManager model.DifficultyManager,
|
||||||
pastMedianTimeManager model.PastMedianTimeManager,
|
pastMedianTimeManager model.PastMedianTimeManager,
|
||||||
@ -65,7 +63,6 @@ func New(
|
|||||||
return &blockBuilder{
|
return &blockBuilder{
|
||||||
databaseContext: databaseContext,
|
databaseContext: databaseContext,
|
||||||
genesisHash: genesisHash,
|
genesisHash: genesisHash,
|
||||||
hfDAAScore: hfDAAScore,
|
|
||||||
|
|
||||||
difficultyManager: difficultyManager,
|
difficultyManager: difficultyManager,
|
||||||
pastMedianTimeManager: pastMedianTimeManager,
|
pastMedianTimeManager: pastMedianTimeManager,
|
||||||
@ -209,7 +206,7 @@ func (bb *blockBuilder) buildHeader(stagingArea *model.StagingArea, transactions
|
|||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
hashMerkleRoot := bb.newBlockHashMerkleRoot(transactions, daaScore >= bb.hfDAAScore)
|
hashMerkleRoot := bb.newBlockHashMerkleRoot(transactions)
|
||||||
acceptedIDMerkleRoot, err := bb.newBlockAcceptedIDMerkleRoot(stagingArea)
|
acceptedIDMerkleRoot, err := bb.newBlockAcceptedIDMerkleRoot(stagingArea)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
@ -282,8 +279,8 @@ func (bb *blockBuilder) newBlockDifficulty(stagingArea *model.StagingArea) (uint
|
|||||||
return bb.difficultyManager.RequiredDifficulty(stagingArea, model.VirtualBlockHash)
|
return bb.difficultyManager.RequiredDifficulty(stagingArea, model.VirtualBlockHash)
|
||||||
}
|
}
|
||||||
|
|
||||||
func (bb *blockBuilder) newBlockHashMerkleRoot(transactions []*externalapi.DomainTransaction, postHF bool) *externalapi.DomainHash {
|
func (bb *blockBuilder) newBlockHashMerkleRoot(transactions []*externalapi.DomainTransaction) *externalapi.DomainHash {
|
||||||
return merkle.CalculateHashMerkleRoot(transactions, postHF)
|
return merkle.CalculateHashMerkleRoot(transactions)
|
||||||
}
|
}
|
||||||
|
|
||||||
func (bb *blockBuilder) newBlockAcceptedIDMerkleRoot(stagingArea *model.StagingArea) (*externalapi.DomainHash, error) {
|
func (bb *blockBuilder) newBlockAcceptedIDMerkleRoot(stagingArea *model.StagingArea) (*externalapi.DomainHash, error) {
|
||||||
|
|||||||
@ -76,7 +76,7 @@ func (bb *testBlockBuilder) buildUTXOInvalidHeader(stagingArea *model.StagingAre
|
|||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
hashMerkleRoot := bb.newBlockHashMerkleRoot(transactions, daaScore >= bb.hfDAAScore)
|
hashMerkleRoot := bb.newBlockHashMerkleRoot(transactions)
|
||||||
|
|
||||||
pruningPoint, err := bb.newBlockPruningPoint(stagingArea, tempBlockHash)
|
pruningPoint, err := bb.newBlockPruningPoint(stagingArea, tempBlockHash)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
@ -120,7 +120,7 @@ func (bb *testBlockBuilder) buildHeaderWithParents(stagingArea *model.StagingAre
|
|||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
hashMerkleRoot := bb.newBlockHashMerkleRoot(transactions, daaScore >= bb.hfDAAScore)
|
hashMerkleRoot := bb.newBlockHashMerkleRoot(transactions)
|
||||||
acceptedIDMerkleRoot, err := bb.calculateAcceptedIDMerkleRoot(acceptanceData)
|
acceptedIDMerkleRoot, err := bb.calculateAcceptedIDMerkleRoot(acceptanceData)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
|
|||||||
@ -94,7 +94,7 @@ func TestBlockStatus(t *testing.T) {
|
|||||||
invalidBlock.Header = blockheader.NewImmutableBlockHeader(
|
invalidBlock.Header = blockheader.NewImmutableBlockHeader(
|
||||||
disqualifiedBlock.Header.Version(),
|
disqualifiedBlock.Header.Version(),
|
||||||
disqualifiedBlock.Header.Parents(),
|
disqualifiedBlock.Header.Parents(),
|
||||||
merkle.CalculateHashMerkleRoot(invalidBlock.Transactions, invalidBlock.Header.DAAScore() >= consensusConfig.HFDAAScore),
|
merkle.CalculateHashMerkleRoot(invalidBlock.Transactions),
|
||||||
disqualifiedBlock.Header.AcceptedIDMerkleRoot(),
|
disqualifiedBlock.Header.AcceptedIDMerkleRoot(),
|
||||||
disqualifiedBlock.Header.UTXOCommitment(),
|
disqualifiedBlock.Header.UTXOCommitment(),
|
||||||
disqualifiedBlock.Header.TimeInMilliseconds(),
|
disqualifiedBlock.Header.TimeInMilliseconds(),
|
||||||
|
|||||||
@ -187,7 +187,7 @@ func (v *blockValidator) checkCoinbaseSubsidy(
|
|||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
_, _, subsidy, err := v.coinbaseManager.ExtractCoinbaseDataBlueScoreAndSubsidy(block.Transactions[transactionhelper.CoinbaseTransactionIndex], block.Header.DAAScore() >= v.hfDAAScore)
|
_, _, subsidy, err := v.coinbaseManager.ExtractCoinbaseDataBlueScoreAndSubsidy(block.Transactions[transactionhelper.CoinbaseTransactionIndex])
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|||||||
@ -5,7 +5,6 @@ import (
|
|||||||
"github.com/kaspanet/kaspad/domain/consensus/model/externalapi"
|
"github.com/kaspanet/kaspad/domain/consensus/model/externalapi"
|
||||||
"github.com/kaspanet/kaspad/domain/consensus/ruleerrors"
|
"github.com/kaspanet/kaspad/domain/consensus/ruleerrors"
|
||||||
"github.com/kaspanet/kaspad/domain/consensus/utils/consensushashing"
|
"github.com/kaspanet/kaspad/domain/consensus/utils/consensushashing"
|
||||||
"github.com/kaspanet/kaspad/domain/consensus/utils/constants"
|
|
||||||
"github.com/kaspanet/kaspad/domain/consensus/utils/merkle"
|
"github.com/kaspanet/kaspad/domain/consensus/utils/merkle"
|
||||||
"github.com/kaspanet/kaspad/domain/consensus/utils/subnetworks"
|
"github.com/kaspanet/kaspad/domain/consensus/utils/subnetworks"
|
||||||
"github.com/kaspanet/kaspad/domain/consensus/utils/transactionhelper"
|
"github.com/kaspanet/kaspad/domain/consensus/utils/transactionhelper"
|
||||||
@ -89,21 +88,11 @@ func (v *blockValidator) ValidateBodyInIsolation(stagingArea *model.StagingArea,
|
|||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
if block.Header.DAAScore() < v.hfDAAScore {
|
|
||||||
totalInputs := 0
|
|
||||||
for _, tx := range block.Transactions {
|
|
||||||
totalInputs += len(tx.Inputs)
|
|
||||||
if totalInputs > constants.MaxBlockInputsPreHF {
|
|
||||||
return errors.Wrapf(ruleerrors.ErrOverMaxBlockInputsPreHF, "block has more than %d inputs", constants.MaxBlockInputsPreHF)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func (v *blockValidator) checkCoinbaseBlueScore(block *externalapi.DomainBlock) error {
|
func (v *blockValidator) checkCoinbaseBlueScore(block *externalapi.DomainBlock) error {
|
||||||
coinbaseBlueScore, _, _, err := v.coinbaseManager.ExtractCoinbaseDataBlueScoreAndSubsidy(block.Transactions[transactionhelper.CoinbaseTransactionIndex], block.Header.DAAScore() >= v.hfDAAScore)
|
coinbaseBlueScore, _, _, err := v.coinbaseManager.ExtractCoinbaseDataBlueScoreAndSubsidy(block.Transactions[transactionhelper.CoinbaseTransactionIndex])
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
@ -162,7 +151,7 @@ func (v *blockValidator) checkTransactionsInIsolation(block *externalapi.DomainB
|
|||||||
}
|
}
|
||||||
|
|
||||||
func (v *blockValidator) checkBlockHashMerkleRoot(block *externalapi.DomainBlock) error {
|
func (v *blockValidator) checkBlockHashMerkleRoot(block *externalapi.DomainBlock) error {
|
||||||
calculatedHashMerkleRoot := merkle.CalculateHashMerkleRoot(block.Transactions, block.Header.DAAScore() >= v.hfDAAScore)
|
calculatedHashMerkleRoot := merkle.CalculateHashMerkleRoot(block.Transactions)
|
||||||
if !block.Header.HashMerkleRoot().Equal(calculatedHashMerkleRoot) {
|
if !block.Header.HashMerkleRoot().Equal(calculatedHashMerkleRoot) {
|
||||||
return errors.Wrapf(ruleerrors.ErrBadMerkleRoot, "block hash merkle root is invalid - block "+
|
return errors.Wrapf(ruleerrors.ErrBadMerkleRoot, "block hash merkle root is invalid - block "+
|
||||||
"header indicates %s, but calculated value is %s",
|
"header indicates %s, but calculated value is %s",
|
||||||
@ -232,7 +221,7 @@ func (v *blockValidator) validateGasLimit(block *externalapi.DomainBlock) error
|
|||||||
func (v *blockValidator) checkBlockMass(block *externalapi.DomainBlock) error {
|
func (v *blockValidator) checkBlockMass(block *externalapi.DomainBlock) error {
|
||||||
mass := uint64(0)
|
mass := uint64(0)
|
||||||
for _, transaction := range block.Transactions {
|
for _, transaction := range block.Transactions {
|
||||||
v.transactionValidator.PopulateMass(transaction, block.Header.DAAScore())
|
v.transactionValidator.PopulateMass(transaction)
|
||||||
|
|
||||||
massBefore := mass
|
massBefore := mass
|
||||||
mass += transaction.Mass
|
mass += transaction.Mass
|
||||||
|
|||||||
@ -34,7 +34,6 @@ func TestBlockValidator_ValidateBodyInIsolation(t *testing.T) {
|
|||||||
CheckFirstBlockTransactionIsCoinbase,
|
CheckFirstBlockTransactionIsCoinbase,
|
||||||
}
|
}
|
||||||
testutils.ForAllNets(t, true, func(t *testing.T, consensusConfig *consensus.Config) {
|
testutils.ForAllNets(t, true, func(t *testing.T, consensusConfig *consensus.Config) {
|
||||||
consensusConfig.HFDAAScore = 10
|
|
||||||
tc, teardown, err := consensus.NewFactory().NewTestConsensus(consensusConfig, "TestChainedTransactions")
|
tc, teardown, err := consensus.NewFactory().NewTestConsensus(consensusConfig, "TestChainedTransactions")
|
||||||
if err != nil {
|
if err != nil {
|
||||||
t.Fatalf("Error setting up consensus: %+v", err)
|
t.Fatalf("Error setting up consensus: %+v", err)
|
||||||
@ -170,10 +169,10 @@ var unOrderedParentsBlock = externalapi.DomainBlock{
|
|||||||
}),
|
}),
|
||||||
}},
|
}},
|
||||||
externalapi.NewDomainHashFromByteArray(&[externalapi.DomainHashSize]byte{
|
externalapi.NewDomainHashFromByteArray(&[externalapi.DomainHashSize]byte{
|
||||||
0x31, 0x33, 0x37, 0x72, 0x5c, 0xde, 0x1c, 0xdf,
|
0x7e, 0xe2, 0x10, 0x4e, 0x21, 0x2f, 0x2a, 0xb1,
|
||||||
0xf5, 0x9f, 0xde, 0x16, 0x74, 0xbf, 0x0c, 0x64,
|
0x7d, 0x22, 0xf5, 0xe8, 0xa0, 0x98, 0xef, 0x53,
|
||||||
0x37, 0x40, 0x49, 0xdf, 0x02, 0x05, 0xca, 0x6d,
|
0x83, 0xae, 0x59, 0x1f, 0x83, 0xf3, 0x78, 0x5d,
|
||||||
0x52, 0x23, 0x6f, 0xc2, 0x2b, 0xec, 0xad, 0x42,
|
0x30, 0xae, 0x3e, 0xb3, 0x06, 0x08, 0x6f, 0x79,
|
||||||
}),
|
}),
|
||||||
externalapi.NewDomainHashFromByteArray(&[externalapi.DomainHashSize]byte{
|
externalapi.NewDomainHashFromByteArray(&[externalapi.DomainHashSize]byte{
|
||||||
0x80, 0xf7, 0x00, 0xe3, 0x16, 0x3d, 0x04, 0x95,
|
0x80, 0xf7, 0x00, 0xe3, 0x16, 0x3d, 0x04, 0x95,
|
||||||
@ -203,20 +202,7 @@ var unOrderedParentsBlock = externalapi.DomainBlock{
|
|||||||
Transactions: []*externalapi.DomainTransaction{
|
Transactions: []*externalapi.DomainTransaction{
|
||||||
{
|
{
|
||||||
Version: 0,
|
Version: 0,
|
||||||
Inputs: []*externalapi.DomainTransactionInput{
|
Inputs: nil,
|
||||||
{
|
|
||||||
PreviousOutpoint: externalapi.DomainOutpoint{
|
|
||||||
TransactionID: *externalapi.NewDomainTransactionIDFromByteArray(&[externalapi.DomainHashSize]byte{}),
|
|
||||||
Index: 0xffffffff,
|
|
||||||
},
|
|
||||||
SignatureScript: []byte{
|
|
||||||
0x02, 0x10, 0x27, 0x08, 0xac, 0x29, 0x2f, 0x2f,
|
|
||||||
0xcf, 0x70, 0xb0, 0x7e, 0x0b, 0x2f, 0x50, 0x32,
|
|
||||||
0x53, 0x48, 0x2f, 0x62, 0x74, 0x63, 0x64, 0x2f,
|
|
||||||
},
|
|
||||||
Sequence: math.MaxUint64,
|
|
||||||
},
|
|
||||||
},
|
|
||||||
Outputs: []*externalapi.DomainTransactionOutput{
|
Outputs: []*externalapi.DomainTransactionOutput{
|
||||||
{
|
{
|
||||||
Value: 0x12a05f200, // 5000000000
|
Value: 0x12a05f200, // 5000000000
|
||||||
@ -447,10 +433,10 @@ var exampleValidBlock = externalapi.DomainBlock{
|
|||||||
}),
|
}),
|
||||||
}},
|
}},
|
||||||
externalapi.NewDomainHashFromByteArray(&[externalapi.DomainHashSize]byte{
|
externalapi.NewDomainHashFromByteArray(&[externalapi.DomainHashSize]byte{
|
||||||
0x86, 0x8b, 0x73, 0xcd, 0x20, 0x51, 0x23, 0x60,
|
0x46, 0xec, 0xf4, 0x5b, 0xe3, 0xba, 0xca, 0x34,
|
||||||
0xea, 0x62, 0x99, 0x9b, 0x87, 0xf6, 0xdd, 0x8d,
|
0x9d, 0xfe, 0x8a, 0x78, 0xde, 0xaf, 0x05, 0x3b,
|
||||||
0xa4, 0x0b, 0xd7, 0xcf, 0xc6, 0x32, 0x38, 0xee,
|
0x0a, 0xa6, 0xd5, 0x38, 0x97, 0x4d, 0xa5, 0x0f,
|
||||||
0xd9, 0x68, 0x72, 0x1f, 0xa2, 0x51, 0xe4, 0x28,
|
0xd6, 0xef, 0xb4, 0xd2, 0x66, 0xbc, 0x8d, 0x21,
|
||||||
}),
|
}),
|
||||||
externalapi.NewDomainHashFromByteArray(&[externalapi.DomainHashSize]byte{
|
externalapi.NewDomainHashFromByteArray(&[externalapi.DomainHashSize]byte{
|
||||||
0x8a, 0xb7, 0xd6, 0x73, 0x1b, 0xe6, 0xc5, 0xd3,
|
0x8a, 0xb7, 0xd6, 0x73, 0x1b, 0xe6, 0xc5, 0xd3,
|
||||||
@ -475,21 +461,7 @@ var exampleValidBlock = externalapi.DomainBlock{
|
|||||||
Transactions: []*externalapi.DomainTransaction{
|
Transactions: []*externalapi.DomainTransaction{
|
||||||
{
|
{
|
||||||
Version: 0,
|
Version: 0,
|
||||||
Inputs: []*externalapi.DomainTransactionInput{
|
Inputs: nil,
|
||||||
{
|
|
||||||
PreviousOutpoint: externalapi.DomainOutpoint{
|
|
||||||
TransactionID: *externalapi.NewDomainTransactionIDFromByteArray(&[externalapi.DomainHashSize]byte{
|
|
||||||
0x9b, 0x22, 0x59, 0x44, 0x66, 0xf0, 0xbe, 0x50,
|
|
||||||
0x7c, 0x1c, 0x8a, 0xf6, 0x06, 0x27, 0xe6, 0x33,
|
|
||||||
0x38, 0x7e, 0xd1, 0xd5, 0x8c, 0x42, 0x59, 0x1a,
|
|
||||||
0x31, 0xac, 0x9a, 0xa6, 0x2e, 0xd5, 0x2b, 0x0f,
|
|
||||||
}),
|
|
||||||
Index: 0xffffffff,
|
|
||||||
},
|
|
||||||
SignatureScript: nil,
|
|
||||||
Sequence: math.MaxUint64,
|
|
||||||
},
|
|
||||||
},
|
|
||||||
Outputs: []*externalapi.DomainTransactionOutput{
|
Outputs: []*externalapi.DomainTransactionOutput{
|
||||||
{
|
{
|
||||||
Value: 0x12a05f200, // 5000000000
|
Value: 0x12a05f200, // 5000000000
|
||||||
@ -752,10 +724,10 @@ var blockWithWrongTxOrder = externalapi.DomainBlock{
|
|||||||
}),
|
}),
|
||||||
}},
|
}},
|
||||||
externalapi.NewDomainHashFromByteArray(&[externalapi.DomainHashSize]byte{
|
externalapi.NewDomainHashFromByteArray(&[externalapi.DomainHashSize]byte{
|
||||||
0x7b, 0x25, 0x8b, 0xfa, 0xfb, 0x49, 0xe4, 0x94,
|
0xd5, 0xd2, 0x32, 0xe4, 0xbe, 0x9c, 0x33, 0xbd,
|
||||||
0x48, 0x2c, 0xf9, 0x74, 0xdd, 0xad, 0x9d, 0x6f,
|
0xf1, 0x0a, 0xd2, 0x9d, 0x0c, 0xbd, 0xe5, 0xae,
|
||||||
0x98, 0x8f, 0xfb, 0x01, 0x9d, 0x49, 0x29, 0xbe,
|
0xcb, 0x1a, 0xf9, 0x5a, 0x3e, 0xfb, 0xf3, 0xc7,
|
||||||
0x3c, 0xec, 0x90, 0xfe, 0xa5, 0x0c, 0xaf, 0x6b,
|
0x2b, 0x4d, 0x10, 0xa6, 0xbd, 0x5f, 0x07, 0xe7,
|
||||||
}),
|
}),
|
||||||
externalapi.NewDomainHashFromByteArray(&[externalapi.DomainHashSize]byte{
|
externalapi.NewDomainHashFromByteArray(&[externalapi.DomainHashSize]byte{
|
||||||
0xa0, 0x69, 0x2d, 0x16, 0xb5, 0xd7, 0xe4, 0xf3,
|
0xa0, 0x69, 0x2d, 0x16, 0xb5, 0xd7, 0xe4, 0xf3,
|
||||||
@ -1310,7 +1282,7 @@ func initBlockWithFirstTransactionDifferentThanCoinbase(consensusConfig *consens
|
|||||||
Header: blockheader.NewImmutableBlockHeader(
|
Header: blockheader.NewImmutableBlockHeader(
|
||||||
constants.BlockVersion,
|
constants.BlockVersion,
|
||||||
[]externalapi.BlockLevelParents{[]*externalapi.DomainHash{consensusConfig.GenesisHash}},
|
[]externalapi.BlockLevelParents{[]*externalapi.DomainHash{consensusConfig.GenesisHash}},
|
||||||
merkle.CalculateHashMerkleRoot([]*externalapi.DomainTransaction{tx}, consensusConfig.HFDAAScore == 0),
|
merkle.CalculateHashMerkleRoot([]*externalapi.DomainTransaction{tx}),
|
||||||
&externalapi.DomainHash{},
|
&externalapi.DomainHash{},
|
||||||
externalapi.NewDomainHashFromByteArray(&[externalapi.DomainHashSize]byte{
|
externalapi.NewDomainHashFromByteArray(&[externalapi.DomainHashSize]byte{
|
||||||
0x80, 0xf7, 0x00, 0xe3, 0x16, 0x3d, 0x04, 0x95,
|
0x80, 0xf7, 0x00, 0xe3, 0x16, 0x3d, 0x04, 0x95,
|
||||||
|
|||||||
@ -25,7 +25,6 @@ type blockValidator struct {
|
|||||||
timestampDeviationTolerance int
|
timestampDeviationTolerance int
|
||||||
targetTimePerBlock time.Duration
|
targetTimePerBlock time.Duration
|
||||||
maxBlockLevel int
|
maxBlockLevel int
|
||||||
hfDAAScore uint64
|
|
||||||
|
|
||||||
databaseContext model.DBReader
|
databaseContext model.DBReader
|
||||||
difficultyManager model.DifficultyManager
|
difficultyManager model.DifficultyManager
|
||||||
@ -65,7 +64,6 @@ func New(powMax *big.Int,
|
|||||||
timestampDeviationTolerance int,
|
timestampDeviationTolerance int,
|
||||||
targetTimePerBlock time.Duration,
|
targetTimePerBlock time.Duration,
|
||||||
maxBlockLevel int,
|
maxBlockLevel int,
|
||||||
hfDAAScore uint64,
|
|
||||||
|
|
||||||
databaseContext model.DBReader,
|
databaseContext model.DBReader,
|
||||||
|
|
||||||
@ -105,7 +103,6 @@ func New(powMax *big.Int,
|
|||||||
mergeSetSizeLimit: mergeSetSizeLimit,
|
mergeSetSizeLimit: mergeSetSizeLimit,
|
||||||
maxBlockParents: maxBlockParents,
|
maxBlockParents: maxBlockParents,
|
||||||
maxBlockLevel: maxBlockLevel,
|
maxBlockLevel: maxBlockLevel,
|
||||||
hfDAAScore: hfDAAScore,
|
|
||||||
|
|
||||||
timestampDeviationTolerance: timestampDeviationTolerance,
|
timestampDeviationTolerance: timestampDeviationTolerance,
|
||||||
targetTimePerBlock: targetTimePerBlock,
|
targetTimePerBlock: targetTimePerBlock,
|
||||||
|
|||||||
@ -181,7 +181,7 @@ func TestCheckParentHeadersExist(t *testing.T) {
|
|||||||
invalidBlock.Header = blockheader.NewImmutableBlockHeader(
|
invalidBlock.Header = blockheader.NewImmutableBlockHeader(
|
||||||
invalidBlock.Header.Version(),
|
invalidBlock.Header.Version(),
|
||||||
invalidBlock.Header.Parents(),
|
invalidBlock.Header.Parents(),
|
||||||
merkle.CalculateHashMerkleRoot(invalidBlock.Transactions, orphanBlock.Header.DAAScore() >= consensusConfig.HFDAAScore),
|
merkle.CalculateHashMerkleRoot(invalidBlock.Transactions),
|
||||||
orphanBlock.Header.AcceptedIDMerkleRoot(),
|
orphanBlock.Header.AcceptedIDMerkleRoot(),
|
||||||
orphanBlock.Header.UTXOCommitment(),
|
orphanBlock.Header.UTXOCommitment(),
|
||||||
orphanBlock.Header.TimeInMilliseconds(),
|
orphanBlock.Header.TimeInMilliseconds(),
|
||||||
|
|||||||
@ -19,7 +19,6 @@ type coinbaseManager struct {
|
|||||||
genesisHash *externalapi.DomainHash
|
genesisHash *externalapi.DomainHash
|
||||||
deflationaryPhaseDaaScore uint64
|
deflationaryPhaseDaaScore uint64
|
||||||
deflationaryPhaseBaseSubsidy uint64
|
deflationaryPhaseBaseSubsidy uint64
|
||||||
hfDAAScore uint64
|
|
||||||
|
|
||||||
databaseContext model.DBReader
|
databaseContext model.DBReader
|
||||||
dagTraversalManager model.DAGTraversalManager
|
dagTraversalManager model.DAGTraversalManager
|
||||||
@ -128,8 +127,7 @@ func (c *coinbaseManager) coinbaseOutputForBlueBlock(stagingArea *model.StagingA
|
|||||||
}
|
}
|
||||||
|
|
||||||
// the ScriptPublicKey for the coinbase is parsed from the coinbase payload
|
// the ScriptPublicKey for the coinbase is parsed from the coinbase payload
|
||||||
// We pass postHF=true since it only affects the deserialization of the subsidy, which is not used in this context.
|
_, coinbaseData, _, err := c.ExtractCoinbaseDataBlueScoreAndSubsidy(blockAcceptanceData.TransactionAcceptanceData[0].Transaction)
|
||||||
_, coinbaseData, _, err := c.ExtractCoinbaseDataBlueScoreAndSubsidy(blockAcceptanceData.TransactionAcceptanceData[0].Transaction, true)
|
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, false, err
|
return nil, false, err
|
||||||
}
|
}
|
||||||
@ -267,7 +265,7 @@ func (c *coinbaseManager) calcMergedBlockReward(stagingArea *model.StagingArea,
|
|||||||
return 0, err
|
return 0, err
|
||||||
}
|
}
|
||||||
|
|
||||||
_, _, subsidy, err := c.ExtractCoinbaseDataBlueScoreAndSubsidy(block.Transactions[transactionhelper.CoinbaseTransactionIndex], block.Header.DAAScore() >= c.hfDAAScore)
|
_, _, subsidy, err := c.ExtractCoinbaseDataBlueScoreAndSubsidy(block.Transactions[transactionhelper.CoinbaseTransactionIndex])
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return 0, err
|
return 0, err
|
||||||
}
|
}
|
||||||
@ -285,7 +283,6 @@ func New(
|
|||||||
genesisHash *externalapi.DomainHash,
|
genesisHash *externalapi.DomainHash,
|
||||||
deflationaryPhaseDaaScore uint64,
|
deflationaryPhaseDaaScore uint64,
|
||||||
deflationaryPhaseBaseSubsidy uint64,
|
deflationaryPhaseBaseSubsidy uint64,
|
||||||
hfDAAScore uint64,
|
|
||||||
|
|
||||||
dagTraversalManager model.DAGTraversalManager,
|
dagTraversalManager model.DAGTraversalManager,
|
||||||
ghostdagDataStore model.GHOSTDAGDataStore,
|
ghostdagDataStore model.GHOSTDAGDataStore,
|
||||||
@ -304,7 +301,6 @@ func New(
|
|||||||
genesisHash: genesisHash,
|
genesisHash: genesisHash,
|
||||||
deflationaryPhaseDaaScore: deflationaryPhaseDaaScore,
|
deflationaryPhaseDaaScore: deflationaryPhaseDaaScore,
|
||||||
deflationaryPhaseBaseSubsidy: deflationaryPhaseBaseSubsidy,
|
deflationaryPhaseBaseSubsidy: deflationaryPhaseBaseSubsidy,
|
||||||
hfDAAScore: hfDAAScore,
|
|
||||||
|
|
||||||
dagTraversalManager: dagTraversalManager,
|
dagTraversalManager: dagTraversalManager,
|
||||||
ghostdagDataStore: ghostdagDataStore,
|
ghostdagDataStore: ghostdagDataStore,
|
||||||
|
|||||||
@ -20,17 +20,14 @@ func TestExtractCoinbaseDataBlueScoreAndSubsidy(t *testing.T) {
|
|||||||
tests := []struct {
|
tests := []struct {
|
||||||
name string
|
name string
|
||||||
scriptPublicKeyVersion uint16
|
scriptPublicKeyVersion uint16
|
||||||
expectedScriptPublicKeyVersionBeforeHF uint16
|
|
||||||
}{
|
}{
|
||||||
{
|
{
|
||||||
name: "below 255",
|
name: "below 255",
|
||||||
scriptPublicKeyVersion: 100,
|
scriptPublicKeyVersion: 100,
|
||||||
expectedScriptPublicKeyVersionBeforeHF: 100,
|
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
name: "above 255",
|
name: "above 255",
|
||||||
scriptPublicKeyVersion: 300,
|
scriptPublicKeyVersion: 300,
|
||||||
expectedScriptPublicKeyVersionBeforeHF: 44,
|
|
||||||
},
|
},
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -46,16 +43,7 @@ func TestExtractCoinbaseDataBlueScoreAndSubsidy(t *testing.T) {
|
|||||||
t.Fatal(err)
|
t.Fatal(err)
|
||||||
}
|
}
|
||||||
|
|
||||||
_, cbData, _, err := tc.CoinbaseManager().ExtractCoinbaseDataBlueScoreAndSubsidy(coinbaseTx, false)
|
_, cbData, _, err := tc.CoinbaseManager().ExtractCoinbaseDataBlueScoreAndSubsidy(coinbaseTx)
|
||||||
if err != nil {
|
|
||||||
t.Fatal(err)
|
|
||||||
}
|
|
||||||
|
|
||||||
if cbData.ScriptPublicKey.Version != test.expectedScriptPublicKeyVersionBeforeHF {
|
|
||||||
t.Fatalf("test %s pre HF expected %d but got %d", test.name, test.expectedScriptPublicKeyVersionBeforeHF, cbData.ScriptPublicKey.Version)
|
|
||||||
}
|
|
||||||
|
|
||||||
_, cbData, _, err = tc.CoinbaseManager().ExtractCoinbaseDataBlueScoreAndSubsidy(coinbaseTx, true)
|
|
||||||
if err != nil {
|
if err != nil {
|
||||||
t.Fatal(err)
|
t.Fatal(err)
|
||||||
}
|
}
|
||||||
|
|||||||
@ -21,7 +21,6 @@ func TestCalcDeflationaryPeriodBlockSubsidy(t *testing.T) {
|
|||||||
&externalapi.DomainHash{},
|
&externalapi.DomainHash{},
|
||||||
deflationaryPhaseDaaScore,
|
deflationaryPhaseDaaScore,
|
||||||
deflationaryPhaseBaseSubsidy,
|
deflationaryPhaseBaseSubsidy,
|
||||||
0,
|
|
||||||
nil,
|
nil,
|
||||||
nil,
|
nil,
|
||||||
nil,
|
nil,
|
||||||
@ -97,7 +96,6 @@ func TestBuildSubsidyTable(t *testing.T) {
|
|||||||
&externalapi.DomainHash{},
|
&externalapi.DomainHash{},
|
||||||
0,
|
0,
|
||||||
deflationaryPhaseBaseSubsidy,
|
deflationaryPhaseBaseSubsidy,
|
||||||
0,
|
|
||||||
nil,
|
nil,
|
||||||
nil,
|
nil,
|
||||||
nil,
|
nil,
|
||||||
|
|||||||
@ -61,7 +61,7 @@ func ModifyCoinbasePayload(payload []byte, coinbaseData *externalapi.DomainCoinb
|
|||||||
}
|
}
|
||||||
|
|
||||||
// ExtractCoinbaseDataBlueScoreAndSubsidy deserializes the coinbase payload to its component (scriptPubKey, extra data, and subsidy).
|
// ExtractCoinbaseDataBlueScoreAndSubsidy deserializes the coinbase payload to its component (scriptPubKey, extra data, and subsidy).
|
||||||
func (c *coinbaseManager) ExtractCoinbaseDataBlueScoreAndSubsidy(coinbaseTx *externalapi.DomainTransaction, postHF bool) (
|
func (c *coinbaseManager) ExtractCoinbaseDataBlueScoreAndSubsidy(coinbaseTx *externalapi.DomainTransaction) (
|
||||||
blueScore uint64, coinbaseData *externalapi.DomainCoinbaseData, subsidy uint64, err error) {
|
blueScore uint64, coinbaseData *externalapi.DomainCoinbaseData, subsidy uint64, err error) {
|
||||||
|
|
||||||
minLength := uint64Len + lengthOfSubsidy + lengthOfVersionScriptPubKey + lengthOfScriptPubKeyLength
|
minLength := uint64Len + lengthOfSubsidy + lengthOfVersionScriptPubKey + lengthOfScriptPubKeyLength
|
||||||
@ -73,10 +73,7 @@ func (c *coinbaseManager) ExtractCoinbaseDataBlueScoreAndSubsidy(coinbaseTx *ext
|
|||||||
blueScore = binary.LittleEndian.Uint64(coinbaseTx.Payload[:uint64Len])
|
blueScore = binary.LittleEndian.Uint64(coinbaseTx.Payload[:uint64Len])
|
||||||
subsidy = binary.LittleEndian.Uint64(coinbaseTx.Payload[uint64Len:])
|
subsidy = binary.LittleEndian.Uint64(coinbaseTx.Payload[uint64Len:])
|
||||||
|
|
||||||
scriptPubKeyVersion := uint16(coinbaseTx.Payload[uint64Len+lengthOfSubsidy])
|
scriptPubKeyVersion := binary.LittleEndian.Uint16(coinbaseTx.Payload[uint64Len+lengthOfSubsidy : uint64Len+lengthOfSubsidy+uint16Len])
|
||||||
if postHF {
|
|
||||||
scriptPubKeyVersion = binary.LittleEndian.Uint16(coinbaseTx.Payload[uint64Len+lengthOfSubsidy : uint64Len+lengthOfSubsidy+uint16Len])
|
|
||||||
}
|
|
||||||
|
|
||||||
scriptPubKeyScriptLength := coinbaseTx.Payload[uint64Len+lengthOfSubsidy+lengthOfVersionScriptPubKey]
|
scriptPubKeyScriptLength := coinbaseTx.Payload[uint64Len+lengthOfSubsidy+lengthOfVersionScriptPubKey]
|
||||||
|
|
||||||
|
|||||||
@ -10,7 +10,6 @@ type consensusStateManager struct {
|
|||||||
maxBlockParents externalapi.KType
|
maxBlockParents externalapi.KType
|
||||||
mergeSetSizeLimit uint64
|
mergeSetSizeLimit uint64
|
||||||
genesisHash *externalapi.DomainHash
|
genesisHash *externalapi.DomainHash
|
||||||
hfDAAScore uint64
|
|
||||||
databaseContext model.DBManager
|
databaseContext model.DBManager
|
||||||
|
|
||||||
ghostdagManager model.GHOSTDAGManager
|
ghostdagManager model.GHOSTDAGManager
|
||||||
@ -45,7 +44,6 @@ func New(
|
|||||||
maxBlockParents externalapi.KType,
|
maxBlockParents externalapi.KType,
|
||||||
mergeSetSizeLimit uint64,
|
mergeSetSizeLimit uint64,
|
||||||
genesisHash *externalapi.DomainHash,
|
genesisHash *externalapi.DomainHash,
|
||||||
hfDAAScore uint64,
|
|
||||||
|
|
||||||
ghostdagManager model.GHOSTDAGManager,
|
ghostdagManager model.GHOSTDAGManager,
|
||||||
dagTopologyManager model.DAGTopologyManager,
|
dagTopologyManager model.DAGTopologyManager,
|
||||||
@ -74,7 +72,6 @@ func New(
|
|||||||
maxBlockParents: maxBlockParents,
|
maxBlockParents: maxBlockParents,
|
||||||
mergeSetSizeLimit: mergeSetSizeLimit,
|
mergeSetSizeLimit: mergeSetSizeLimit,
|
||||||
genesisHash: genesisHash,
|
genesisHash: genesisHash,
|
||||||
hfDAAScore: hfDAAScore,
|
|
||||||
|
|
||||||
databaseContext: databaseContext,
|
databaseContext: databaseContext,
|
||||||
|
|
||||||
|
|||||||
@ -39,7 +39,7 @@ func (csm *consensusStateManager) verifyUTXO(stagingArea *model.StagingArea, blo
|
|||||||
coinbaseTransaction := block.Transactions[0]
|
coinbaseTransaction := block.Transactions[0]
|
||||||
log.Debugf("Validating coinbase transaction %s for block %s",
|
log.Debugf("Validating coinbase transaction %s for block %s",
|
||||||
consensushashing.TransactionID(coinbaseTransaction), blockHash)
|
consensushashing.TransactionID(coinbaseTransaction), blockHash)
|
||||||
err = csm.validateCoinbaseTransaction(stagingArea, blockHash, coinbaseTransaction, block.Header.DAAScore() >= csm.hfDAAScore)
|
err = csm.validateCoinbaseTransaction(stagingArea, blockHash, coinbaseTransaction)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
@ -153,14 +153,14 @@ func calculateAcceptedIDMerkleRoot(multiblockAcceptanceData externalapi.Acceptan
|
|||||||
}
|
}
|
||||||
|
|
||||||
func (csm *consensusStateManager) validateCoinbaseTransaction(stagingArea *model.StagingArea,
|
func (csm *consensusStateManager) validateCoinbaseTransaction(stagingArea *model.StagingArea,
|
||||||
blockHash *externalapi.DomainHash, coinbaseTransaction *externalapi.DomainTransaction, postHF bool) error {
|
blockHash *externalapi.DomainHash, coinbaseTransaction *externalapi.DomainTransaction) error {
|
||||||
|
|
||||||
log.Tracef("validateCoinbaseTransaction start for block %s", blockHash)
|
log.Tracef("validateCoinbaseTransaction start for block %s", blockHash)
|
||||||
defer log.Tracef("validateCoinbaseTransaction end for block %s", blockHash)
|
defer log.Tracef("validateCoinbaseTransaction end for block %s", blockHash)
|
||||||
|
|
||||||
log.Tracef("Extracting coinbase data for coinbase transaction %s in block %s",
|
log.Tracef("Extracting coinbase data for coinbase transaction %s in block %s",
|
||||||
consensushashing.TransactionID(coinbaseTransaction), blockHash)
|
consensushashing.TransactionID(coinbaseTransaction), blockHash)
|
||||||
_, coinbaseData, _, err := csm.coinbaseManager.ExtractCoinbaseDataBlueScoreAndSubsidy(coinbaseTransaction, postHF)
|
_, coinbaseData, _, err := csm.coinbaseManager.ExtractCoinbaseDataBlueScoreAndSubsidy(coinbaseTransaction)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
@ -172,8 +172,8 @@ func (csm *consensusStateManager) validateCoinbaseTransaction(stagingArea *model
|
|||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
coinbaseTransactionHash := consensushashing.TransactionHash(coinbaseTransaction, true)
|
coinbaseTransactionHash := consensushashing.TransactionHash(coinbaseTransaction)
|
||||||
expectedCoinbaseTransactionHash := consensushashing.TransactionHash(expectedCoinbaseTransaction, true)
|
expectedCoinbaseTransactionHash := consensushashing.TransactionHash(expectedCoinbaseTransaction)
|
||||||
log.Tracef("given coinbase hash: %s, expected coinbase hash: %s",
|
log.Tracef("given coinbase hash: %s, expected coinbase hash: %s",
|
||||||
coinbaseTransactionHash, expectedCoinbaseTransactionHash)
|
coinbaseTransactionHash, expectedCoinbaseTransactionHash)
|
||||||
|
|
||||||
|
|||||||
@ -5,9 +5,9 @@ import (
|
|||||||
)
|
)
|
||||||
|
|
||||||
// PopulateMass calculates and populates the mass of the given transaction
|
// PopulateMass calculates and populates the mass of the given transaction
|
||||||
func (v *transactionValidator) PopulateMass(transaction *externalapi.DomainTransaction, daaScore uint64) {
|
func (v *transactionValidator) PopulateMass(transaction *externalapi.DomainTransaction) {
|
||||||
if transaction.Mass != 0 {
|
if transaction.Mass != 0 {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
transaction.Mass = v.txMassCalculator.CalculateTransactionMass(transaction, daaScore >= v.hfDAAScore)
|
transaction.Mass = v.txMassCalculator.CalculateTransactionMass(transaction)
|
||||||
}
|
}
|
||||||
|
|||||||
@ -90,12 +90,7 @@ func (v *transactionValidator) ValidateTransactionInContextAndPopulateFee(stagin
|
|||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
daaScore, err := v.daaBlocksStore.DAAScore(v.databaseContext, stagingArea, povBlockHash)
|
err = v.validateTransactionSigOpCounts(tx)
|
||||||
if err != nil {
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
|
|
||||||
err = v.validateTransactionSigOpCounts(tx, daaScore >= v.hfDAAScore)
|
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
@ -346,7 +341,7 @@ func (v *transactionValidator) sequenceLockActive(sequenceLock *sequenceLock, bl
|
|||||||
return true
|
return true
|
||||||
}
|
}
|
||||||
|
|
||||||
func (v *transactionValidator) validateTransactionSigOpCounts(tx *externalapi.DomainTransaction, postHF bool) error {
|
func (v *transactionValidator) validateTransactionSigOpCounts(tx *externalapi.DomainTransaction) error {
|
||||||
for i, input := range tx.Inputs {
|
for i, input := range tx.Inputs {
|
||||||
utxoEntry := input.UTXOEntry
|
utxoEntry := input.UTXOEntry
|
||||||
|
|
||||||
@ -356,20 +351,11 @@ func (v *transactionValidator) validateTransactionSigOpCounts(tx *externalapi.Do
|
|||||||
isP2SH := txscript.IsPayToScriptHash(utxoEntry.ScriptPublicKey())
|
isP2SH := txscript.IsPayToScriptHash(utxoEntry.ScriptPublicKey())
|
||||||
sigOpCount := txscript.GetPreciseSigOpCount(sigScript, utxoEntry.ScriptPublicKey(), isP2SH)
|
sigOpCount := txscript.GetPreciseSigOpCount(sigScript, utxoEntry.ScriptPublicKey(), isP2SH)
|
||||||
|
|
||||||
if postHF {
|
|
||||||
if sigOpCount != int(input.SigOpCount) {
|
if sigOpCount != int(input.SigOpCount) {
|
||||||
return errors.Wrapf(ruleerrors.ErrWrongSigOpCount,
|
return errors.Wrapf(ruleerrors.ErrWrongSigOpCount,
|
||||||
"input %d specifies SigOpCount %d while actual SigOpCount is %d",
|
"input %d specifies SigOpCount %d while actual SigOpCount is %d",
|
||||||
i, input.SigOpCount, sigOpCount)
|
i, input.SigOpCount, sigOpCount)
|
||||||
}
|
}
|
||||||
} else {
|
|
||||||
const sigOpCountLimit = 10
|
|
||||||
if sigOpCount > sigOpCountLimit {
|
|
||||||
return errors.Wrapf(ruleerrors.ErrWrongSigOpCount,
|
|
||||||
"input %d is using SigOpCount %d while the limit is %d",
|
|
||||||
i, sigOpCount, sigOpCountLimit)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|||||||
@ -23,7 +23,7 @@ func (v *transactionValidator) ValidateTransactionInIsolation(tx *externalapi.Do
|
|||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
err = v.checkCoinbaseInIsolation(tx, povDAAScore >= v.hfDAAScore)
|
err = v.checkCoinbaseInIsolation(tx)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
@ -114,7 +114,7 @@ func (v *transactionValidator) checkDuplicateTransactionInputs(tx *externalapi.D
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func (v *transactionValidator) checkCoinbaseInIsolation(tx *externalapi.DomainTransaction, postHF bool) error {
|
func (v *transactionValidator) checkCoinbaseInIsolation(tx *externalapi.DomainTransaction) error {
|
||||||
if !transactionhelper.IsCoinBase(tx) {
|
if !transactionhelper.IsCoinBase(tx) {
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
@ -127,7 +127,6 @@ func (v *transactionValidator) checkCoinbaseInIsolation(tx *externalapi.DomainTr
|
|||||||
payloadLen, v.maxCoinbasePayloadLength)
|
payloadLen, v.maxCoinbasePayloadLength)
|
||||||
}
|
}
|
||||||
|
|
||||||
if postHF {
|
|
||||||
if len(tx.Inputs) != 0 {
|
if len(tx.Inputs) != 0 {
|
||||||
return errors.Wrap(ruleerrors.ErrCoinbaseWithInputs, "coinbase has inputs")
|
return errors.Wrap(ruleerrors.ErrCoinbaseWithInputs, "coinbase has inputs")
|
||||||
}
|
}
|
||||||
@ -143,7 +142,6 @@ func (v *transactionValidator) checkCoinbaseInIsolation(tx *externalapi.DomainTr
|
|||||||
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
|
||||||
|
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|||||||
@ -22,7 +22,6 @@ type txSubnetworkData struct {
|
|||||||
func TestValidateTransactionInIsolationAndPopulateMass(t *testing.T) {
|
func TestValidateTransactionInIsolationAndPopulateMass(t *testing.T) {
|
||||||
testutils.ForAllNets(t, true, func(t *testing.T, consensusConfig *consensus.Config) {
|
testutils.ForAllNets(t, true, func(t *testing.T, consensusConfig *consensus.Config) {
|
||||||
cfg := *consensusConfig
|
cfg := *consensusConfig
|
||||||
cfg.HFDAAScore = 1000
|
|
||||||
|
|
||||||
factory := consensus.NewFactory()
|
factory := consensus.NewFactory()
|
||||||
tc, teardown, err := factory.NewTestConsensus(&cfg, "TestValidateTransactionInIsolationAndPopulateMass")
|
tc, teardown, err := factory.NewTestConsensus(&cfg, "TestValidateTransactionInIsolationAndPopulateMass")
|
||||||
@ -70,22 +69,14 @@ func TestValidateTransactionInIsolationAndPopulateMass(t *testing.T) {
|
|||||||
nil,
|
nil,
|
||||||
func(tx *externalapi.DomainTransaction) { tx.Inputs[1].PreviousOutpoint.Index = 0 },
|
func(tx *externalapi.DomainTransaction) { tx.Inputs[1].PreviousOutpoint.Index = 0 },
|
||||||
ruleerrors.ErrDuplicateTxInputs, 0},
|
ruleerrors.ErrDuplicateTxInputs, 0},
|
||||||
{"1 input coinbase - pre HF",
|
{"1 input coinbase",
|
||||||
1,
|
1,
|
||||||
1,
|
1,
|
||||||
1,
|
1,
|
||||||
subnetworks.SubnetworkIDNative,
|
subnetworks.SubnetworkIDNative,
|
||||||
&txSubnetworkData{subnetworks.SubnetworkIDCoinbase, 0, nil},
|
&txSubnetworkData{subnetworks.SubnetworkIDCoinbase, 0, nil},
|
||||||
nil,
|
nil,
|
||||||
nil, 0},
|
ruleerrors.ErrCoinbaseWithInputs, 0},
|
||||||
{"1 input coinbase - post HF",
|
|
||||||
1,
|
|
||||||
1,
|
|
||||||
1,
|
|
||||||
subnetworks.SubnetworkIDNative,
|
|
||||||
&txSubnetworkData{subnetworks.SubnetworkIDCoinbase, 0, nil},
|
|
||||||
nil,
|
|
||||||
ruleerrors.ErrCoinbaseWithInputs, cfg.HFDAAScore},
|
|
||||||
{"no inputs coinbase",
|
{"no inputs coinbase",
|
||||||
0,
|
0,
|
||||||
1,
|
1,
|
||||||
|
|||||||
@ -19,7 +19,6 @@ type transactionValidator struct {
|
|||||||
daaBlocksStore model.DAABlocksStore
|
daaBlocksStore model.DAABlocksStore
|
||||||
enableNonNativeSubnetworks bool
|
enableNonNativeSubnetworks bool
|
||||||
maxCoinbasePayloadLength uint64
|
maxCoinbasePayloadLength uint64
|
||||||
hfDAAScore uint64
|
|
||||||
ghostdagK externalapi.KType
|
ghostdagK externalapi.KType
|
||||||
coinbasePayloadScriptPublicKeyMaxLength uint8
|
coinbasePayloadScriptPublicKeyMaxLength uint8
|
||||||
sigCache *txscript.SigCache
|
sigCache *txscript.SigCache
|
||||||
@ -31,7 +30,6 @@ type transactionValidator struct {
|
|||||||
func New(blockCoinbaseMaturity uint64,
|
func New(blockCoinbaseMaturity uint64,
|
||||||
enableNonNativeSubnetworks bool,
|
enableNonNativeSubnetworks bool,
|
||||||
maxCoinbasePayloadLength uint64,
|
maxCoinbasePayloadLength uint64,
|
||||||
hfDAAScore uint64,
|
|
||||||
ghostdagK externalapi.KType,
|
ghostdagK externalapi.KType,
|
||||||
coinbasePayloadScriptPublicKeyMaxLength uint8,
|
coinbasePayloadScriptPublicKeyMaxLength uint8,
|
||||||
databaseContext model.DBReader,
|
databaseContext model.DBReader,
|
||||||
@ -44,7 +42,6 @@ func New(blockCoinbaseMaturity uint64,
|
|||||||
blockCoinbaseMaturity: blockCoinbaseMaturity,
|
blockCoinbaseMaturity: blockCoinbaseMaturity,
|
||||||
enableNonNativeSubnetworks: enableNonNativeSubnetworks,
|
enableNonNativeSubnetworks: enableNonNativeSubnetworks,
|
||||||
maxCoinbasePayloadLength: maxCoinbasePayloadLength,
|
maxCoinbasePayloadLength: maxCoinbasePayloadLength,
|
||||||
hfDAAScore: hfDAAScore,
|
|
||||||
ghostdagK: ghostdagK,
|
ghostdagK: ghostdagK,
|
||||||
coinbasePayloadScriptPublicKeyMaxLength: coinbasePayloadScriptPublicKeyMaxLength,
|
coinbasePayloadScriptPublicKeyMaxLength: coinbasePayloadScriptPublicKeyMaxLength,
|
||||||
databaseContext: databaseContext,
|
databaseContext: databaseContext,
|
||||||
|
|||||||
@ -244,7 +244,6 @@ var (
|
|||||||
ErrCoinbaseWithInputs = newRuleError("ErrCoinbaseWithInputs")
|
ErrCoinbaseWithInputs = newRuleError("ErrCoinbaseWithInputs")
|
||||||
ErrCoinbaseTooManyOutputs = newRuleError("ErrCoinbaseTooManyOutputs")
|
ErrCoinbaseTooManyOutputs = newRuleError("ErrCoinbaseTooManyOutputs")
|
||||||
ErrCoinbaseTooLongScriptPublicKey = newRuleError("ErrCoinbaseTooLongScriptPublicKey")
|
ErrCoinbaseTooLongScriptPublicKey = newRuleError("ErrCoinbaseTooLongScriptPublicKey")
|
||||||
ErrOverMaxBlockInputsPreHF = newRuleError("ErrOverMaxBlockInputsPreHF")
|
|
||||||
)
|
)
|
||||||
|
|
||||||
// RuleError identifies a rule violation. It is used to indicate that
|
// RuleError identifies a rule violation. It is used to indicate that
|
||||||
|
|||||||
@ -23,11 +23,11 @@ const (
|
|||||||
)
|
)
|
||||||
|
|
||||||
// TransactionHash returns the transaction hash.
|
// TransactionHash returns the transaction hash.
|
||||||
func TransactionHash(tx *externalapi.DomainTransaction, postHF bool) *externalapi.DomainHash {
|
func TransactionHash(tx *externalapi.DomainTransaction) *externalapi.DomainHash {
|
||||||
// Encode the header and hash everything prior to the number of
|
// Encode the header and hash everything prior to the number of
|
||||||
// transactions.
|
// transactions.
|
||||||
writer := hashes.NewTransactionHashWriter()
|
writer := hashes.NewTransactionHashWriter()
|
||||||
err := serializeTransaction(writer, tx, txEncodingFull, postHF)
|
err := serializeTransaction(writer, tx, txEncodingFull)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
// It seems like this could only happen if the writer returned an error.
|
// It seems like this could only happen if the writer returned an error.
|
||||||
// and this writer should never return an error (no allocations or possible failures)
|
// and this writer should never return an error (no allocations or possible failures)
|
||||||
@ -52,7 +52,7 @@ func TransactionID(tx *externalapi.DomainTransaction) *externalapi.DomainTransac
|
|||||||
encodingFlags = txEncodingExcludeSignatureScript
|
encodingFlags = txEncodingExcludeSignatureScript
|
||||||
}
|
}
|
||||||
writer := hashes.NewTransactionIDWriter()
|
writer := hashes.NewTransactionIDWriter()
|
||||||
err := serializeTransaction(writer, tx, encodingFlags, true)
|
err := serializeTransaction(writer, tx, encodingFlags)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
// this writer never return errors (no allocations or possible failures) so errors can only come from validity checks,
|
// this writer never return errors (no allocations or possible failures) so errors can only come from validity checks,
|
||||||
// and we assume we never construct malformed transactions.
|
// and we assume we never construct malformed transactions.
|
||||||
@ -74,7 +74,7 @@ func TransactionIDs(txs []*externalapi.DomainTransaction) []*externalapi.DomainT
|
|||||||
return txIDs
|
return txIDs
|
||||||
}
|
}
|
||||||
|
|
||||||
func serializeTransaction(w io.Writer, tx *externalapi.DomainTransaction, encodingFlags txEncoding, postHF bool) error {
|
func serializeTransaction(w io.Writer, tx *externalapi.DomainTransaction, encodingFlags txEncoding) error {
|
||||||
err := binaryserializer.PutUint16(w, tx.Version)
|
err := binaryserializer.PutUint16(w, tx.Version)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
@ -87,7 +87,7 @@ func serializeTransaction(w io.Writer, tx *externalapi.DomainTransaction, encodi
|
|||||||
}
|
}
|
||||||
|
|
||||||
for _, ti := range tx.Inputs {
|
for _, ti := range tx.Inputs {
|
||||||
err = writeTransactionInput(w, ti, encodingFlags, postHF)
|
err = writeTransactionInput(w, ti, encodingFlags)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
@ -131,7 +131,7 @@ func serializeTransaction(w io.Writer, tx *externalapi.DomainTransaction, encodi
|
|||||||
|
|
||||||
// writeTransactionInput encodes ti to the kaspa protocol encoding for a transaction
|
// writeTransactionInput encodes ti to the kaspa protocol encoding for a transaction
|
||||||
// input to w.
|
// input to w.
|
||||||
func writeTransactionInput(w io.Writer, ti *externalapi.DomainTransactionInput, encodingFlags txEncoding, postHF bool) error {
|
func writeTransactionInput(w io.Writer, ti *externalapi.DomainTransactionInput, encodingFlags txEncoding) error {
|
||||||
err := writeOutpoint(w, &ti.PreviousOutpoint)
|
err := writeOutpoint(w, &ti.PreviousOutpoint)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
@ -143,12 +143,10 @@ func writeTransactionInput(w io.Writer, ti *externalapi.DomainTransactionInput,
|
|||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
if postHF {
|
|
||||||
_, err = w.Write([]byte{ti.SigOpCount})
|
_, err = w.Write([]byte{ti.SigOpCount})
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
}
|
|
||||||
} else {
|
} else {
|
||||||
err = writeVarBytes(w, []byte{})
|
err = writeVarBytes(w, []byte{})
|
||||||
if err != nil {
|
if err != nil {
|
||||||
|
|||||||
@ -38,7 +38,4 @@ const (
|
|||||||
// UnacceptedDAAScore is used to for UTXOEntries that were created by transactions in the mempool, or otherwise
|
// UnacceptedDAAScore is used to for UTXOEntries that were created by transactions in the mempool, or otherwise
|
||||||
// not-yet-accepted transactions.
|
// not-yet-accepted transactions.
|
||||||
UnacceptedDAAScore = math.MaxUint64
|
UnacceptedDAAScore = math.MaxUint64
|
||||||
|
|
||||||
// MaxBlockInputsPreHF is the maximum number of inputs a block can hold before the HF
|
|
||||||
MaxBlockInputsPreHF = 900
|
|
||||||
)
|
)
|
||||||
|
|||||||
@ -37,10 +37,10 @@ func hashMerkleBranches(left, right *externalapi.DomainHash) *externalapi.Domain
|
|||||||
|
|
||||||
// CalculateHashMerkleRoot calculates the merkle root of a tree consisted of the given transaction hashes.
|
// CalculateHashMerkleRoot calculates the merkle root of a tree consisted of the given transaction hashes.
|
||||||
// See `merkleRoot` for more info.
|
// See `merkleRoot` for more info.
|
||||||
func CalculateHashMerkleRoot(transactions []*externalapi.DomainTransaction, postHF bool) *externalapi.DomainHash {
|
func CalculateHashMerkleRoot(transactions []*externalapi.DomainTransaction) *externalapi.DomainHash {
|
||||||
txHashes := make([]*externalapi.DomainHash, len(transactions))
|
txHashes := make([]*externalapi.DomainHash, len(transactions))
|
||||||
for i, tx := range transactions {
|
for i, tx := range transactions {
|
||||||
txHashes[i] = consensushashing.TransactionHash(tx, postHF)
|
txHashes[i] = consensushashing.TransactionHash(tx)
|
||||||
}
|
}
|
||||||
return merkleRoot(txHashes)
|
return merkleRoot(txHashes)
|
||||||
}
|
}
|
||||||
|
|||||||
@ -188,8 +188,6 @@ type Params struct {
|
|||||||
MaxBlockLevel int
|
MaxBlockLevel int
|
||||||
|
|
||||||
MergeDepth uint64
|
MergeDepth uint64
|
||||||
|
|
||||||
HFDAAScore uint64
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// NormalizeRPCServerAddress returns addr with the current network default
|
// NormalizeRPCServerAddress returns addr with the current network default
|
||||||
@ -290,8 +288,6 @@ var MainnetParams = Params{
|
|||||||
// This means that any block that has a level lower or equal to genesis will be level 0.
|
// This means that any block that has a level lower or equal to genesis will be level 0.
|
||||||
MaxBlockLevel: 225,
|
MaxBlockLevel: 225,
|
||||||
MergeDepth: defaultMergeDepth,
|
MergeDepth: defaultMergeDepth,
|
||||||
|
|
||||||
HFDAAScore: 27905000,
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// TestnetParams defines the network parameters for the test Kaspa network.
|
// TestnetParams defines the network parameters for the test Kaspa network.
|
||||||
@ -358,7 +354,6 @@ var TestnetParams = Params{
|
|||||||
|
|
||||||
MaxBlockLevel: 250,
|
MaxBlockLevel: 250,
|
||||||
MergeDepth: defaultMergeDepth,
|
MergeDepth: defaultMergeDepth,
|
||||||
HFDAAScore: 14106400,
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// SimnetParams defines the network parameters for the simulation test Kaspa
|
// SimnetParams defines the network parameters for the simulation test Kaspa
|
||||||
|
|||||||
@ -37,19 +37,17 @@ type blockTemplateBuilder struct {
|
|||||||
policy policy
|
policy policy
|
||||||
|
|
||||||
coinbasePayloadScriptPublicKeyMaxLength uint8
|
coinbasePayloadScriptPublicKeyMaxLength uint8
|
||||||
hfDAAScore uint64
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// New creates a new blockTemplateBuilder
|
// New creates a new blockTemplateBuilder
|
||||||
func New(consensusReference consensusreference.ConsensusReference, mempool miningmanagerapi.Mempool,
|
func New(consensusReference consensusreference.ConsensusReference, mempool miningmanagerapi.Mempool,
|
||||||
blockMaxMass uint64, coinbasePayloadScriptPublicKeyMaxLength uint8, hfDAAScore uint64) miningmanagerapi.BlockTemplateBuilder {
|
blockMaxMass uint64, coinbasePayloadScriptPublicKeyMaxLength uint8) miningmanagerapi.BlockTemplateBuilder {
|
||||||
return &blockTemplateBuilder{
|
return &blockTemplateBuilder{
|
||||||
consensusReference: consensusReference,
|
consensusReference: consensusReference,
|
||||||
mempool: mempool,
|
mempool: mempool,
|
||||||
policy: policy{BlockMaxMass: blockMaxMass},
|
policy: policy{BlockMaxMass: blockMaxMass},
|
||||||
|
|
||||||
coinbasePayloadScriptPublicKeyMaxLength: coinbasePayloadScriptPublicKeyMaxLength,
|
coinbasePayloadScriptPublicKeyMaxLength: coinbasePayloadScriptPublicKeyMaxLength,
|
||||||
hfDAAScore: hfDAAScore,
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -192,7 +190,7 @@ func (btb *blockTemplateBuilder) ModifyBlockTemplate(newCoinbaseData *consensuse
|
|||||||
// Update the hash merkle root according to the modified transactions
|
// Update the hash merkle root according to the modified transactions
|
||||||
mutableHeader := blockTemplateToModify.Block.Header.ToMutable()
|
mutableHeader := blockTemplateToModify.Block.Header.ToMutable()
|
||||||
// TODO: can be optimized to O(log(#transactions)) by caching the whole merkle tree in BlockTemplate and changing only the relevant path
|
// TODO: can be optimized to O(log(#transactions)) by caching the whole merkle tree in BlockTemplate and changing only the relevant path
|
||||||
mutableHeader.SetHashMerkleRoot(merkle.CalculateHashMerkleRoot(blockTemplateToModify.Block.Transactions, mutableHeader.DAAScore() >= btb.hfDAAScore))
|
mutableHeader.SetHashMerkleRoot(merkle.CalculateHashMerkleRoot(blockTemplateToModify.Block.Transactions))
|
||||||
|
|
||||||
newTimestamp := mstime.Now().UnixMilliseconds()
|
newTimestamp := mstime.Now().UnixMilliseconds()
|
||||||
if newTimestamp >= mutableHeader.TimeInMilliseconds() {
|
if newTimestamp >= mutableHeader.TimeInMilliseconds() {
|
||||||
|
|||||||
@ -1,7 +1,6 @@
|
|||||||
package blocktemplatebuilder
|
package blocktemplatebuilder
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"github.com/kaspanet/kaspad/domain/consensus/utils/constants"
|
|
||||||
"math"
|
"math"
|
||||||
"math/rand"
|
"math/rand"
|
||||||
"sort"
|
"sort"
|
||||||
@ -75,8 +74,6 @@ func (btb *blockTemplateBuilder) selectTransactions(candidateTxs []*candidateTx)
|
|||||||
usedP += candidateTx.p
|
usedP += candidateTx.p
|
||||||
}
|
}
|
||||||
|
|
||||||
totalInputs := 0
|
|
||||||
|
|
||||||
selectedTxs := make([]*candidateTx, 0)
|
selectedTxs := make([]*candidateTx, 0)
|
||||||
for len(candidateTxs)-usedCount > 0 {
|
for len(candidateTxs)-usedCount > 0 {
|
||||||
// Rebalance the candidates if it's required
|
// Rebalance the candidates if it's required
|
||||||
@ -102,10 +99,6 @@ func (btb *blockTemplateBuilder) selectTransactions(candidateTxs []*candidateTx)
|
|||||||
}
|
}
|
||||||
tx := selectedTx.DomainTransaction
|
tx := selectedTx.DomainTransaction
|
||||||
|
|
||||||
if totalInputs+len(tx.Inputs) > maxBlockInputsPreHF(btb.hfDAAScore) {
|
|
||||||
continue
|
|
||||||
}
|
|
||||||
|
|
||||||
// Enforce maximum transaction mass per block. Also check
|
// Enforce maximum transaction mass per block. Also check
|
||||||
// for overflow.
|
// for overflow.
|
||||||
if txsForBlockTemplate.totalMass+selectedTx.Mass < txsForBlockTemplate.totalMass ||
|
if txsForBlockTemplate.totalMass+selectedTx.Mass < txsForBlockTemplate.totalMass ||
|
||||||
@ -150,7 +143,6 @@ func (btb *blockTemplateBuilder) selectTransactions(candidateTxs []*candidateTx)
|
|||||||
// save the masses, fees, and signature operation counts to the
|
// save the masses, fees, and signature operation counts to the
|
||||||
// result.
|
// result.
|
||||||
selectedTxs = append(selectedTxs, selectedTx)
|
selectedTxs = append(selectedTxs, selectedTx)
|
||||||
totalInputs += len(selectedTx.Inputs)
|
|
||||||
txsForBlockTemplate.totalMass += selectedTx.Mass
|
txsForBlockTemplate.totalMass += selectedTx.Mass
|
||||||
txsForBlockTemplate.totalFees += selectedTx.Fee
|
txsForBlockTemplate.totalFees += selectedTx.Fee
|
||||||
|
|
||||||
@ -158,10 +150,6 @@ func (btb *blockTemplateBuilder) selectTransactions(candidateTxs []*candidateTx)
|
|||||||
consensushashing.TransactionID(tx), selectedTx.Fee*1e6/selectedTx.Mass)
|
consensushashing.TransactionID(tx), selectedTx.Fee*1e6/selectedTx.Mass)
|
||||||
|
|
||||||
markCandidateTxForDeletion(selectedTx)
|
markCandidateTxForDeletion(selectedTx)
|
||||||
|
|
||||||
if totalInputs == maxBlockInputsPreHF(btb.hfDAAScore) {
|
|
||||||
break
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
sort.Slice(selectedTxs, func(i, j int) bool {
|
sort.Slice(selectedTxs, func(i, j int) bool {
|
||||||
@ -175,10 +163,6 @@ func (btb *blockTemplateBuilder) selectTransactions(candidateTxs []*candidateTx)
|
|||||||
return txsForBlockTemplate
|
return txsForBlockTemplate
|
||||||
}
|
}
|
||||||
|
|
||||||
func maxBlockInputsPreHF(hfDAAScore uint64) int {
|
|
||||||
return constants.MaxBlockInputsPreHF
|
|
||||||
}
|
|
||||||
|
|
||||||
func rebalanceCandidates(oldCandidateTxs []*candidateTx, isFirstRun bool) (
|
func rebalanceCandidates(oldCandidateTxs []*candidateTx, isFirstRun bool) (
|
||||||
candidateTxs []*candidateTx, totalP float64) {
|
candidateTxs []*candidateTx, totalP float64) {
|
||||||
|
|
||||||
|
|||||||
@ -21,7 +21,7 @@ func (f *factory) NewMiningManager(consensusReference consensusreference.Consens
|
|||||||
mempoolConfig *mempoolpkg.Config) MiningManager {
|
mempoolConfig *mempoolpkg.Config) MiningManager {
|
||||||
|
|
||||||
mempool := mempoolpkg.New(mempoolConfig, consensusReference)
|
mempool := mempoolpkg.New(mempoolConfig, consensusReference)
|
||||||
blockTemplateBuilder := blocktemplatebuilder.New(consensusReference, mempool, params.MaxBlockMass, params.CoinbasePayloadScriptPublicKeyMaxLength, params.HFDAAScore)
|
blockTemplateBuilder := blocktemplatebuilder.New(consensusReference, mempool, params.MaxBlockMass, params.CoinbasePayloadScriptPublicKeyMaxLength)
|
||||||
|
|
||||||
return &miningManager{
|
return &miningManager{
|
||||||
consensusReference: consensusReference,
|
consensusReference: consensusReference,
|
||||||
|
|||||||
2
go.mod
2
go.mod
@ -7,6 +7,7 @@ require (
|
|||||||
github.com/btcsuite/go-socks v0.0.0-20170105172521-4720035b7bfd
|
github.com/btcsuite/go-socks v0.0.0-20170105172521-4720035b7bfd
|
||||||
github.com/btcsuite/winsvc v1.0.0
|
github.com/btcsuite/winsvc v1.0.0
|
||||||
github.com/davecgh/go-spew v1.1.1
|
github.com/davecgh/go-spew v1.1.1
|
||||||
|
github.com/gofrs/flock v0.8.1
|
||||||
github.com/golang/protobuf v1.5.2
|
github.com/golang/protobuf v1.5.2
|
||||||
github.com/jessevdk/go-flags v1.4.0
|
github.com/jessevdk/go-flags v1.4.0
|
||||||
github.com/jrick/logrotate v1.0.0
|
github.com/jrick/logrotate v1.0.0
|
||||||
@ -28,6 +29,5 @@ require (
|
|||||||
golang.org/x/sys v0.0.0-20211019181941-9d821ace8654 // indirect
|
golang.org/x/sys v0.0.0-20211019181941-9d821ace8654 // indirect
|
||||||
golang.org/x/text v0.3.5 // indirect
|
golang.org/x/text v0.3.5 // indirect
|
||||||
google.golang.org/genproto v0.0.0-20210604141403-392c879c8b08 // indirect
|
google.golang.org/genproto v0.0.0-20210604141403-392c879c8b08 // indirect
|
||||||
google.golang.org/grpc/cmd/protoc-gen-go-grpc v1.2.0 // indirect
|
|
||||||
gopkg.in/yaml.v2 v2.3.0 // indirect
|
gopkg.in/yaml.v2 v2.3.0 // indirect
|
||||||
)
|
)
|
||||||
|
|||||||
10
go.sum
10
go.sum
@ -26,6 +26,8 @@ github.com/envoyproxy/go-control-plane v0.9.1-0.20191026205805-5f8ba28d4473/go.m
|
|||||||
github.com/envoyproxy/go-control-plane v0.9.9-0.20210217033140-668b12f5399d/go.mod h1:cXg6YxExXjJnVBQHBLXeUAgxn2UodCpnH306RInaBQk=
|
github.com/envoyproxy/go-control-plane v0.9.9-0.20210217033140-668b12f5399d/go.mod h1:cXg6YxExXjJnVBQHBLXeUAgxn2UodCpnH306RInaBQk=
|
||||||
github.com/envoyproxy/protoc-gen-validate v0.1.0/go.mod h1:iSmxcyjqTsJpI2R4NaDN7+kN2VEUnK/pcBlmesArF7c=
|
github.com/envoyproxy/protoc-gen-validate v0.1.0/go.mod h1:iSmxcyjqTsJpI2R4NaDN7+kN2VEUnK/pcBlmesArF7c=
|
||||||
github.com/fsnotify/fsnotify v1.4.7/go.mod h1:jwhsz4b93w/PPRr/qN1Yymfu8t87LnFCMoQvtojpjFo=
|
github.com/fsnotify/fsnotify v1.4.7/go.mod h1:jwhsz4b93w/PPRr/qN1Yymfu8t87LnFCMoQvtojpjFo=
|
||||||
|
github.com/gofrs/flock v0.8.1 h1:+gYjHKf32LDeiEEFhQaotPbLuUXjY5ZqxKgXy7n59aw=
|
||||||
|
github.com/gofrs/flock v0.8.1/go.mod h1:F1TvTiK9OcQqauNUHlbJvyl9Qa1QvF/gOUDKA14jxHU=
|
||||||
github.com/golang/glog v0.0.0-20160126235308-23def4e6c14b/go.mod h1:SBH7ygxi8pfUlaOkMMuAQtPIUF8ecWP5IEl/CR7VP2Q=
|
github.com/golang/glog v0.0.0-20160126235308-23def4e6c14b/go.mod h1:SBH7ygxi8pfUlaOkMMuAQtPIUF8ecWP5IEl/CR7VP2Q=
|
||||||
github.com/golang/mock v1.1.1/go.mod h1:oTYuIxOrZwtPieC+H1uAHpcLFnEyAGVDL/k47Jfbm0A=
|
github.com/golang/mock v1.1.1/go.mod h1:oTYuIxOrZwtPieC+H1uAHpcLFnEyAGVDL/k47Jfbm0A=
|
||||||
github.com/golang/protobuf v1.2.0/go.mod h1:6lQm79b+lXiMfvg/cZm0SGofjICqVBUtrP5yJMmIC1U=
|
github.com/golang/protobuf v1.2.0/go.mod h1:6lQm79b+lXiMfvg/cZm0SGofjICqVBUtrP5yJMmIC1U=
|
||||||
@ -118,8 +120,6 @@ golang.org/x/sys v0.0.0-20201119102817-f84b799fce68/go.mod h1:h1NjWce9XRLGQEsW7w
|
|||||||
golang.org/x/sys v0.0.0-20210320140829-1e4c9ba3b0c4/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
|
golang.org/x/sys v0.0.0-20210320140829-1e4c9ba3b0c4/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
|
||||||
golang.org/x/sys v0.0.0-20210330210617-4fbd30eecc44/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
|
golang.org/x/sys v0.0.0-20210330210617-4fbd30eecc44/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
|
||||||
golang.org/x/sys v0.0.0-20210510120138-977fb7262007/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
|
golang.org/x/sys v0.0.0-20210510120138-977fb7262007/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
|
||||||
golang.org/x/sys v0.0.0-20210525143221-35b2ab0089ea h1:+WiDlPBBaO+h9vPNZi8uJ3k4BkKQB7Iow3aqwHVA5hI=
|
|
||||||
golang.org/x/sys v0.0.0-20210525143221-35b2ab0089ea/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
|
|
||||||
golang.org/x/sys v0.0.0-20211019181941-9d821ace8654 h1:id054HUawV2/6IGm2IV8KZQjqtwAOo2CYlOToYqa0d0=
|
golang.org/x/sys v0.0.0-20211019181941-9d821ace8654 h1:id054HUawV2/6IGm2IV8KZQjqtwAOo2CYlOToYqa0d0=
|
||||||
golang.org/x/sys v0.0.0-20211019181941-9d821ace8654/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
|
golang.org/x/sys v0.0.0-20211019181941-9d821ace8654/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
|
||||||
golang.org/x/term v0.0.0-20201126162022-7de9c90e9dd1/go.mod h1:bj7SfCRtBDWHUb9snDiAeCFNEtKQo2Wmx5Cou7ajbmo=
|
golang.org/x/term v0.0.0-20201126162022-7de9c90e9dd1/go.mod h1:bj7SfCRtBDWHUb9snDiAeCFNEtKQo2Wmx5Cou7ajbmo=
|
||||||
@ -155,8 +155,6 @@ google.golang.org/grpc v1.25.1/go.mod h1:c3i+UQWmh7LiEpx4sFZnkU36qjEYZ0imhYfXVyQ
|
|||||||
google.golang.org/grpc v1.27.0/go.mod h1:qbnxyOmOxrQa7FizSgH+ReBfzJrCY1pSN7KXBS8abTk=
|
google.golang.org/grpc v1.27.0/go.mod h1:qbnxyOmOxrQa7FizSgH+ReBfzJrCY1pSN7KXBS8abTk=
|
||||||
google.golang.org/grpc v1.38.0 h1:/9BgsAsa5nWe26HqOlvlgJnqBuktYOLCgjCPqsa56W0=
|
google.golang.org/grpc v1.38.0 h1:/9BgsAsa5nWe26HqOlvlgJnqBuktYOLCgjCPqsa56W0=
|
||||||
google.golang.org/grpc v1.38.0/go.mod h1:NREThFqKR1f3iQ6oBuvc5LadQuXVGo9rkm5ZGrQdJfM=
|
google.golang.org/grpc v1.38.0/go.mod h1:NREThFqKR1f3iQ6oBuvc5LadQuXVGo9rkm5ZGrQdJfM=
|
||||||
google.golang.org/grpc/cmd/protoc-gen-go-grpc v1.2.0 h1:TLkBREm4nIsEcexnCjgQd5GQWaHcqMzwQV0TX9pq8S0=
|
|
||||||
google.golang.org/grpc/cmd/protoc-gen-go-grpc v1.2.0/go.mod h1:DNq5QpG7LJqD2AamLZ7zvKE0DEpVl2BSEVjFycAAjRY=
|
|
||||||
google.golang.org/protobuf v0.0.0-20200109180630-ec00e32a8dfd/go.mod h1:DFci5gLYBciE7Vtevhsrf46CRTquxDuWsQurQQe4oz8=
|
google.golang.org/protobuf v0.0.0-20200109180630-ec00e32a8dfd/go.mod h1:DFci5gLYBciE7Vtevhsrf46CRTquxDuWsQurQQe4oz8=
|
||||||
google.golang.org/protobuf v0.0.0-20200221191635-4d8936d0db64/go.mod h1:kwYJMbMJ01Woi6D6+Kah6886xMZcty6N08ah7+eCXa0=
|
google.golang.org/protobuf v0.0.0-20200221191635-4d8936d0db64/go.mod h1:kwYJMbMJ01Woi6D6+Kah6886xMZcty6N08ah7+eCXa0=
|
||||||
google.golang.org/protobuf v0.0.0-20200228230310-ab0ca4ff8a60/go.mod h1:cfTl7dwQJ+fmap5saPgwCLgHXTUD7jkjRqWcaiX5VyM=
|
google.golang.org/protobuf v0.0.0-20200228230310-ab0ca4ff8a60/go.mod h1:cfTl7dwQJ+fmap5saPgwCLgHXTUD7jkjRqWcaiX5VyM=
|
||||||
@ -167,12 +165,10 @@ google.golang.org/protobuf v1.23.0/go.mod h1:EGpADcykh3NcUnDUJcl1+ZksZNG86OlYog2
|
|||||||
google.golang.org/protobuf v1.23.1-0.20200526195155-81db48ad09cc/go.mod h1:EGpADcykh3NcUnDUJcl1+ZksZNG86OlYog2l/sGQquU=
|
google.golang.org/protobuf v1.23.1-0.20200526195155-81db48ad09cc/go.mod h1:EGpADcykh3NcUnDUJcl1+ZksZNG86OlYog2l/sGQquU=
|
||||||
google.golang.org/protobuf v1.25.0/go.mod h1:9JNX74DMeImyA3h4bdi1ymwjUzf21/xIlbajtzgsN7c=
|
google.golang.org/protobuf v1.25.0/go.mod h1:9JNX74DMeImyA3h4bdi1ymwjUzf21/xIlbajtzgsN7c=
|
||||||
google.golang.org/protobuf v1.26.0-rc.1/go.mod h1:jlhhOSvTdKEhbULTjvd4ARK9grFBp09yW+WbY/TyQbw=
|
google.golang.org/protobuf v1.26.0-rc.1/go.mod h1:jlhhOSvTdKEhbULTjvd4ARK9grFBp09yW+WbY/TyQbw=
|
||||||
google.golang.org/protobuf v1.26.0 h1:bxAC2xTBsZGibn2RTntX0oH50xLsqy1OxA9tTL3p/lk=
|
|
||||||
google.golang.org/protobuf v1.26.0/go.mod h1:9q0QmTI4eRPtz6boOQmLYwt+qCgq0jsYwAQnmE0givc=
|
google.golang.org/protobuf v1.26.0/go.mod h1:9q0QmTI4eRPtz6boOQmLYwt+qCgq0jsYwAQnmE0givc=
|
||||||
google.golang.org/protobuf v1.27.1 h1:SnqbnDw1V7RiZcXPx5MEeqPv2s79L9i7BJUlG/+RurQ=
|
|
||||||
google.golang.org/protobuf v1.27.1/go.mod h1:9q0QmTI4eRPtz6boOQmLYwt+qCgq0jsYwAQnmE0givc=
|
|
||||||
google.golang.org/protobuf v1.28.1 h1:d0NfwRgPtno5B1Wa6L2DAG+KivqkdutMf1UhdNx175w=
|
google.golang.org/protobuf v1.28.1 h1:d0NfwRgPtno5B1Wa6L2DAG+KivqkdutMf1UhdNx175w=
|
||||||
google.golang.org/protobuf v1.28.1/go.mod h1:HV8QOd/L58Z+nl8r43ehVNZIU/HEI6OcFqwMG9pJV4I=
|
google.golang.org/protobuf v1.28.1/go.mod h1:HV8QOd/L58Z+nl8r43ehVNZIU/HEI6OcFqwMG9pJV4I=
|
||||||
|
gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405 h1:yhCVgyC4o1eVCa2tZl7eS0r+SDo693bJlVdllGtEeKM=
|
||||||
gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0=
|
gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0=
|
||||||
gopkg.in/fsnotify.v1 v1.4.7 h1:xOHLXZwVvI9hhs+cLKq5+I5onOuwQLhQwiu63xxlHs4=
|
gopkg.in/fsnotify.v1 v1.4.7 h1:xOHLXZwVvI9hhs+cLKq5+I5onOuwQLhQwiu63xxlHs4=
|
||||||
gopkg.in/fsnotify.v1 v1.4.7/go.mod h1:Tz8NjZHkW78fSQdbUxIjBTcgA1z1m8ZHf0WmKUhAMys=
|
gopkg.in/fsnotify.v1 v1.4.7/go.mod h1:Tz8NjZHkW78fSQdbUxIjBTcgA1z1m8ZHf0WmKUhAMys=
|
||||||
|
|||||||
@ -31,7 +31,7 @@ func (c *Calculator) MassPerScriptPubKeyByte() uint64 { return c.massPerScriptPu
|
|||||||
func (c *Calculator) MassPerSigOp() uint64 { return c.massPerSigOp }
|
func (c *Calculator) MassPerSigOp() uint64 { return c.massPerSigOp }
|
||||||
|
|
||||||
// CalculateTransactionMass calculates the mass of the given transaction
|
// CalculateTransactionMass calculates the mass of the given transaction
|
||||||
func (c *Calculator) CalculateTransactionMass(transaction *externalapi.DomainTransaction, postHF bool) uint64 {
|
func (c *Calculator) CalculateTransactionMass(transaction *externalapi.DomainTransaction) uint64 {
|
||||||
if transactionhelper.IsCoinBase(transaction) {
|
if transactionhelper.IsCoinBase(transaction) {
|
||||||
return 0
|
return 0
|
||||||
}
|
}
|
||||||
@ -49,14 +49,11 @@ func (c *Calculator) CalculateTransactionMass(transaction *externalapi.DomainTra
|
|||||||
massForScriptPubKey := totalScriptPubKeySize * c.massPerScriptPubKeyByte
|
massForScriptPubKey := totalScriptPubKeySize * c.massPerScriptPubKeyByte
|
||||||
|
|
||||||
// calculate mass for SigOps
|
// calculate mass for SigOps
|
||||||
massForSigOps := uint64(0)
|
|
||||||
if postHF {
|
|
||||||
totalSigOpCount := uint64(0)
|
totalSigOpCount := uint64(0)
|
||||||
for _, input := range transaction.Inputs {
|
for _, input := range transaction.Inputs {
|
||||||
totalSigOpCount += uint64(input.SigOpCount)
|
totalSigOpCount += uint64(input.SigOpCount)
|
||||||
}
|
}
|
||||||
massForSigOps = totalSigOpCount * c.massPerSigOp
|
massForSigOps := totalSigOpCount * c.massPerSigOp
|
||||||
}
|
|
||||||
|
|
||||||
// Sum all components of mass
|
// Sum all components of mass
|
||||||
return massForSize + massForScriptPubKey + massForSigOps
|
return massForSize + massForScriptPubKey + massForSigOps
|
||||||
|
|||||||
@ -11,7 +11,7 @@ const validCharacters = "0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrs
|
|||||||
const (
|
const (
|
||||||
appMajor uint = 0
|
appMajor uint = 0
|
||||||
appMinor uint = 12
|
appMinor uint = 12
|
||||||
appPatch uint = 7
|
appPatch uint = 8
|
||||||
)
|
)
|
||||||
|
|
||||||
// appBuild is defined as a variable so it can be overridden during the build
|
// appBuild is defined as a variable so it can be overridden during the build
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user