mirror of
https://github.com/kaspanet/kaspad.git
synced 2025-03-30 15:08:33 +00:00
Allow to configure consensus (closes #1067)
* Allow to configure consensus with a JSON file * Define everywhere maxBlockParents as KType * Move consensus default to consensus_defaults.go
This commit is contained in:
parent
a585f32763
commit
32a04d1811
@ -8,7 +8,6 @@ import (
|
||||
"github.com/kaspanet/kaspad/domain"
|
||||
"github.com/kaspanet/kaspad/domain/consensus/model/externalapi"
|
||||
"github.com/kaspanet/kaspad/domain/consensus/ruleerrors"
|
||||
"github.com/kaspanet/kaspad/domain/consensus/utils/blocks"
|
||||
"github.com/kaspanet/kaspad/domain/consensus/utils/consensushashing"
|
||||
"github.com/kaspanet/kaspad/infrastructure/logger"
|
||||
"github.com/kaspanet/kaspad/infrastructure/network/netadapter"
|
||||
@ -225,29 +224,6 @@ func (flow *handleRelayInvsFlow) processAndRelayBlock(requestQueue *hashesQueueS
|
||||
|
||||
missingParentsError := &ruleerrors.ErrMissingParents{}
|
||||
if errors.As(err, missingParentsError) {
|
||||
blueScore, err := blocks.ExtractBlueScore(block)
|
||||
if err != nil {
|
||||
return protocolerrors.Errorf(true, "received an orphan "+
|
||||
"block %s with malformed blue score", blockHash)
|
||||
}
|
||||
|
||||
const maxOrphanBlueScoreDiff = 10000
|
||||
virtualSelectedParent, err := flow.Domain().Consensus().GetVirtualSelectedParent()
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
selectedTipBlueScore, err := blocks.ExtractBlueScore(virtualSelectedParent)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
if blueScore > selectedTipBlueScore+maxOrphanBlueScoreDiff {
|
||||
log.Infof("Orphan block %s has blue score %d and the selected tip blue score is "+
|
||||
"%d. Ignoring orphans with a blue score difference from the selected tip greater than %d",
|
||||
blockHash, blueScore, selectedTipBlueScore, maxOrphanBlueScoreDiff)
|
||||
return nil
|
||||
}
|
||||
|
||||
// Add the orphan to the orphan pool
|
||||
flow.AddOrphan(block)
|
||||
|
||||
|
@ -6,8 +6,6 @@ import (
|
||||
"math/big"
|
||||
"strconv"
|
||||
|
||||
"github.com/kaspanet/kaspad/domain/consensus/utils/blocks"
|
||||
|
||||
"github.com/kaspanet/kaspad/domain/consensus/utils/estimatedsize"
|
||||
"github.com/kaspanet/kaspad/domain/consensus/utils/txscript"
|
||||
|
||||
@ -27,7 +25,7 @@ func (ctx *Context) BuildBlockVerboseData(block *externalapi.DomainBlock, includ
|
||||
hash := consensushashing.BlockHash(block)
|
||||
blockHeader := block.Header
|
||||
|
||||
blueScore, err := blocks.ExtractBlueScore(block)
|
||||
blockInfo, err := ctx.Domain.Consensus().GetBlockInfo(hash)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
@ -44,7 +42,7 @@ func (ctx *Context) BuildBlockVerboseData(block *externalapi.DomainBlock, includ
|
||||
Time: blockHeader.TimeInMilliseconds,
|
||||
Bits: strconv.FormatInt(int64(blockHeader.Bits), 16),
|
||||
Difficulty: ctx.GetDifficultyRatio(blockHeader.Bits, ctx.Config.ActiveNetParams),
|
||||
BlueScore: blueScore,
|
||||
BlueScore: blockInfo.BlueScore,
|
||||
}
|
||||
|
||||
txIDs := make([]string, len(block.Transactions))
|
||||
|
@ -129,6 +129,13 @@ func (s *consensus) GetBlockInfo(blockHash *externalapi.DomainHash) (*externalap
|
||||
return blockInfo, nil
|
||||
}
|
||||
|
||||
ghostdagData, err := s.ghostdagDataStore.Get(s.databaseContext, blockHash)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
blockInfo.BlueScore = ghostdagData.BlueScore
|
||||
|
||||
isBlockInHeaderPruningPointFuture, err := s.syncManager.IsBlockInHeaderPruningPointFuture(blockHash)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
|
@ -22,7 +22,6 @@ import (
|
||||
"github.com/kaspanet/kaspad/domain/consensus/datastructures/pruningstore"
|
||||
"github.com/kaspanet/kaspad/domain/consensus/datastructures/reachabilitydatastore"
|
||||
"github.com/kaspanet/kaspad/domain/consensus/datastructures/utxodiffstore"
|
||||
"github.com/kaspanet/kaspad/domain/consensus/model"
|
||||
"github.com/kaspanet/kaspad/domain/consensus/model/externalapi"
|
||||
"github.com/kaspanet/kaspad/domain/consensus/model/testapi"
|
||||
"github.com/kaspanet/kaspad/domain/consensus/processes/blockbuilder"
|
||||
@ -97,7 +96,7 @@ func (f *factory) NewConsensus(dagParams *dagconfig.Params, db infrastructuredat
|
||||
dbManager,
|
||||
dagTopologyManager,
|
||||
ghostdagDataStore,
|
||||
model.KType(dagParams.K))
|
||||
dagParams.K)
|
||||
dagTraversalManager := dagtraversalmanager.New(
|
||||
dbManager,
|
||||
dagTopologyManager,
|
||||
@ -111,6 +110,10 @@ func (f *factory) NewConsensus(dagParams *dagconfig.Params, db infrastructuredat
|
||||
ghostdagDataStore)
|
||||
transactionValidator := transactionvalidator.New(dagParams.BlockCoinbaseMaturity,
|
||||
dagParams.EnableNonNativeSubnetworks,
|
||||
dagParams.MassPerTxByte,
|
||||
dagParams.MassPerScriptPubKeyByte,
|
||||
dagParams.MassPerSigOp,
|
||||
dagParams.MaxCoinbasePayloadLength,
|
||||
dbManager,
|
||||
pastMedianTimeManager,
|
||||
ghostdagDataStore)
|
||||
@ -123,9 +126,13 @@ func (f *factory) NewConsensus(dagParams *dagconfig.Params, db infrastructuredat
|
||||
dagTraversalManager,
|
||||
dagParams.PowMax,
|
||||
dagParams.DifficultyAdjustmentWindowSize,
|
||||
dagParams.TargetTimePerBlock)
|
||||
dagParams.TargetTimePerBlock,
|
||||
dagParams.GenesisHash)
|
||||
coinbaseManager := coinbasemanager.New(
|
||||
dbManager,
|
||||
dagParams.SubsidyReductionInterval,
|
||||
dagParams.BaseSubsidy,
|
||||
dagParams.CoinbasePayloadScriptPublicKeyMaxLength,
|
||||
ghostdagDataStore,
|
||||
acceptanceDataStore)
|
||||
headerTipsManager := headertipsmanager.New(dbManager, dagTopologyManager, ghostdagManager, headerTipsStore)
|
||||
@ -143,6 +150,9 @@ func (f *factory) NewConsensus(dagParams *dagconfig.Params, db infrastructuredat
|
||||
dagParams.EnableNonNativeSubnetworks,
|
||||
dagParams.DisableDifficultyAdjustment,
|
||||
dagParams.DifficultyAdjustmentWindowSize,
|
||||
dagParams.MaxBlockSize,
|
||||
dagParams.MergeSetSizeLimit,
|
||||
dagParams.MaxBlockParents,
|
||||
|
||||
dbManager,
|
||||
difficultyManager,
|
||||
@ -164,7 +174,11 @@ func (f *factory) NewConsensus(dagParams *dagconfig.Params, db infrastructuredat
|
||||
dbManager,
|
||||
dagParams.FinalityDepth(),
|
||||
dagParams.PruningDepth(),
|
||||
dagParams.MaxMassAcceptedByBlock,
|
||||
dagParams.MaxBlockParents,
|
||||
dagParams.MergeSetSizeLimit,
|
||||
genesisHash,
|
||||
|
||||
ghostdagManager,
|
||||
dagTopologyManager,
|
||||
dagTraversalManager,
|
||||
|
@ -4,6 +4,7 @@ package externalapi
|
||||
type BlockInfo struct {
|
||||
Exists bool
|
||||
BlockStatus BlockStatus
|
||||
BlueScore uint64
|
||||
|
||||
IsBlockInHeaderPruningPointFuture bool
|
||||
}
|
||||
|
@ -7,4 +7,6 @@ import "github.com/kaspanet/kaspad/domain/consensus/model/externalapi"
|
||||
type CoinbaseManager interface {
|
||||
ExpectedCoinbaseTransaction(blockHash *externalapi.DomainHash,
|
||||
coinbaseData *externalapi.DomainCoinbaseData) (*externalapi.DomainTransaction, error)
|
||||
ExtractCoinbaseDataAndBlueScore(coinbaseTx *externalapi.DomainTransaction) (blueScore uint64,
|
||||
coinbaseData *externalapi.DomainCoinbaseData, err error)
|
||||
}
|
||||
|
@ -3,9 +3,7 @@ package blockvalidator
|
||||
import (
|
||||
"github.com/kaspanet/kaspad/domain/consensus/model/externalapi"
|
||||
"github.com/kaspanet/kaspad/domain/consensus/ruleerrors"
|
||||
"github.com/kaspanet/kaspad/domain/consensus/utils/coinbase"
|
||||
"github.com/kaspanet/kaspad/domain/consensus/utils/consensushashing"
|
||||
"github.com/kaspanet/kaspad/domain/consensus/utils/constants"
|
||||
"github.com/kaspanet/kaspad/domain/consensus/utils/estimatedsize"
|
||||
"github.com/kaspanet/kaspad/domain/consensus/utils/merkle"
|
||||
"github.com/kaspanet/kaspad/domain/consensus/utils/subnetworks"
|
||||
@ -85,7 +83,7 @@ func (v *blockValidator) ValidateBodyInIsolation(blockHash *externalapi.DomainHa
|
||||
}
|
||||
|
||||
func (v *blockValidator) checkCoinbase(block *externalapi.DomainBlock) error {
|
||||
_, _, err := coinbase.ExtractCoinbaseDataAndBlueScore(block.Transactions[transactionhelper.CoinbaseTransactionIndex])
|
||||
_, _, err := v.coinbaseManager.ExtractCoinbaseDataAndBlueScore(block.Transactions[transactionhelper.CoinbaseTransactionIndex])
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
@ -214,9 +212,9 @@ func (v *blockValidator) checkBlockSize(block *externalapi.DomainBlock) error {
|
||||
for _, tx := range block.Transactions {
|
||||
sizeBefore := size
|
||||
size += estimatedsize.TransactionEstimatedSerializedSize(tx)
|
||||
if size > constants.MaxBlockSize || size < sizeBefore {
|
||||
if size > v.maxBlockSize || size < sizeBefore {
|
||||
return errors.Wrapf(ruleerrors.ErrBlockSizeTooHigh, "block excceeded the size limit of %d",
|
||||
constants.MaxBlockSize)
|
||||
v.maxBlockSize)
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -4,7 +4,6 @@ import (
|
||||
"github.com/kaspanet/kaspad/domain/consensus/model/externalapi"
|
||||
"github.com/kaspanet/kaspad/domain/consensus/ruleerrors"
|
||||
"github.com/kaspanet/kaspad/domain/consensus/utils/consensushashing"
|
||||
"github.com/kaspanet/kaspad/domain/consensus/utils/constants"
|
||||
"github.com/pkg/errors"
|
||||
)
|
||||
|
||||
@ -118,9 +117,9 @@ func (v *blockValidator) checkMergeSizeLimit(hash *externalapi.DomainHash) error
|
||||
|
||||
mergeSetSize := len(ghostdagData.MergeSetReds) + len(ghostdagData.MergeSetBlues)
|
||||
|
||||
if mergeSetSize > constants.MergeSetSizeLimit {
|
||||
if uint64(mergeSetSize) > v.mergeSetSizeLimit {
|
||||
return errors.Wrapf(ruleerrors.ErrViolatingMergeLimit,
|
||||
"The block merges %d blocks > %d merge set size limit", mergeSetSize, constants.MergeSetSizeLimit)
|
||||
"The block merges %d blocks > %d merge set size limit", mergeSetSize, v.mergeSetSizeLimit)
|
||||
}
|
||||
|
||||
return nil
|
||||
|
@ -4,7 +4,6 @@ import (
|
||||
"github.com/kaspanet/kaspad/domain/consensus/model/externalapi"
|
||||
"github.com/kaspanet/kaspad/domain/consensus/ruleerrors"
|
||||
"github.com/kaspanet/kaspad/domain/consensus/utils/consensushashing"
|
||||
"github.com/kaspanet/kaspad/domain/consensus/utils/constants"
|
||||
"github.com/pkg/errors"
|
||||
)
|
||||
|
||||
@ -30,9 +29,9 @@ func (v *blockValidator) checkParentsLimit(header *externalapi.DomainBlockHeader
|
||||
return errors.Wrapf(ruleerrors.ErrNoParents, "block has no parents")
|
||||
}
|
||||
|
||||
if len(header.ParentHashes) > constants.MaxBlockParents {
|
||||
if uint64(len(header.ParentHashes)) > uint64(v.maxBlockParents) {
|
||||
return errors.Wrapf(ruleerrors.ErrTooManyParents, "block header has %d parents, but the maximum allowed amount "+
|
||||
"is %d", len(header.ParentHashes), constants.MaxBlockParents)
|
||||
"is %d", len(header.ParentHashes), v.maxBlockParents)
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
@ -18,6 +18,9 @@ type blockValidator struct {
|
||||
disableDifficultyAdjustment bool
|
||||
powMaxBits uint32
|
||||
difficultyAdjustmentWindowSize uint64
|
||||
maxBlockSize uint64
|
||||
mergeSetSizeLimit uint64
|
||||
maxBlockParents model.KType
|
||||
|
||||
databaseContext model.DBReader
|
||||
difficultyManager model.DifficultyManager
|
||||
@ -43,6 +46,10 @@ func New(powMax *big.Int,
|
||||
enableNonNativeSubnetworks bool,
|
||||
disableDifficultyAdjustment bool,
|
||||
difficultyAdjustmentWindowSize uint64,
|
||||
maxBlockSize uint64,
|
||||
mergeSetSizeLimit uint64,
|
||||
maxBlockParents model.KType,
|
||||
|
||||
databaseContext model.DBReader,
|
||||
|
||||
difficultyManager model.DifficultyManager,
|
||||
@ -68,16 +75,20 @@ func New(powMax *big.Int,
|
||||
disableDifficultyAdjustment: disableDifficultyAdjustment,
|
||||
powMaxBits: util.BigToCompact(powMax),
|
||||
difficultyAdjustmentWindowSize: difficultyAdjustmentWindowSize,
|
||||
databaseContext: databaseContext,
|
||||
difficultyManager: difficultyManager,
|
||||
pastMedianTimeManager: pastMedianTimeManager,
|
||||
transactionValidator: transactionValidator,
|
||||
ghostdagManager: ghostdagManager,
|
||||
dagTopologyManager: dagTopologyManager,
|
||||
dagTraversalManager: dagTraversalManager,
|
||||
coinbaseManager: coinbaseManager,
|
||||
mergeDepthManager: mergeDepthManager,
|
||||
pruningStore: pruningStore,
|
||||
maxBlockSize: maxBlockSize,
|
||||
mergeSetSizeLimit: mergeSetSizeLimit,
|
||||
maxBlockParents: maxBlockParents,
|
||||
|
||||
databaseContext: databaseContext,
|
||||
difficultyManager: difficultyManager,
|
||||
pastMedianTimeManager: pastMedianTimeManager,
|
||||
transactionValidator: transactionValidator,
|
||||
ghostdagManager: ghostdagManager,
|
||||
dagTopologyManager: dagTopologyManager,
|
||||
dagTraversalManager: dagTraversalManager,
|
||||
coinbaseManager: coinbaseManager,
|
||||
mergeDepthManager: mergeDepthManager,
|
||||
pruningStore: pruningStore,
|
||||
|
||||
blockStore: blockStore,
|
||||
ghostdagDataStore: ghostdagDataStore,
|
||||
|
@ -3,14 +3,15 @@ package coinbasemanager
|
||||
import (
|
||||
"github.com/kaspanet/kaspad/domain/consensus/model"
|
||||
"github.com/kaspanet/kaspad/domain/consensus/model/externalapi"
|
||||
"github.com/kaspanet/kaspad/domain/consensus/utils/coinbase"
|
||||
"github.com/kaspanet/kaspad/domain/consensus/utils/constants"
|
||||
"github.com/kaspanet/kaspad/domain/consensus/utils/hashes"
|
||||
"github.com/kaspanet/kaspad/domain/consensus/utils/subnetworks"
|
||||
)
|
||||
|
||||
type coinbaseManager struct {
|
||||
subsidyReductionInterval uint64
|
||||
subsidyReductionInterval uint64
|
||||
baseSubsidy uint64
|
||||
coinbasePayloadScriptPublicKeyMaxLength uint64
|
||||
|
||||
databaseContext model.DBReader
|
||||
ghostdagDataStore model.GHOSTDAGDataStore
|
||||
@ -42,7 +43,7 @@ func (c coinbaseManager) ExpectedCoinbaseTransaction(blockHash *externalapi.Doma
|
||||
}
|
||||
}
|
||||
|
||||
payload, err := coinbase.SerializeCoinbasePayload(ghostdagData.BlueScore, coinbaseData)
|
||||
payload, err := c.serializeCoinbasePayload(ghostdagData.BlueScore, coinbaseData)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
@ -85,7 +86,7 @@ func (c coinbaseManager) coinbaseOutputForBlueBlock(blueBlock *externalapi.Domai
|
||||
}
|
||||
|
||||
// the ScriptPubKey for the coinbase is parsed from the coinbase payload
|
||||
_, coinbaseData, err := coinbase.ExtractCoinbaseDataAndBlueScore(blockAcceptanceData.TransactionAcceptanceData[0].Transaction)
|
||||
_, coinbaseData, err := c.ExtractCoinbaseDataAndBlueScore(blockAcceptanceData.TransactionAcceptanceData[0].Transaction)
|
||||
if err != nil {
|
||||
return nil, false, err
|
||||
}
|
||||
@ -110,7 +111,7 @@ func (c coinbaseManager) coinbaseOutputForBlueBlock(blueBlock *externalapi.Domai
|
||||
// approximately every 4 years.
|
||||
func (c coinbaseManager) calcBlockSubsidy(blockHash *externalapi.DomainHash) (uint64, error) {
|
||||
if c.subsidyReductionInterval == 0 {
|
||||
return constants.BaseSubsidy, nil
|
||||
return c.baseSubsidy, nil
|
||||
}
|
||||
|
||||
ghostdagData, err := c.ghostdagDataStore.Get(c.databaseContext, blockHash)
|
||||
@ -119,17 +120,27 @@ func (c coinbaseManager) calcBlockSubsidy(blockHash *externalapi.DomainHash) (ui
|
||||
}
|
||||
|
||||
// Equivalent to: baseSubsidy / 2^(blueScore/subsidyHalvingInterval)
|
||||
return constants.BaseSubsidy >> uint(ghostdagData.BlueScore/c.subsidyReductionInterval), nil
|
||||
return c.baseSubsidy >> uint(ghostdagData.BlueScore/c.subsidyReductionInterval), nil
|
||||
}
|
||||
|
||||
// New instantiates a new CoinbaseManager
|
||||
func New(
|
||||
databaseContext model.DBReader,
|
||||
|
||||
subsidyReductionInterval uint64,
|
||||
baseSubsidy uint64,
|
||||
coinbasePayloadScriptPublicKeyMaxLength uint64,
|
||||
|
||||
ghostdagDataStore model.GHOSTDAGDataStore,
|
||||
acceptanceDataStore model.AcceptanceDataStore) model.CoinbaseManager {
|
||||
|
||||
return &coinbaseManager{
|
||||
databaseContext: databaseContext,
|
||||
databaseContext: databaseContext,
|
||||
|
||||
subsidyReductionInterval: subsidyReductionInterval,
|
||||
baseSubsidy: baseSubsidy,
|
||||
coinbasePayloadScriptPublicKeyMaxLength: coinbasePayloadScriptPublicKeyMaxLength,
|
||||
|
||||
ghostdagDataStore: ghostdagDataStore,
|
||||
acceptanceDataStore: acceptanceDataStore,
|
||||
}
|
||||
|
@ -1,4 +1,4 @@
|
||||
package coinbase
|
||||
package coinbasemanager
|
||||
|
||||
import (
|
||||
"encoding/binary"
|
||||
@ -6,7 +6,6 @@ import (
|
||||
|
||||
"github.com/kaspanet/kaspad/domain/consensus/model/externalapi"
|
||||
"github.com/kaspanet/kaspad/domain/consensus/ruleerrors"
|
||||
"github.com/kaspanet/kaspad/domain/consensus/utils/constants"
|
||||
"github.com/pkg/errors"
|
||||
)
|
||||
|
||||
@ -15,12 +14,12 @@ var byteOrder = binary.LittleEndian
|
||||
const uint64Len = 8
|
||||
const lengthOfscriptPubKeyLength = 1
|
||||
|
||||
// SerializeCoinbasePayload builds the coinbase payload based on the provided scriptPubKey and extra data.
|
||||
func SerializeCoinbasePayload(blueScore uint64, coinbaseData *externalapi.DomainCoinbaseData) ([]byte, error) {
|
||||
// serializeCoinbasePayload builds the coinbase payload based on the provided scriptPubKey and extra data.
|
||||
func (c coinbaseManager) serializeCoinbasePayload(blueScore uint64, coinbaseData *externalapi.DomainCoinbaseData) ([]byte, error) {
|
||||
scriptPubKeyLength := len(coinbaseData.ScriptPublicKey)
|
||||
if scriptPubKeyLength > constants.CoinbasePayloadScriptPublicKeyMaxLength {
|
||||
if uint64(scriptPubKeyLength) > c.coinbasePayloadScriptPublicKeyMaxLength {
|
||||
return nil, errors.Wrapf(ruleerrors.ErrBadCoinbasePayloadLen, "coinbase's payload script public key is "+
|
||||
"longer than the max allowed length of %d", constants.CoinbasePayloadScriptPublicKeyMaxLength)
|
||||
"longer than the max allowed length of %d", c.coinbasePayloadScriptPublicKeyMaxLength)
|
||||
}
|
||||
|
||||
payload := make([]byte, uint64Len+lengthOfscriptPubKeyLength+scriptPubKeyLength+len(coinbaseData.ExtraData))
|
||||
@ -35,7 +34,7 @@ func SerializeCoinbasePayload(blueScore uint64, coinbaseData *externalapi.Domain
|
||||
}
|
||||
|
||||
// ExtractCoinbaseDataAndBlueScore deserializes the coinbase payload to its component (scriptPubKey and extra data).
|
||||
func ExtractCoinbaseDataAndBlueScore(coinbaseTx *externalapi.DomainTransaction) (blueScore uint64,
|
||||
func (c coinbaseManager) ExtractCoinbaseDataAndBlueScore(coinbaseTx *externalapi.DomainTransaction) (blueScore uint64,
|
||||
coinbaseData *externalapi.DomainCoinbaseData, err error) {
|
||||
|
||||
minLength := uint64Len + lengthOfscriptPubKeyLength
|
||||
@ -47,9 +46,9 @@ func ExtractCoinbaseDataAndBlueScore(coinbaseTx *externalapi.DomainTransaction)
|
||||
blueScore = byteOrder.Uint64(coinbaseTx.Payload[:uint64Len])
|
||||
scriptPubKeyLength := coinbaseTx.Payload[uint64Len]
|
||||
|
||||
if scriptPubKeyLength > constants.CoinbasePayloadScriptPublicKeyMaxLength {
|
||||
if uint64(scriptPubKeyLength) > c.coinbasePayloadScriptPublicKeyMaxLength {
|
||||
return 0, nil, errors.Wrapf(ruleerrors.ErrBadCoinbasePayloadLen, "coinbase's payload script public key is "+
|
||||
"longer than the max allowed length of %d", constants.CoinbasePayloadScriptPublicKeyMaxLength)
|
||||
"longer than the max allowed length of %d", c.coinbasePayloadScriptPublicKeyMaxLength)
|
||||
}
|
||||
|
||||
if len(coinbaseTx.Payload) < minLength+int(scriptPubKeyLength) {
|
@ -2,7 +2,6 @@ package consensusstatemanager
|
||||
|
||||
import (
|
||||
"github.com/kaspanet/kaspad/domain/consensus/utils/consensushashing"
|
||||
"github.com/kaspanet/kaspad/domain/consensus/utils/constants"
|
||||
"github.com/kaspanet/kaspad/domain/consensus/utils/multiset"
|
||||
"github.com/kaspanet/kaspad/domain/consensus/utils/utxo"
|
||||
"github.com/pkg/errors"
|
||||
@ -242,7 +241,7 @@ func (csm *consensusStateManager) checkTransactionMass(
|
||||
|
||||
// We could potentially overflow the accumulator so check for
|
||||
// overflow as well.
|
||||
if accumulatedMassAfter < transaction.Mass || accumulatedMassAfter > constants.MaxMassAcceptedByBlock {
|
||||
if accumulatedMassAfter < transaction.Mass || accumulatedMassAfter > csm.maxMassAcceptedByBlock {
|
||||
return false, 0
|
||||
}
|
||||
|
||||
|
@ -7,10 +7,13 @@ import (
|
||||
|
||||
// consensusStateManager manages the node's consensus state
|
||||
type consensusStateManager struct {
|
||||
finalityDepth uint64
|
||||
pruningDepth uint64
|
||||
genesisHash *externalapi.DomainHash
|
||||
databaseContext model.DBManager
|
||||
finalityDepth uint64
|
||||
pruningDepth uint64
|
||||
maxMassAcceptedByBlock uint64
|
||||
maxBlockParents model.KType
|
||||
mergeSetSizeLimit uint64
|
||||
genesisHash *externalapi.DomainHash
|
||||
databaseContext model.DBManager
|
||||
|
||||
ghostdagManager model.GHOSTDAGManager
|
||||
dagTopologyManager model.DAGTopologyManager
|
||||
@ -41,7 +44,11 @@ func New(
|
||||
databaseContext model.DBManager,
|
||||
finalityDepth uint64,
|
||||
pruningDepth uint64,
|
||||
maxMassAcceptedByBlock uint64,
|
||||
maxBlockParents model.KType,
|
||||
mergeSetSizeLimit uint64,
|
||||
genesisHash *externalapi.DomainHash,
|
||||
|
||||
ghostdagManager model.GHOSTDAGManager,
|
||||
dagTopologyManager model.DAGTopologyManager,
|
||||
dagTraversalManager model.DAGTraversalManager,
|
||||
@ -64,10 +71,13 @@ func New(
|
||||
headerTipsStore model.HeaderTipsStore) (model.ConsensusStateManager, error) {
|
||||
|
||||
csm := &consensusStateManager{
|
||||
finalityDepth: finalityDepth,
|
||||
pruningDepth: pruningDepth,
|
||||
genesisHash: genesisHash,
|
||||
databaseContext: databaseContext,
|
||||
finalityDepth: finalityDepth,
|
||||
pruningDepth: pruningDepth,
|
||||
maxMassAcceptedByBlock: maxMassAcceptedByBlock,
|
||||
maxBlockParents: maxBlockParents,
|
||||
mergeSetSizeLimit: mergeSetSizeLimit,
|
||||
genesisHash: genesisHash,
|
||||
databaseContext: databaseContext,
|
||||
|
||||
ghostdagManager: ghostdagManager,
|
||||
dagTopologyManager: dagTopologyManager,
|
||||
|
@ -5,7 +5,6 @@ import (
|
||||
|
||||
"github.com/kaspanet/kaspad/domain/consensus/model"
|
||||
"github.com/kaspanet/kaspad/domain/consensus/model/externalapi"
|
||||
"github.com/kaspanet/kaspad/domain/consensus/utils/constants"
|
||||
"github.com/kaspanet/kaspad/domain/consensus/utils/hashset"
|
||||
)
|
||||
|
||||
@ -34,9 +33,9 @@ func (csm *consensusStateManager) pickVirtualParents(tips []*externalapi.DomainH
|
||||
|
||||
selectedVirtualParents := hashset.NewFromSlice(virtualSelectedParent)
|
||||
|
||||
mergeSetSize := 1 // starts counting from 1 because selectedParent is already in the mergeSet
|
||||
mergeSetSize := uint64(1) // starts counting from 1 because selectedParent is already in the mergeSet
|
||||
|
||||
for candidatesHeap.Len() > 0 && len(selectedVirtualParents) < constants.MaxBlockParents {
|
||||
for candidatesHeap.Len() > 0 && uint64(len(selectedVirtualParents)) < uint64(csm.maxBlockParents) {
|
||||
candidate := candidatesHeap.Pop()
|
||||
|
||||
log.Tracef("Attempting to add %s to the virtual parents", candidate)
|
||||
@ -48,7 +47,7 @@ func (csm *consensusStateManager) pickVirtualParents(tips []*externalapi.DomainH
|
||||
}
|
||||
log.Tracef("The merge set would increase by %d with block %s", mergeSetIncrease, candidate)
|
||||
|
||||
if mergeSetSize+mergeSetIncrease > constants.MergeSetSizeLimit {
|
||||
if mergeSetSize+mergeSetIncrease > csm.mergeSetSizeLimit {
|
||||
log.Tracef("Cannot add block %s since that would violate the merge set size limit", candidate)
|
||||
continue
|
||||
}
|
||||
@ -130,7 +129,7 @@ func (csm *consensusStateManager) selectVirtualSelectedParent(
|
||||
}
|
||||
|
||||
func (csm *consensusStateManager) mergeSetIncrease(
|
||||
candidate *externalapi.DomainHash, selectedVirtualParents hashset.HashSet) (int, error) {
|
||||
candidate *externalapi.DomainHash, selectedVirtualParents hashset.HashSet) (uint64, error) {
|
||||
|
||||
log.Tracef("mergeSetIncrease start")
|
||||
defer log.Tracef("mergeSetIncrease end")
|
||||
@ -141,7 +140,7 @@ func (csm *consensusStateManager) mergeSetIncrease(
|
||||
if err != nil {
|
||||
return 0, err
|
||||
}
|
||||
mergeSetIncrease := 1 // starts with 1 for the candidate itself
|
||||
mergeSetIncrease := uint64(1) // starts with 1 for the candidate itself
|
||||
|
||||
for queue.Len() > 0 {
|
||||
current := queue.Pop()
|
||||
|
@ -5,7 +5,6 @@ import (
|
||||
|
||||
"github.com/kaspanet/kaspad/domain/consensus/utils/transactionhelper"
|
||||
|
||||
"github.com/kaspanet/kaspad/domain/consensus/utils/coinbase"
|
||||
"github.com/kaspanet/kaspad/domain/consensus/utils/transactionid"
|
||||
|
||||
"github.com/kaspanet/kaspad/domain/consensus/utils/consensushashing"
|
||||
@ -157,7 +156,7 @@ func (csm *consensusStateManager) validateCoinbaseTransaction(blockHash *externa
|
||||
|
||||
log.Tracef("Extracting coinbase data for coinbase transaction %s in block %s",
|
||||
consensushashing.TransactionID(coinbaseTransaction), blockHash)
|
||||
_, coinbaseData, err := coinbase.ExtractCoinbaseDataAndBlueScore(coinbaseTransaction)
|
||||
_, coinbaseData, err := csm.coinbaseManager.ExtractCoinbaseDataAndBlueScore(coinbaseTransaction)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
@ -18,6 +18,7 @@ type difficultyManager struct {
|
||||
headerStore model.BlockHeaderStore
|
||||
dagTopologyManager model.DAGTopologyManager
|
||||
dagTraversalManager model.DAGTraversalManager
|
||||
genesisHash *externalapi.DomainHash
|
||||
powMax *big.Int
|
||||
difficultyAdjustmentWindowSize uint64
|
||||
targetTimePerBlock time.Duration
|
||||
@ -34,6 +35,7 @@ func New(
|
||||
powMax *big.Int,
|
||||
difficultyAdjustmentWindowSize uint64,
|
||||
targetTimePerBlock time.Duration,
|
||||
genesisHash *externalapi.DomainHash,
|
||||
) model.DifficultyManager {
|
||||
return &difficultyManager{
|
||||
databaseContext: databaseContext,
|
||||
@ -45,9 +47,19 @@ func New(
|
||||
powMax: powMax,
|
||||
difficultyAdjustmentWindowSize: difficultyAdjustmentWindowSize,
|
||||
targetTimePerBlock: targetTimePerBlock,
|
||||
genesisHash: genesisHash,
|
||||
}
|
||||
}
|
||||
|
||||
func (dm *difficultyManager) genesisBits() (uint32, error) {
|
||||
header, err := dm.headerStore.BlockHeader(dm.databaseContext, dm.genesisHash)
|
||||
if err != nil {
|
||||
return 0, err
|
||||
}
|
||||
|
||||
return header.Bits, nil
|
||||
}
|
||||
|
||||
// RequiredDifficulty returns the difficulty required for some block
|
||||
func (dm *difficultyManager) RequiredDifficulty(blockHash *externalapi.DomainHash) (uint32, error) {
|
||||
|
||||
@ -57,7 +69,7 @@ func (dm *difficultyManager) RequiredDifficulty(blockHash *externalapi.DomainHas
|
||||
}
|
||||
// Genesis block
|
||||
if len(parents) == 0 {
|
||||
return util.BigToCompact(dm.powMax), nil
|
||||
return dm.genesisBits()
|
||||
}
|
||||
|
||||
// find bluestParent
|
||||
@ -83,7 +95,7 @@ func (dm *difficultyManager) RequiredDifficulty(blockHash *externalapi.DomainHas
|
||||
|
||||
// Not enough blocks for building a difficulty window.
|
||||
if bluestGhostDAG.BlueScore < dm.difficultyAdjustmentWindowSize+1 {
|
||||
return util.BigToCompact(dm.powMax), nil
|
||||
return dm.genesisBits()
|
||||
}
|
||||
|
||||
// Fetch window of dag.difficultyAdjustmentWindowSize + 1 so we can have dag.difficultyAdjustmentWindowSize block intervals
|
||||
|
@ -3,7 +3,6 @@ package transactionvalidator
|
||||
import (
|
||||
"github.com/kaspanet/kaspad/domain/consensus/model/externalapi"
|
||||
"github.com/kaspanet/kaspad/domain/consensus/ruleerrors"
|
||||
"github.com/kaspanet/kaspad/domain/consensus/utils/constants"
|
||||
"github.com/kaspanet/kaspad/domain/consensus/utils/estimatedsize"
|
||||
"github.com/kaspanet/kaspad/domain/consensus/utils/transactionhelper"
|
||||
"github.com/kaspanet/kaspad/domain/consensus/utils/txscript"
|
||||
@ -17,7 +16,7 @@ func (v *transactionValidator) transactionMassStandalonePart(tx *externalapi.Dom
|
||||
totalScriptPubKeySize += uint64(len(output.ScriptPublicKey))
|
||||
}
|
||||
|
||||
return size*constants.MassPerTxByte + totalScriptPubKeySize*constants.MassPerScriptPubKeyByte
|
||||
return size*v.massPerTxByte + totalScriptPubKeySize*v.massPerScriptPubKeyByte
|
||||
}
|
||||
|
||||
func (v *transactionValidator) transactionMass(tx *externalapi.DomainTransaction) (uint64, error) {
|
||||
@ -44,5 +43,5 @@ func (v *transactionValidator) transactionMass(tx *externalapi.DomainTransaction
|
||||
return 0, ruleerrors.NewErrMissingTxOut(missingOutpoints)
|
||||
}
|
||||
|
||||
return standaloneMass + sigOpsCount*constants.MassPerSigOp, nil
|
||||
return standaloneMass + sigOpsCount*v.massPerSigOp, nil
|
||||
}
|
||||
|
@ -116,10 +116,10 @@ func (v *transactionValidator) checkCoinbaseLength(tx *externalapi.DomainTransac
|
||||
|
||||
// Coinbase payload length must not exceed the max length.
|
||||
payloadLen := len(tx.Payload)
|
||||
if payloadLen > constants.MaxCoinbasePayloadLength {
|
||||
if uint64(payloadLen) > v.maxCoinbasePayloadLength {
|
||||
return errors.Wrapf(ruleerrors.ErrBadCoinbasePayloadLen, "coinbase transaction payload length "+
|
||||
"of %d is out of range (max: %d)",
|
||||
payloadLen, constants.MaxCoinbasePayloadLength)
|
||||
payloadLen, v.maxCoinbasePayloadLength)
|
||||
}
|
||||
|
||||
return nil
|
||||
|
@ -79,7 +79,7 @@ func TestValidateTransactionInIsolation(t *testing.T) {
|
||||
1,
|
||||
1,
|
||||
subnetworks.SubnetworkIDNative,
|
||||
&txSubnetworkData{subnetworks.SubnetworkIDCoinbase, 0, make([]byte, constants.MaxCoinbasePayloadLength+1)},
|
||||
&txSubnetworkData{subnetworks.SubnetworkIDCoinbase, 0, make([]byte, params.MaxCoinbasePayloadLength+1)},
|
||||
nil,
|
||||
ruleerrors.ErrBadCoinbasePayloadLen},
|
||||
{"non-zero gas in Kaspa", 1, 1, 0,
|
||||
|
@ -15,18 +15,30 @@ type transactionValidator struct {
|
||||
pastMedianTimeManager model.PastMedianTimeManager
|
||||
ghostdagDataStore model.GHOSTDAGDataStore
|
||||
enableNonNativeSubnetworks bool
|
||||
massPerTxByte uint64
|
||||
massPerScriptPubKeyByte uint64
|
||||
massPerSigOp uint64
|
||||
maxCoinbasePayloadLength uint64
|
||||
sigCache *txscript.SigCache
|
||||
}
|
||||
|
||||
// New instantiates a new TransactionValidator
|
||||
func New(blockCoinbaseMaturity uint64,
|
||||
enableNonNativeSubnetworks bool,
|
||||
massPerTxByte uint64,
|
||||
massPerScriptPubKeyByte uint64,
|
||||
massPerSigOp uint64,
|
||||
maxCoinbasePayloadLength uint64,
|
||||
databaseContext model.DBReader,
|
||||
pastMedianTimeManager model.PastMedianTimeManager,
|
||||
ghostdagDataStore model.GHOSTDAGDataStore) model.TransactionValidator {
|
||||
return &transactionValidator{
|
||||
blockCoinbaseMaturity: blockCoinbaseMaturity,
|
||||
enableNonNativeSubnetworks: enableNonNativeSubnetworks,
|
||||
massPerTxByte: massPerTxByte,
|
||||
massPerScriptPubKeyByte: massPerScriptPubKeyByte,
|
||||
massPerSigOp: massPerSigOp,
|
||||
maxCoinbasePayloadLength: maxCoinbasePayloadLength,
|
||||
databaseContext: databaseContext,
|
||||
pastMedianTimeManager: pastMedianTimeManager,
|
||||
ghostdagDataStore: ghostdagDataStore,
|
||||
|
@ -1,22 +0,0 @@
|
||||
package blocks
|
||||
|
||||
import (
|
||||
"errors"
|
||||
|
||||
"github.com/kaspanet/kaspad/domain/consensus/utils/coinbase"
|
||||
|
||||
"github.com/kaspanet/kaspad/domain/consensus/model/externalapi"
|
||||
"github.com/kaspanet/kaspad/domain/consensus/utils/transactionhelper"
|
||||
)
|
||||
|
||||
// ExtractBlueScore extracts the block's blue score out of it's coinbase transaction's payload
|
||||
func ExtractBlueScore(block *externalapi.DomainBlock) (uint64, error) {
|
||||
if len(block.Transactions) < transactionhelper.CoinbaseTransactionIndex+1 {
|
||||
return 0, errors.New("Block has no coinbase transaction")
|
||||
}
|
||||
|
||||
coinbaseTransaction := block.Transactions[transactionhelper.CoinbaseTransactionIndex]
|
||||
|
||||
blueScore, _, err := coinbase.ExtractCoinbaseDataAndBlueScore(coinbaseTransaction)
|
||||
return blueScore, err
|
||||
}
|
@ -16,39 +16,6 @@ const (
|
||||
// MaxSompi is the maximum transaction amount allowed in sompi.
|
||||
MaxSompi = 21_000_000 * SompiPerKaspa
|
||||
|
||||
// MaxCoinbasePayloadLength is the maximum length in bites allowed for a block's coinbase's payload
|
||||
MaxCoinbasePayloadLength = 150
|
||||
|
||||
// MaxBlockSize is the maximum size in bytes a block is allowed
|
||||
MaxBlockSize = 1_000_000
|
||||
|
||||
// MaxBlockParents is the maximum number of blocks a block is allowed to point to
|
||||
MaxBlockParents = 10
|
||||
|
||||
// MassPerTxByte is the number of grams that any byte
|
||||
// adds to a transaction.
|
||||
MassPerTxByte = 1
|
||||
|
||||
// MassPerScriptPubKeyByte is the number of grams that any
|
||||
// scriptPubKey byte adds to a transaction.
|
||||
MassPerScriptPubKeyByte = 10
|
||||
|
||||
// MassPerSigOp is the number of grams that any
|
||||
// signature operation adds to a transaction.
|
||||
MassPerSigOp = 10000
|
||||
|
||||
// MergeSetSizeLimit is the maximum number of blocks in a block's merge set
|
||||
MergeSetSizeLimit = 1000
|
||||
|
||||
// MaxMassAcceptedByBlock is the maximum total transaction mass a block may accept.
|
||||
MaxMassAcceptedByBlock = 10000000
|
||||
|
||||
// BaseSubsidy is the starting subsidy amount for mined blocks.
|
||||
BaseSubsidy = 50 * SompiPerKaspa
|
||||
|
||||
// CoinbasePayloadScriptPublicKeyMaxLength is the maximum allowed script public key in the coinbase's payload
|
||||
CoinbasePayloadScriptPublicKeyMaxLength = 150
|
||||
|
||||
// MaxTxInSequenceNum is the maximum sequence number the sequence field
|
||||
// of a transaction input can be.
|
||||
MaxTxInSequenceNum uint64 = math.MaxUint64
|
||||
|
24
domain/dagconfig/consensus_defaults.go
Normal file
24
domain/dagconfig/consensus_defaults.go
Normal file
@ -0,0 +1,24 @@
|
||||
package dagconfig
|
||||
|
||||
import (
|
||||
"github.com/kaspanet/kaspad/domain/consensus/utils/constants"
|
||||
"time"
|
||||
)
|
||||
|
||||
const (
|
||||
defaultMaxCoinbasePayloadLength = 150
|
||||
defaultMaxBlockSize = 1_000_000
|
||||
defaultMaxBlockParents = 10
|
||||
defaultMassPerTxByte = 1
|
||||
defaultMassPerScriptPubKeyByte = 10
|
||||
defaultMassPerSigOp = 10000
|
||||
defaultMergeSetSizeLimit = 1000
|
||||
defaultMaxMassAcceptedByBlock = 10000000
|
||||
defaultBaseSubsidy = 50 * constants.SompiPerKaspa
|
||||
defaultCoinbasePayloadScriptPublicKeyMaxLength = 150
|
||||
defaultGHOSTDAGK = 18
|
||||
defaultDifficultyAdjustmentWindowSize = 2640
|
||||
defaultTimestampDeviationTolerance = 132
|
||||
defaultFinalityDuration = 24 * time.Hour
|
||||
defaultTargetTimePerBlock = 1 * time.Second
|
||||
)
|
@ -5,11 +5,10 @@
|
||||
package dagconfig
|
||||
|
||||
import (
|
||||
"github.com/kaspanet/kaspad/domain/consensus/model"
|
||||
"math/big"
|
||||
"time"
|
||||
|
||||
"github.com/kaspanet/kaspad/domain/consensus/utils/constants"
|
||||
|
||||
"github.com/kaspanet/kaspad/domain/consensus/model/externalapi"
|
||||
|
||||
"github.com/kaspanet/kaspad/app/appmessage"
|
||||
@ -45,14 +44,6 @@ var (
|
||||
devnetPowMax = new(big.Int).Sub(new(big.Int).Lsh(bigOne, 239), bigOne)
|
||||
)
|
||||
|
||||
const (
|
||||
ghostdagK = 18
|
||||
difficultyAdjustmentWindowSize = 2640
|
||||
timestampDeviationTolerance = 132
|
||||
finalityDuration = 24 * time.Hour
|
||||
targetTimePerBlock = 1 * time.Second
|
||||
)
|
||||
|
||||
// KType defines the size of GHOSTDAG consensus algorithm K parameter.
|
||||
type KType uint8
|
||||
|
||||
@ -62,7 +53,7 @@ type KType uint8
|
||||
type Params struct {
|
||||
// K defines the K parameter for GHOSTDAG consensus algorithm.
|
||||
// See ghostdag.go for further details.
|
||||
K KType
|
||||
K model.KType
|
||||
|
||||
// Name defines a human-readable identifier for the network.
|
||||
Name string
|
||||
@ -150,6 +141,39 @@ type Params struct {
|
||||
|
||||
// SkipProofOfWork indicates whether proof of work should be checked.
|
||||
SkipProofOfWork bool
|
||||
|
||||
// MaxCoinbasePayloadLength is the maximum length in bytes allowed for a block's coinbase's payload
|
||||
MaxCoinbasePayloadLength uint64
|
||||
|
||||
// MaxBlockSize is the maximum size in bytes a block is allowed
|
||||
MaxBlockSize uint64
|
||||
|
||||
// MaxBlockParents is the maximum number of blocks a block is allowed to point to
|
||||
MaxBlockParents model.KType
|
||||
|
||||
// MassPerTxByte is the number of grams that any byte
|
||||
// adds to a transaction.
|
||||
MassPerTxByte uint64
|
||||
|
||||
// MassPerScriptPubKeyByte is the number of grams that any
|
||||
// scriptPubKey byte adds to a transaction.
|
||||
MassPerScriptPubKeyByte uint64
|
||||
|
||||
// MassPerSigOp is the number of grams that any
|
||||
// signature operation adds to a transaction.
|
||||
MassPerSigOp uint64
|
||||
|
||||
// MergeSetSizeLimit is the maximum number of blocks in a block's merge set
|
||||
MergeSetSizeLimit uint64
|
||||
|
||||
// MaxMassAcceptedByBlock is the maximum total transaction mass a block may accept.
|
||||
MaxMassAcceptedByBlock uint64
|
||||
|
||||
// CoinbasePayloadScriptPublicKeyMaxLength is the maximum allowed script public key in the coinbase's payload
|
||||
CoinbasePayloadScriptPublicKeyMaxLength uint64
|
||||
|
||||
// BaseSubsidy is the starting subsidy amount for mined blocks.
|
||||
BaseSubsidy uint64
|
||||
}
|
||||
|
||||
// NormalizeRPCServerAddress returns addr with the current network default
|
||||
@ -165,12 +189,12 @@ func (p *Params) FinalityDepth() uint64 {
|
||||
|
||||
// PruningDepth returns the pruning duration represented in blocks
|
||||
func (p *Params) PruningDepth() uint64 {
|
||||
return 2*p.FinalityDepth() + 4*constants.MergeSetSizeLimit*uint64(p.K) + 2*uint64(p.K) + 2
|
||||
return 2*p.FinalityDepth() + 4*p.MergeSetSizeLimit*uint64(p.K) + 2*uint64(p.K) + 2
|
||||
}
|
||||
|
||||
// MainnetParams defines the network parameters for the main Kaspa network.
|
||||
var MainnetParams = Params{
|
||||
K: ghostdagK,
|
||||
K: defaultGHOSTDAGK,
|
||||
Name: "kaspa-mainnet",
|
||||
Net: appmessage.Mainnet,
|
||||
RPCPort: "16110",
|
||||
@ -183,10 +207,10 @@ var MainnetParams = Params{
|
||||
PowMax: mainPowMax,
|
||||
BlockCoinbaseMaturity: 100,
|
||||
SubsidyReductionInterval: 210000,
|
||||
TargetTimePerBlock: targetTimePerBlock,
|
||||
FinalityDuration: finalityDuration,
|
||||
DifficultyAdjustmentWindowSize: difficultyAdjustmentWindowSize,
|
||||
TimestampDeviationTolerance: timestampDeviationTolerance,
|
||||
TargetTimePerBlock: defaultTargetTimePerBlock,
|
||||
FinalityDuration: defaultFinalityDuration,
|
||||
DifficultyAdjustmentWindowSize: defaultDifficultyAdjustmentWindowSize,
|
||||
TimestampDeviationTolerance: defaultTimestampDeviationTolerance,
|
||||
|
||||
// Consensus rule change deployments.
|
||||
//
|
||||
@ -212,11 +236,22 @@ var MainnetParams = Params{
|
||||
EnableNonNativeSubnetworks: false,
|
||||
|
||||
DisableDifficultyAdjustment: false,
|
||||
|
||||
MaxCoinbasePayloadLength: defaultMaxCoinbasePayloadLength,
|
||||
MaxBlockSize: defaultMaxBlockSize,
|
||||
MaxBlockParents: defaultMaxBlockParents,
|
||||
MassPerTxByte: defaultMassPerTxByte,
|
||||
MassPerScriptPubKeyByte: defaultMassPerScriptPubKeyByte,
|
||||
MassPerSigOp: defaultMassPerSigOp,
|
||||
MergeSetSizeLimit: defaultMergeSetSizeLimit,
|
||||
MaxMassAcceptedByBlock: defaultMaxMassAcceptedByBlock,
|
||||
BaseSubsidy: defaultBaseSubsidy,
|
||||
CoinbasePayloadScriptPublicKeyMaxLength: defaultCoinbasePayloadScriptPublicKeyMaxLength,
|
||||
}
|
||||
|
||||
// TestnetParams defines the network parameters for the test Kaspa network.
|
||||
var TestnetParams = Params{
|
||||
K: ghostdagK,
|
||||
K: defaultGHOSTDAGK,
|
||||
Name: "kaspa-testnet",
|
||||
Net: appmessage.Testnet,
|
||||
RPCPort: "16210",
|
||||
@ -229,10 +264,10 @@ var TestnetParams = Params{
|
||||
PowMax: testnetPowMax,
|
||||
BlockCoinbaseMaturity: 100,
|
||||
SubsidyReductionInterval: 210000,
|
||||
TargetTimePerBlock: targetTimePerBlock,
|
||||
FinalityDuration: finalityDuration,
|
||||
DifficultyAdjustmentWindowSize: difficultyAdjustmentWindowSize,
|
||||
TimestampDeviationTolerance: timestampDeviationTolerance,
|
||||
TargetTimePerBlock: defaultTargetTimePerBlock,
|
||||
FinalityDuration: defaultFinalityDuration,
|
||||
DifficultyAdjustmentWindowSize: defaultDifficultyAdjustmentWindowSize,
|
||||
TimestampDeviationTolerance: defaultTimestampDeviationTolerance,
|
||||
|
||||
// Consensus rule change deployments.
|
||||
//
|
||||
@ -258,6 +293,17 @@ var TestnetParams = Params{
|
||||
EnableNonNativeSubnetworks: false,
|
||||
|
||||
DisableDifficultyAdjustment: false,
|
||||
|
||||
MaxCoinbasePayloadLength: defaultMaxCoinbasePayloadLength,
|
||||
MaxBlockSize: defaultMaxBlockSize,
|
||||
MaxBlockParents: defaultMaxBlockParents,
|
||||
MassPerTxByte: defaultMassPerTxByte,
|
||||
MassPerScriptPubKeyByte: defaultMassPerScriptPubKeyByte,
|
||||
MassPerSigOp: defaultMassPerSigOp,
|
||||
MergeSetSizeLimit: defaultMergeSetSizeLimit,
|
||||
MaxMassAcceptedByBlock: defaultMaxMassAcceptedByBlock,
|
||||
BaseSubsidy: defaultBaseSubsidy,
|
||||
CoinbasePayloadScriptPublicKeyMaxLength: defaultCoinbasePayloadScriptPublicKeyMaxLength,
|
||||
}
|
||||
|
||||
// SimnetParams defines the network parameters for the simulation test Kaspa
|
||||
@ -268,7 +314,7 @@ var TestnetParams = Params{
|
||||
// following normal discovery rules. This is important as otherwise it would
|
||||
// just turn into another public testnet.
|
||||
var SimnetParams = Params{
|
||||
K: ghostdagK,
|
||||
K: defaultGHOSTDAGK,
|
||||
Name: "kaspa-simnet",
|
||||
Net: appmessage.Simnet,
|
||||
RPCPort: "16510",
|
||||
@ -283,8 +329,8 @@ var SimnetParams = Params{
|
||||
SubsidyReductionInterval: 210000,
|
||||
TargetTimePerBlock: time.Millisecond,
|
||||
FinalityDuration: time.Minute,
|
||||
DifficultyAdjustmentWindowSize: difficultyAdjustmentWindowSize,
|
||||
TimestampDeviationTolerance: timestampDeviationTolerance,
|
||||
DifficultyAdjustmentWindowSize: defaultDifficultyAdjustmentWindowSize,
|
||||
TimestampDeviationTolerance: defaultTimestampDeviationTolerance,
|
||||
|
||||
// Consensus rule change deployments.
|
||||
//
|
||||
@ -308,11 +354,22 @@ var SimnetParams = Params{
|
||||
EnableNonNativeSubnetworks: false,
|
||||
|
||||
DisableDifficultyAdjustment: true,
|
||||
|
||||
MaxCoinbasePayloadLength: defaultMaxCoinbasePayloadLength,
|
||||
MaxBlockSize: defaultMaxBlockSize,
|
||||
MaxBlockParents: defaultMaxBlockParents,
|
||||
MassPerTxByte: defaultMassPerTxByte,
|
||||
MassPerScriptPubKeyByte: defaultMassPerScriptPubKeyByte,
|
||||
MassPerSigOp: defaultMassPerSigOp,
|
||||
MergeSetSizeLimit: defaultMergeSetSizeLimit,
|
||||
MaxMassAcceptedByBlock: defaultMaxMassAcceptedByBlock,
|
||||
BaseSubsidy: defaultBaseSubsidy,
|
||||
CoinbasePayloadScriptPublicKeyMaxLength: defaultCoinbasePayloadScriptPublicKeyMaxLength,
|
||||
}
|
||||
|
||||
// DevnetParams defines the network parameters for the development Kaspa network.
|
||||
var DevnetParams = Params{
|
||||
K: ghostdagK,
|
||||
K: defaultGHOSTDAGK,
|
||||
Name: "kaspa-devnet",
|
||||
Net: appmessage.Devnet,
|
||||
RPCPort: "16610",
|
||||
@ -325,10 +382,10 @@ var DevnetParams = Params{
|
||||
PowMax: devnetPowMax,
|
||||
BlockCoinbaseMaturity: 100,
|
||||
SubsidyReductionInterval: 210000,
|
||||
TargetTimePerBlock: targetTimePerBlock,
|
||||
FinalityDuration: finalityDuration,
|
||||
DifficultyAdjustmentWindowSize: difficultyAdjustmentWindowSize,
|
||||
TimestampDeviationTolerance: timestampDeviationTolerance,
|
||||
TargetTimePerBlock: defaultTargetTimePerBlock,
|
||||
FinalityDuration: defaultFinalityDuration,
|
||||
DifficultyAdjustmentWindowSize: defaultDifficultyAdjustmentWindowSize,
|
||||
TimestampDeviationTolerance: defaultTimestampDeviationTolerance,
|
||||
|
||||
// Consensus rule change deployments.
|
||||
//
|
||||
@ -354,6 +411,17 @@ var DevnetParams = Params{
|
||||
EnableNonNativeSubnetworks: false,
|
||||
|
||||
DisableDifficultyAdjustment: false,
|
||||
|
||||
MaxCoinbasePayloadLength: defaultMaxCoinbasePayloadLength,
|
||||
MaxBlockSize: defaultMaxBlockSize,
|
||||
MaxBlockParents: defaultMaxBlockParents,
|
||||
MassPerTxByte: defaultMassPerTxByte,
|
||||
MassPerScriptPubKeyByte: defaultMassPerScriptPubKeyByte,
|
||||
MassPerSigOp: defaultMassPerSigOp,
|
||||
MergeSetSizeLimit: defaultMergeSetSizeLimit,
|
||||
MaxMassAcceptedByBlock: defaultMaxMassAcceptedByBlock,
|
||||
BaseSubsidy: defaultBaseSubsidy,
|
||||
CoinbasePayloadScriptPublicKeyMaxLength: defaultCoinbasePayloadScriptPublicKeyMaxLength,
|
||||
}
|
||||
|
||||
var (
|
||||
|
@ -3,7 +3,6 @@ package domain
|
||||
import (
|
||||
"github.com/kaspanet/kaspad/domain/consensus"
|
||||
"github.com/kaspanet/kaspad/domain/consensus/model/externalapi"
|
||||
"github.com/kaspanet/kaspad/domain/consensus/utils/constants"
|
||||
"github.com/kaspanet/kaspad/domain/dagconfig"
|
||||
"github.com/kaspanet/kaspad/domain/miningmanager"
|
||||
infrastructuredatabase "github.com/kaspanet/kaspad/infrastructure/db/database"
|
||||
@ -37,7 +36,8 @@ func New(dagParams *dagconfig.Params, db infrastructuredatabase.Database) (Domai
|
||||
}
|
||||
|
||||
miningManagerFactory := miningmanager.NewFactory()
|
||||
miningManager := miningManagerFactory.NewMiningManager(consensusInstance, constants.MaxMassAcceptedByBlock)
|
||||
miningManager := miningManagerFactory.NewMiningManager(consensusInstance, dagParams.MaxMassAcceptedByBlock,
|
||||
dagParams.RelayNonStdTxs)
|
||||
|
||||
return &domain{
|
||||
consensus: consensusInstance,
|
||||
|
@ -8,14 +8,14 @@ import (
|
||||
|
||||
// Factory instantiates new mining managers
|
||||
type Factory interface {
|
||||
NewMiningManager(consensus externalapi.Consensus, blockMaxMass uint64) MiningManager
|
||||
NewMiningManager(consensus externalapi.Consensus, blockMaxMass uint64, acceptNonStd bool) MiningManager
|
||||
}
|
||||
|
||||
type factory struct{}
|
||||
|
||||
// NewMiningManager instantiate a new mining manager
|
||||
func (f *factory) NewMiningManager(consensus externalapi.Consensus, blockMaxMass uint64) MiningManager {
|
||||
mempool := mempoolpkg.New(consensus)
|
||||
func (f *factory) NewMiningManager(consensus externalapi.Consensus, blockMaxMass uint64, acceptNonStd bool) MiningManager {
|
||||
mempool := mempoolpkg.New(consensus, acceptNonStd)
|
||||
blockTemplateBuilder := blocktemplatebuilder.New(consensus, mempool, blockMaxMass)
|
||||
|
||||
return &miningManager{
|
||||
|
@ -90,10 +90,10 @@ type mempool struct {
|
||||
|
||||
// New returns a new memory pool for validating and storing standalone
|
||||
// transactions until they are mined into a block.
|
||||
func New(consensus consensusexternalapi.Consensus) miningmanagermodel.Mempool {
|
||||
func New(consensus consensusexternalapi.Consensus, acceptNonStd bool) miningmanagermodel.Mempool {
|
||||
policy := policy{
|
||||
MaxTxVersion: constants.TransactionVersion,
|
||||
AcceptNonStd: false,
|
||||
AcceptNonStd: acceptNonStd,
|
||||
MaxOrphanTxs: 5,
|
||||
MaxOrphanTxSize: 100000,
|
||||
MinRelayTxFee: 1000, // 1 sompi per byte
|
||||
|
@ -1,21 +1,53 @@
|
||||
package config
|
||||
|
||||
import (
|
||||
"encoding/json"
|
||||
"fmt"
|
||||
"github.com/jessevdk/go-flags"
|
||||
"github.com/kaspanet/kaspad/domain/consensus/model"
|
||||
"github.com/kaspanet/kaspad/domain/consensus/utils/math"
|
||||
"github.com/kaspanet/kaspad/domain/dagconfig"
|
||||
"github.com/pkg/errors"
|
||||
"math/big"
|
||||
"os"
|
||||
"time"
|
||||
)
|
||||
|
||||
// NetworkFlags holds the network configuration, that is which network is selected.
|
||||
type NetworkFlags struct {
|
||||
Testnet bool `long:"testnet" description:"Use the test network"`
|
||||
Simnet bool `long:"simnet" description:"Use the simulation test network"`
|
||||
Devnet bool `long:"devnet" description:"Use the development test network"`
|
||||
Testnet bool `long:"testnet" description:"Use the test network"`
|
||||
Simnet bool `long:"simnet" description:"Use the simulation test network"`
|
||||
Devnet bool `long:"devnet" description:"Use the development test network"`
|
||||
OverrideDAGParamsFile string `long:"override-dag-params-file" description:"Overrides DAG params (allowed only on devnet)"`
|
||||
|
||||
ActiveNetParams *dagconfig.Params
|
||||
}
|
||||
|
||||
type overrideDAGParamsConfig struct {
|
||||
K *model.KType `json:"k"`
|
||||
MaxBlockParents *model.KType `json:"maxBlockParents"`
|
||||
MergeSetSizeLimit *uint64 `json:"mergeSetSizeLimit"`
|
||||
MaxMassAcceptedByBlock *uint64 `json:"maxMassAcceptedByBlock"`
|
||||
MaxBlockSize *uint64 `json:"maxBlockSize"`
|
||||
MaxCoinbasePayloadLength *uint64 `json:"maxCoinbasePayloadLength"`
|
||||
MassPerTxByte *uint64 `json:"massPerTxByte"`
|
||||
MassPerScriptPubKeyByte *uint64 `json:"massPerScriptPubKeyByte"`
|
||||
MassPerSigOp *uint64 `json:"massPerSigOp"`
|
||||
CoinbasePayloadScriptPublicKeyMaxLength *uint64 `json:"coinbasePayloadScriptPublicKeyMaxLength"`
|
||||
PowMax *string `json:"powMax"`
|
||||
BlockCoinbaseMaturity *uint64 `json:"blockCoinbaseMaturity"`
|
||||
SubsidyReductionInterval *uint64 `json:"subsidyReductionInterval"`
|
||||
TargetTimePerBlockInMilliSeconds *int64 `json:"targetTimePerBlockInMilliSeconds"`
|
||||
FinalityDuration *int64 `json:"finalityDuration"`
|
||||
TimestampDeviationTolerance *uint64 `json:"timestampDeviationTolerance"`
|
||||
DifficultyAdjustmentWindowSize *uint64 `json:"difficultyAdjustmentWindowSize"`
|
||||
RelayNonStdTxs *bool `json:"relayNonStdTxs"`
|
||||
AcceptUnroutable *bool `json:"acceptUnroutable"`
|
||||
EnableNonNativeSubnetworks *bool `json:"enableNonNativeSubnetworks"`
|
||||
DisableDifficultyAdjustment *bool `json:"disableDifficultyAdjustment"`
|
||||
SkipProofOfWork *bool `json:"skipProofOfWork"`
|
||||
}
|
||||
|
||||
// ResolveNetwork parses the network command line argument and sets NetParams accordingly.
|
||||
// It returns error if more than one network was selected, nil otherwise.
|
||||
func (networkFlags *NetworkFlags) ResolveNetwork(parser *flags.Parser) error {
|
||||
@ -58,3 +90,128 @@ func (networkFlags *NetworkFlags) ResolveNetwork(parser *flags.Parser) error {
|
||||
func (networkFlags *NetworkFlags) NetParams() *dagconfig.Params {
|
||||
return networkFlags.ActiveNetParams
|
||||
}
|
||||
|
||||
func (networkFlags *NetworkFlags) overrideDAGParams() error {
|
||||
|
||||
if networkFlags.OverrideDAGParamsFile == "" {
|
||||
return nil
|
||||
}
|
||||
|
||||
if !networkFlags.Devnet {
|
||||
return errors.Errorf("override-dag-params-file is allowed only when using devnet")
|
||||
}
|
||||
|
||||
overrideDAGParamsFile, err := os.Open(networkFlags.OverrideDAGParamsFile)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
defer overrideDAGParamsFile.Close()
|
||||
|
||||
decoder := json.NewDecoder(overrideDAGParamsFile)
|
||||
config := &overrideDAGParamsConfig{}
|
||||
err = decoder.Decode(config)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
if config.K != nil {
|
||||
networkFlags.ActiveNetParams.K = *config.K
|
||||
}
|
||||
|
||||
if config.MaxBlockParents != nil {
|
||||
networkFlags.ActiveNetParams.MaxBlockParents = *config.MaxBlockParents
|
||||
}
|
||||
|
||||
if config.MergeSetSizeLimit != nil {
|
||||
networkFlags.ActiveNetParams.MergeSetSizeLimit = *config.MergeSetSizeLimit
|
||||
}
|
||||
|
||||
if config.MaxMassAcceptedByBlock != nil {
|
||||
networkFlags.ActiveNetParams.MaxMassAcceptedByBlock = *config.MaxMassAcceptedByBlock
|
||||
}
|
||||
|
||||
if config.MaxBlockSize != nil {
|
||||
networkFlags.ActiveNetParams.MaxBlockSize = *config.MaxBlockSize
|
||||
}
|
||||
|
||||
if config.MaxCoinbasePayloadLength != nil {
|
||||
networkFlags.ActiveNetParams.MaxCoinbasePayloadLength = *config.MaxCoinbasePayloadLength
|
||||
}
|
||||
|
||||
if config.MassPerTxByte != nil {
|
||||
networkFlags.ActiveNetParams.MassPerTxByte = *config.MassPerTxByte
|
||||
}
|
||||
|
||||
if config.MassPerScriptPubKeyByte != nil {
|
||||
networkFlags.ActiveNetParams.MassPerScriptPubKeyByte = *config.MassPerScriptPubKeyByte
|
||||
}
|
||||
|
||||
if config.MassPerSigOp != nil {
|
||||
networkFlags.ActiveNetParams.MassPerSigOp = *config.MassPerSigOp
|
||||
}
|
||||
|
||||
if config.CoinbasePayloadScriptPublicKeyMaxLength != nil {
|
||||
networkFlags.ActiveNetParams.CoinbasePayloadScriptPublicKeyMaxLength = *config.CoinbasePayloadScriptPublicKeyMaxLength
|
||||
}
|
||||
|
||||
if config.PowMax != nil {
|
||||
powMax, ok := big.NewInt(0).SetString(*config.PowMax, 16)
|
||||
if !ok {
|
||||
return errors.Errorf("couldn't convert %s to big int", *config.PowMax)
|
||||
}
|
||||
|
||||
genesisTarget := math.CompactToBig(networkFlags.ActiveNetParams.GenesisBlock.Header.Bits)
|
||||
if powMax.Cmp(genesisTarget) > 0 {
|
||||
return errors.Errorf("powMax (%s) is smaller than genesis's target (%s)", powMax.Text(16),
|
||||
genesisTarget.Text(16))
|
||||
}
|
||||
networkFlags.ActiveNetParams.PowMax = powMax
|
||||
}
|
||||
|
||||
if config.BlockCoinbaseMaturity != nil {
|
||||
networkFlags.ActiveNetParams.BlockCoinbaseMaturity = *config.BlockCoinbaseMaturity
|
||||
}
|
||||
|
||||
if config.SubsidyReductionInterval != nil {
|
||||
networkFlags.ActiveNetParams.SubsidyReductionInterval = *config.SubsidyReductionInterval
|
||||
}
|
||||
|
||||
if config.TargetTimePerBlockInMilliSeconds != nil {
|
||||
networkFlags.ActiveNetParams.TargetTimePerBlock = time.Duration(*config.TargetTimePerBlockInMilliSeconds) *
|
||||
time.Millisecond
|
||||
}
|
||||
|
||||
if config.FinalityDuration != nil {
|
||||
networkFlags.ActiveNetParams.FinalityDuration = time.Duration(*config.FinalityDuration) * time.Millisecond
|
||||
}
|
||||
|
||||
if config.TimestampDeviationTolerance != nil {
|
||||
networkFlags.ActiveNetParams.TimestampDeviationTolerance = *config.TimestampDeviationTolerance
|
||||
}
|
||||
|
||||
if config.DifficultyAdjustmentWindowSize != nil {
|
||||
networkFlags.ActiveNetParams.DifficultyAdjustmentWindowSize = *config.DifficultyAdjustmentWindowSize
|
||||
}
|
||||
|
||||
if config.TimestampDeviationTolerance != nil {
|
||||
networkFlags.ActiveNetParams.TimestampDeviationTolerance = *config.TimestampDeviationTolerance
|
||||
}
|
||||
|
||||
if config.RelayNonStdTxs != nil {
|
||||
networkFlags.ActiveNetParams.RelayNonStdTxs = *config.RelayNonStdTxs
|
||||
}
|
||||
|
||||
if config.AcceptUnroutable != nil {
|
||||
networkFlags.ActiveNetParams.AcceptUnroutable = *config.AcceptUnroutable
|
||||
}
|
||||
|
||||
if config.EnableNonNativeSubnetworks != nil {
|
||||
networkFlags.ActiveNetParams.EnableNonNativeSubnetworks = *config.EnableNonNativeSubnetworks
|
||||
}
|
||||
|
||||
if config.SkipProofOfWork != nil {
|
||||
networkFlags.ActiveNetParams.SkipProofOfWork = *config.SkipProofOfWork
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
|
Loading…
x
Reference in New Issue
Block a user