mirror of
https://github.com/kaspanet/kaspad.git
synced 2025-06-07 06:36:46 +00:00
Sync pruning point UTXO sets incrementally instead of all at once (#1431)
* Replaced the content of MsgIBDRootUTXOSetChunk with pairs of outpoint-utxo entry pairs. * Rename utxoIter to utxoIterator. * Add a big stinky TODO on an assert. * Replace pruningStore staging with a UTXO set iterator. * Reimplement receiveAndInsertIBDRootUTXOSet. * Extract OutpointAndUTXOEntryPairsToDomainOutpointAndUTXOEntryPairs into domainconverters.go. * Pass the outpoint and utxy entry pairs to the pruning store. * Implement InsertCandidatePruningPointUTXOs. * Implement ClearCandidatePruningPointUTXOs. * Implement UpdateCandidatePruningPointMultiset. * Use the candidate pruning point multiset in updatePruningPoint. * Implement CandidatePruningPointUTXOIterator. * Use the pruning point utxo set iterator for StageVirtualUTXOSet. * Defer ClearCandidatePruningPointUTXOs. * Implement OverwriteVirtualUTXOSet. * Implement CommitCandidatePruningPointUTXOSet. * Implement BeginOverwritingVirtualUTXOSet and FinishOverwritingVirtualUTXOSet. * Implement overwriteVirtualUTXOSetAndCommitPruningPointUTXOSet. * Rename ClearCandidatePruningPointUTXOs to ClearCandidatePruningPointData. * Add missing methods to dbManager. * Implement PruningPointUTXOs. * Implement RecoverUTXOIfRequired. * Delete the utxoserialization package. * Fix compilation errors in TestValidateAndInsertPruningPoint. * Switch order of operations in the if statements in PruningPointUTXOs so that Next() wouldn't be unnecessarily called. * Fix missing pruning point utxo set staging and bad slice length. * Fix no default multiset in InsertCandidatePruningPointUTXOs. * Make go vet happy. * Rename candidateXXX to importedXXX. * Do some more renaming. * Rename some more. * Fix bad MsgIBDRootNotFound logic. * Fix an error message. * Simplify receiveIBDRootBlock. * Fix error message in receiveAndInsertIBDRootUTXOSet. * Do some more renaming. * Fix merge errors. * Fix a bug caused by calling iterator.First() unnecessarily. * Remove databaseContext from stores and don't use a transaction in ClearXXX functions. * Simplify receiveAndInsertIBDRootUTXOSet. * Fix offset count in PruningPointUTXOs(). * Fix readOnlyUTXOIteratorWithDiff.First(). * Split handleRequestIBDRootUTXOSetAndBlockFlow into smaller methods. * Rename IbdRootNotFound to UnexpectedPruningPoint. * Rename requestIBDRootHash to requestPruningPointHash. * Rename IBDRootHash to PruningPointHash. * Rename RequestIBDRootUTXOSetAndBlock to RequestPruningPointUTXOSetAndBlock. * Rename IBDRootUTXOSetChunk to PruningPointUTXOSetChunk. * Rename RequestNextIBDRootUTXOSetChunk to RequestNextPruningPointUTXOSetChunk. * Rename DoneIBDRootUTXOSetChunks to DonePruningPointUTXOSetChunks. * Rename remaining references to IBD root. * Fix an error message. * Add a check for HadStartedImportingPruningPointUTXOSet in commitVirtualUTXODiff. * Add a check for HadStartedImportingPruningPointUTXOSet in ImportPruningPointUTXOSetIntoVirtualUTXOSet. * Move FinishImportingPruningPointUTXOSet closer to HadStartedImportingPruningPointUTXOSet. * Remove reference to pruningStore in utxoSetIterator. * Pointerify utxoSetIterator receivers. * Fix bad insert in CommitImportedPruningPointUTXOSet. * Rename commitImportedPruningPointUTXOSetAll to applyImportedPruningPointUTXOSet. * Simplify PruningPointUTXOs. * Add populateTransactionWithUTXOEntriesFromUTXOSet. * Fix a TODO comment. * Rename InsertImportedPruningPointUTXOs to AppendImportedPruningPointUTXOs. * Extract handleRequestPruningPointUTXOSetAndBlockMessage to a separate method. * Rename stuff in readOnlyUTXOIteratorWithDiff.First(). * Address toAddIterator in readOnlyUTXOIteratorWithDiff.First(). * Call First() before any full iteration on ReadOnlyUTXOSetIterator. * Call First() before any full iteration on a database Cursor. * Put StartImportingPruningPointUTXOSet inside the pruning point transaction. * Make serializeOutpoint and serializeUTXOEntry free functions in pruningStore. * Fix readOnlyUTXOIteratorWithDiff.First(). * Fix bad validations in importPruningPoint. * Remove superfluous call to validateBlockTransactionsAgainstPastUTXO.
This commit is contained in:
parent
6a03d31f98
commit
756f40c59a
@ -3,6 +3,7 @@ package appmessage
|
||||
import (
|
||||
"encoding/hex"
|
||||
"github.com/kaspanet/kaspad/domain/consensus/utils/blockheader"
|
||||
"github.com/kaspanet/kaspad/domain/consensus/utils/utxo"
|
||||
|
||||
"github.com/kaspanet/kaspad/domain/consensus/model/externalapi"
|
||||
"github.com/kaspanet/kaspad/domain/consensus/utils/subnetworks"
|
||||
@ -268,3 +269,49 @@ func DomainTransactionToRPCTransaction(transaction *externalapi.DomainTransactio
|
||||
Payload: payload,
|
||||
}
|
||||
}
|
||||
|
||||
// OutpointAndUTXOEntryPairsToDomainOutpointAndUTXOEntryPairs converts
|
||||
// OutpointAndUTXOEntryPairs to domain OutpointAndUTXOEntryPairs
|
||||
func OutpointAndUTXOEntryPairsToDomainOutpointAndUTXOEntryPairs(
|
||||
outpointAndUTXOEntryPairs []*OutpointAndUTXOEntryPair) []*externalapi.OutpointAndUTXOEntryPair {
|
||||
|
||||
domainOutpointAndUTXOEntryPairs := make([]*externalapi.OutpointAndUTXOEntryPair, len(outpointAndUTXOEntryPairs))
|
||||
for i, outpointAndUTXOEntryPair := range outpointAndUTXOEntryPairs {
|
||||
domainOutpointAndUTXOEntryPairs[i] = &externalapi.OutpointAndUTXOEntryPair{
|
||||
Outpoint: &externalapi.DomainOutpoint{
|
||||
TransactionID: outpointAndUTXOEntryPair.Outpoint.TxID,
|
||||
Index: outpointAndUTXOEntryPair.Outpoint.Index,
|
||||
},
|
||||
UTXOEntry: utxo.NewUTXOEntry(
|
||||
outpointAndUTXOEntryPair.UTXOEntry.Amount,
|
||||
outpointAndUTXOEntryPair.UTXOEntry.ScriptPublicKey,
|
||||
outpointAndUTXOEntryPair.UTXOEntry.IsCoinbase,
|
||||
outpointAndUTXOEntryPair.UTXOEntry.BlockBlueScore,
|
||||
),
|
||||
}
|
||||
}
|
||||
return domainOutpointAndUTXOEntryPairs
|
||||
}
|
||||
|
||||
// DomainOutpointAndUTXOEntryPairsToOutpointAndUTXOEntryPairs converts
|
||||
// domain OutpointAndUTXOEntryPairs to OutpointAndUTXOEntryPairs
|
||||
func DomainOutpointAndUTXOEntryPairsToOutpointAndUTXOEntryPairs(
|
||||
outpointAndUTXOEntryPairs []*externalapi.OutpointAndUTXOEntryPair) []*OutpointAndUTXOEntryPair {
|
||||
|
||||
domainOutpointAndUTXOEntryPairs := make([]*OutpointAndUTXOEntryPair, len(outpointAndUTXOEntryPairs))
|
||||
for i, outpointAndUTXOEntryPair := range outpointAndUTXOEntryPairs {
|
||||
domainOutpointAndUTXOEntryPairs[i] = &OutpointAndUTXOEntryPair{
|
||||
Outpoint: &Outpoint{
|
||||
TxID: outpointAndUTXOEntryPair.Outpoint.TransactionID,
|
||||
Index: outpointAndUTXOEntryPair.Outpoint.Index,
|
||||
},
|
||||
UTXOEntry: &UTXOEntry{
|
||||
Amount: outpointAndUTXOEntryPair.UTXOEntry.Amount(),
|
||||
ScriptPublicKey: outpointAndUTXOEntryPair.UTXOEntry.ScriptPublicKey(),
|
||||
IsCoinbase: outpointAndUTXOEntryPair.UTXOEntry.IsCoinbase(),
|
||||
BlockBlueScore: outpointAndUTXOEntryPair.UTXOEntry.BlockBlueScore(),
|
||||
},
|
||||
}
|
||||
}
|
||||
return domainOutpointAndUTXOEntryPairs
|
||||
}
|
||||
|
@ -51,17 +51,17 @@ const (
|
||||
CmdReject
|
||||
CmdHeader
|
||||
CmdRequestNextHeaders
|
||||
CmdRequestIBDRootUTXOSetAndBlock
|
||||
CmdIBDRootUTXOSetChunk
|
||||
CmdRequestPruningPointUTXOSetAndBlock
|
||||
CmdPruningPointUTXOSetChunk
|
||||
CmdRequestIBDBlocks
|
||||
CmdIBDRootNotFound
|
||||
CmdRequestIBDRootHash
|
||||
CmdIBDRootHash
|
||||
CmdUnexpectedPruningPoint
|
||||
CmdRequestPruningPointHash
|
||||
CmdPruningPointHash
|
||||
CmdIBDBlockLocator
|
||||
CmdIBDBlockLocatorHighestHash
|
||||
CmdBlockHeaders
|
||||
CmdRequestNextIBDRootUTXOSetChunk
|
||||
CmdDoneIBDRootUTXOSetChunks
|
||||
CmdRequestNextPruningPointUTXOSetChunk
|
||||
CmdDonePruningPointUTXOSetChunks
|
||||
|
||||
// rpc
|
||||
CmdGetCurrentNetworkRequestMessage
|
||||
@ -148,17 +148,17 @@ var ProtocolMessageCommandToString = map[MessageCommand]string{
|
||||
CmdReject: "Reject",
|
||||
CmdHeader: "Header",
|
||||
CmdRequestNextHeaders: "RequestNextHeaders",
|
||||
CmdRequestIBDRootUTXOSetAndBlock: "RequestPruningUTXOSetAndBlock",
|
||||
CmdIBDRootUTXOSetChunk: "IBDRootUTXOSetChunk",
|
||||
CmdRequestPruningPointUTXOSetAndBlock: "RequestPruningPointUTXOSetAndBlock",
|
||||
CmdPruningPointUTXOSetChunk: "PruningPointUTXOSetChunk",
|
||||
CmdRequestIBDBlocks: "RequestIBDBlocks",
|
||||
CmdIBDRootNotFound: "IBDRootNotFound",
|
||||
CmdRequestIBDRootHash: "IBDRequestIBDRootHash",
|
||||
CmdIBDRootHash: "IBDIBDRootHash",
|
||||
CmdUnexpectedPruningPoint: "UnexpectedPruningPoint",
|
||||
CmdRequestPruningPointHash: "RequestPruningPointHashHash",
|
||||
CmdPruningPointHash: "PruningPointHash",
|
||||
CmdIBDBlockLocator: "IBDBlockLocator",
|
||||
CmdIBDBlockLocatorHighestHash: "IBDBlockLocatorHighestHash",
|
||||
CmdBlockHeaders: "BlockHeaders",
|
||||
CmdRequestNextIBDRootUTXOSetChunk: "RequestNextIBDRootUTXOSetChunk",
|
||||
CmdDoneIBDRootUTXOSetChunks: "DoneIBDRootUTXOSetChunks",
|
||||
CmdRequestNextPruningPointUTXOSetChunk: "RequestNextPruningPointUTXOSetChunk",
|
||||
CmdDonePruningPointUTXOSetChunks: "DonePruningPointUTXOSetChunks",
|
||||
}
|
||||
|
||||
// RPCMessageCommandToString maps all MessageCommands to their string representation
|
||||
|
@ -1,22 +0,0 @@
|
||||
package appmessage
|
||||
|
||||
// MsgIBDRootNotFound implements the Message interface and represents a kaspa
|
||||
// IBDRootNotFound message. It is used to notify the IBD root that was requested
|
||||
// by other peer was not found.
|
||||
//
|
||||
// This message has no payload.
|
||||
type MsgIBDRootNotFound struct {
|
||||
baseMessage
|
||||
}
|
||||
|
||||
// Command returns the protocol command string for the message. This is part
|
||||
// of the Message interface implementation.
|
||||
func (msg *MsgIBDRootNotFound) Command() MessageCommand {
|
||||
return CmdIBDRootNotFound
|
||||
}
|
||||
|
||||
// NewMsgIBDRootNotFound returns a new kaspa IBDRootNotFound message that conforms to the
|
||||
// Message interface.
|
||||
func NewMsgIBDRootNotFound() *MsgIBDRootNotFound {
|
||||
return &MsgIBDRootNotFound{}
|
||||
}
|
@ -1,16 +0,0 @@
|
||||
package appmessage
|
||||
|
||||
// MsgDoneIBDRootUTXOSetChunks represents a kaspa DoneIBDRootUTXOSetChunks message
|
||||
type MsgDoneIBDRootUTXOSetChunks struct {
|
||||
baseMessage
|
||||
}
|
||||
|
||||
// Command returns the protocol command string for the message
|
||||
func (msg *MsgDoneIBDRootUTXOSetChunks) Command() MessageCommand {
|
||||
return CmdDoneIBDRootUTXOSetChunks
|
||||
}
|
||||
|
||||
// NewMsgDoneIBDRootUTXOSetChunks returns a new MsgDoneIBDRootUTXOSetChunks.
|
||||
func NewMsgDoneIBDRootUTXOSetChunks() *MsgDoneIBDRootUTXOSetChunks {
|
||||
return &MsgDoneIBDRootUTXOSetChunks{}
|
||||
}
|
16
app/appmessage/p2p_msgdonepruningpointutxosetchunks.go
Normal file
16
app/appmessage/p2p_msgdonepruningpointutxosetchunks.go
Normal file
@ -0,0 +1,16 @@
|
||||
package appmessage
|
||||
|
||||
// MsgDonePruningPointUTXOSetChunks represents a kaspa DonePruningPointUTXOSetChunks message
|
||||
type MsgDonePruningPointUTXOSetChunks struct {
|
||||
baseMessage
|
||||
}
|
||||
|
||||
// Command returns the protocol command string for the message
|
||||
func (msg *MsgDonePruningPointUTXOSetChunks) Command() MessageCommand {
|
||||
return CmdDonePruningPointUTXOSetChunks
|
||||
}
|
||||
|
||||
// NewMsgDonePruningPointUTXOSetChunks returns a new MsgDonePruningPointUTXOSetChunks.
|
||||
func NewMsgDonePruningPointUTXOSetChunks() *MsgDonePruningPointUTXOSetChunks {
|
||||
return &MsgDonePruningPointUTXOSetChunks{}
|
||||
}
|
@ -1,26 +0,0 @@
|
||||
package appmessage
|
||||
|
||||
import (
|
||||
"github.com/kaspanet/kaspad/domain/consensus/model/externalapi"
|
||||
)
|
||||
|
||||
// MsgIBDRootHashMessage implements the Message interface and represents a kaspa
|
||||
// IBDRootHash message. It is used as a reply to IBD root hash requests.
|
||||
type MsgIBDRootHashMessage struct {
|
||||
baseMessage
|
||||
Hash *externalapi.DomainHash
|
||||
}
|
||||
|
||||
// Command returns the protocol command string for the message. This is part
|
||||
// of the Message interface implementation.
|
||||
func (msg *MsgIBDRootHashMessage) Command() MessageCommand {
|
||||
return CmdIBDRootHash
|
||||
}
|
||||
|
||||
// NewMsgIBDRootHashMessage returns a new kaspa IBDRootHash message that conforms to
|
||||
// the Message interface. See MsgIBDRootHashMessage for details.
|
||||
func NewMsgIBDRootHashMessage(hash *externalapi.DomainHash) *MsgIBDRootHashMessage {
|
||||
return &MsgIBDRootHashMessage{
|
||||
Hash: hash,
|
||||
}
|
||||
}
|
@ -1,19 +0,0 @@
|
||||
package appmessage
|
||||
|
||||
// MsgIBDRootUTXOSetChunk represents a kaspa IBDRootUTXOSetChunk message
|
||||
type MsgIBDRootUTXOSetChunk struct {
|
||||
baseMessage
|
||||
Chunk []byte
|
||||
}
|
||||
|
||||
// Command returns the protocol command string for the message
|
||||
func (msg *MsgIBDRootUTXOSetChunk) Command() MessageCommand {
|
||||
return CmdIBDRootUTXOSetChunk
|
||||
}
|
||||
|
||||
// NewMsgIBDRootUTXOSetChunk returns a new MsgIBDRootUTXOSetChunk.
|
||||
func NewMsgIBDRootUTXOSetChunk(chunk []byte) *MsgIBDRootUTXOSetChunk {
|
||||
return &MsgIBDRootUTXOSetChunk{
|
||||
Chunk: chunk,
|
||||
}
|
||||
}
|
23
app/appmessage/p2p_msgpruningpointhash.go
Normal file
23
app/appmessage/p2p_msgpruningpointhash.go
Normal file
@ -0,0 +1,23 @@
|
||||
package appmessage
|
||||
|
||||
import (
|
||||
"github.com/kaspanet/kaspad/domain/consensus/model/externalapi"
|
||||
)
|
||||
|
||||
// MsgPruningPointHashMessage represents a kaspa PruningPointHash message
|
||||
type MsgPruningPointHashMessage struct {
|
||||
baseMessage
|
||||
Hash *externalapi.DomainHash
|
||||
}
|
||||
|
||||
// Command returns the protocol command string for the message
|
||||
func (msg *MsgPruningPointHashMessage) Command() MessageCommand {
|
||||
return CmdPruningPointHash
|
||||
}
|
||||
|
||||
// NewPruningPointHashMessage returns a new kaspa PruningPointHash message
|
||||
func NewPruningPointHashMessage(hash *externalapi.DomainHash) *MsgPruningPointHashMessage {
|
||||
return &MsgPruningPointHashMessage{
|
||||
Hash: hash,
|
||||
}
|
||||
}
|
36
app/appmessage/p2p_msgpruningpointutxosetchunk.go
Normal file
36
app/appmessage/p2p_msgpruningpointutxosetchunk.go
Normal file
@ -0,0 +1,36 @@
|
||||
package appmessage
|
||||
|
||||
import "github.com/kaspanet/kaspad/domain/consensus/model/externalapi"
|
||||
|
||||
// MsgPruningPointUTXOSetChunk represents a kaspa PruningPointUTXOSetChunk message
|
||||
type MsgPruningPointUTXOSetChunk struct {
|
||||
baseMessage
|
||||
OutpointAndUTXOEntryPairs []*OutpointAndUTXOEntryPair
|
||||
}
|
||||
|
||||
// Command returns the protocol command string for the message
|
||||
func (msg *MsgPruningPointUTXOSetChunk) Command() MessageCommand {
|
||||
return CmdPruningPointUTXOSetChunk
|
||||
}
|
||||
|
||||
// NewMsgPruningPointUTXOSetChunk returns a new MsgPruningPointUTXOSetChunk.
|
||||
func NewMsgPruningPointUTXOSetChunk(outpointAndUTXOEntryPairs []*OutpointAndUTXOEntryPair) *MsgPruningPointUTXOSetChunk {
|
||||
return &MsgPruningPointUTXOSetChunk{
|
||||
OutpointAndUTXOEntryPairs: outpointAndUTXOEntryPairs,
|
||||
}
|
||||
}
|
||||
|
||||
// OutpointAndUTXOEntryPair is an outpoint along with its
|
||||
// respective UTXO entry
|
||||
type OutpointAndUTXOEntryPair struct {
|
||||
Outpoint *Outpoint
|
||||
UTXOEntry *UTXOEntry
|
||||
}
|
||||
|
||||
// UTXOEntry houses details about an individual transaction output in a UTXO
|
||||
type UTXOEntry struct {
|
||||
Amount uint64
|
||||
ScriptPublicKey *externalapi.ScriptPublicKey
|
||||
BlockBlueScore uint64
|
||||
IsCoinbase bool
|
||||
}
|
@ -1,26 +0,0 @@
|
||||
package appmessage
|
||||
|
||||
import (
|
||||
"github.com/kaspanet/kaspad/domain/consensus/model/externalapi"
|
||||
)
|
||||
|
||||
// MsgRequestIBDRootUTXOSetAndBlock implements the Message interface and represents a kaspa
|
||||
// RequestIBDRootUTXOSetAndBlock message. It is used to request the UTXO set and block body
|
||||
// of the IBD root block.
|
||||
type MsgRequestIBDRootUTXOSetAndBlock struct {
|
||||
baseMessage
|
||||
IBDRoot *externalapi.DomainHash
|
||||
}
|
||||
|
||||
// Command returns the protocol command string for the message. This is part
|
||||
// of the Message interface implementation.
|
||||
func (msg *MsgRequestIBDRootUTXOSetAndBlock) Command() MessageCommand {
|
||||
return CmdRequestIBDRootUTXOSetAndBlock
|
||||
}
|
||||
|
||||
// NewMsgRequestIBDRootUTXOSetAndBlock returns a new MsgRequestIBDRootUTXOSetAndBlock.
|
||||
func NewMsgRequestIBDRootUTXOSetAndBlock(ibdRoot *externalapi.DomainHash) *MsgRequestIBDRootUTXOSetAndBlock {
|
||||
return &MsgRequestIBDRootUTXOSetAndBlock{
|
||||
IBDRoot: ibdRoot,
|
||||
}
|
||||
}
|
@ -1,16 +0,0 @@
|
||||
package appmessage
|
||||
|
||||
// MsgRequestNextIBDRootUTXOSetChunk represents a kaspa RequestNextIBDRootUTXOSetChunk message
|
||||
type MsgRequestNextIBDRootUTXOSetChunk struct {
|
||||
baseMessage
|
||||
}
|
||||
|
||||
// Command returns the protocol command string for the message
|
||||
func (msg *MsgRequestNextIBDRootUTXOSetChunk) Command() MessageCommand {
|
||||
return CmdRequestNextIBDRootUTXOSetChunk
|
||||
}
|
||||
|
||||
// NewMsgRequestNextIBDRootUTXOSetChunk returns a new MsgRequestNextIBDRootUTXOSetChunk.
|
||||
func NewMsgRequestNextIBDRootUTXOSetChunk() *MsgRequestNextIBDRootUTXOSetChunk {
|
||||
return &MsgRequestNextIBDRootUTXOSetChunk{}
|
||||
}
|
16
app/appmessage/p2p_msgrequestnextpruningpointutxosetchunk.go
Normal file
16
app/appmessage/p2p_msgrequestnextpruningpointutxosetchunk.go
Normal file
@ -0,0 +1,16 @@
|
||||
package appmessage
|
||||
|
||||
// MsgRequestNextPruningPointUTXOSetChunk represents a kaspa RequestNextPruningPointUTXOSetChunk message
|
||||
type MsgRequestNextPruningPointUTXOSetChunk struct {
|
||||
baseMessage
|
||||
}
|
||||
|
||||
// Command returns the protocol command string for the message
|
||||
func (msg *MsgRequestNextPruningPointUTXOSetChunk) Command() MessageCommand {
|
||||
return CmdRequestNextPruningPointUTXOSetChunk
|
||||
}
|
||||
|
||||
// NewMsgRequestNextPruningPointUTXOSetChunk returns a new MsgRequestNextPruningPointUTXOSetChunk.
|
||||
func NewMsgRequestNextPruningPointUTXOSetChunk() *MsgRequestNextPruningPointUTXOSetChunk {
|
||||
return &MsgRequestNextPruningPointUTXOSetChunk{}
|
||||
}
|
23
app/appmessage/p2p_msgrequestpruningpointutxosetandblock.go
Normal file
23
app/appmessage/p2p_msgrequestpruningpointutxosetandblock.go
Normal file
@ -0,0 +1,23 @@
|
||||
package appmessage
|
||||
|
||||
import (
|
||||
"github.com/kaspanet/kaspad/domain/consensus/model/externalapi"
|
||||
)
|
||||
|
||||
// MsgRequestPruningPointUTXOSetAndBlock represents a kaspa RequestPruningPointUTXOSetAndBlock message
|
||||
type MsgRequestPruningPointUTXOSetAndBlock struct {
|
||||
baseMessage
|
||||
PruningPointHash *externalapi.DomainHash
|
||||
}
|
||||
|
||||
// Command returns the protocol command string for the message
|
||||
func (msg *MsgRequestPruningPointUTXOSetAndBlock) Command() MessageCommand {
|
||||
return CmdRequestPruningPointUTXOSetAndBlock
|
||||
}
|
||||
|
||||
// NewMsgRequestPruningPointUTXOSetAndBlock returns a new MsgRequestPruningPointUTXOSetAndBlock
|
||||
func NewMsgRequestPruningPointUTXOSetAndBlock(pruningPointHash *externalapi.DomainHash) *MsgRequestPruningPointUTXOSetAndBlock {
|
||||
return &MsgRequestPruningPointUTXOSetAndBlock{
|
||||
PruningPointHash: pruningPointHash,
|
||||
}
|
||||
}
|
@ -1,22 +0,0 @@
|
||||
package appmessage
|
||||
|
||||
// MsgRequestIBDRootHashMessage implements the Message interface and represents a kaspa
|
||||
// MsgRequestIBDRootHashMessage message. It is used to request the IBD root hash
|
||||
// from a peer during IBD.
|
||||
//
|
||||
// This message has no payload.
|
||||
type MsgRequestIBDRootHashMessage struct {
|
||||
baseMessage
|
||||
}
|
||||
|
||||
// Command returns the protocol command string for the message. This is part
|
||||
// of the Message interface implementation.
|
||||
func (msg *MsgRequestIBDRootHashMessage) Command() MessageCommand {
|
||||
return CmdRequestIBDRootHash
|
||||
}
|
||||
|
||||
// NewMsgRequestIBDRootHashMessage returns a new kaspa RequestIBDRootHash message that conforms to the
|
||||
// Message interface.
|
||||
func NewMsgRequestIBDRootHashMessage() *MsgRequestIBDRootHashMessage {
|
||||
return &MsgRequestIBDRootHashMessage{}
|
||||
}
|
16
app/appmessage/p2p_requestpruningpointhash.go
Normal file
16
app/appmessage/p2p_requestpruningpointhash.go
Normal file
@ -0,0 +1,16 @@
|
||||
package appmessage
|
||||
|
||||
// MsgRequestPruningPointHashMessage represents a kaspa RequestPruningPointHashMessage message
|
||||
type MsgRequestPruningPointHashMessage struct {
|
||||
baseMessage
|
||||
}
|
||||
|
||||
// Command returns the protocol command string for the message
|
||||
func (msg *MsgRequestPruningPointHashMessage) Command() MessageCommand {
|
||||
return CmdRequestPruningPointHash
|
||||
}
|
||||
|
||||
// NewMsgRequestPruningPointHashMessage returns a new kaspa RequestPruningPointHash message
|
||||
func NewMsgRequestPruningPointHashMessage() *MsgRequestPruningPointHashMessage {
|
||||
return &MsgRequestPruningPointHashMessage{}
|
||||
}
|
16
app/appmessage/p2p_unexpectedpruningpoint.go
Normal file
16
app/appmessage/p2p_unexpectedpruningpoint.go
Normal file
@ -0,0 +1,16 @@
|
||||
package appmessage
|
||||
|
||||
// MsgUnexpectedPruningPoint represents a kaspa UnexpectedPruningPoint message
|
||||
type MsgUnexpectedPruningPoint struct {
|
||||
baseMessage
|
||||
}
|
||||
|
||||
// Command returns the protocol command string for the message
|
||||
func (msg *MsgUnexpectedPruningPoint) Command() MessageCommand {
|
||||
return CmdUnexpectedPruningPoint
|
||||
}
|
||||
|
||||
// NewMsgUnexpectedPruningPoint returns a new kaspa UnexpectedPruningPoint message
|
||||
func NewMsgUnexpectedPruningPoint() *MsgUnexpectedPruningPoint {
|
||||
return &MsgUnexpectedPruningPoint{}
|
||||
}
|
@ -1,51 +0,0 @@
|
||||
package blockrelay
|
||||
|
||||
import (
|
||||
"github.com/kaspanet/kaspad/app/appmessage"
|
||||
"github.com/kaspanet/kaspad/domain"
|
||||
"github.com/kaspanet/kaspad/infrastructure/network/netadapter/router"
|
||||
)
|
||||
|
||||
// HandleIBDRootHashRequestsFlowContext is the interface for the context needed for the handleIBDRootHashRequestsFlow flow.
|
||||
type HandleIBDRootHashRequestsFlowContext interface {
|
||||
Domain() domain.Domain
|
||||
}
|
||||
|
||||
type handleIBDRootHashRequestsFlow struct {
|
||||
HandleIBDRootHashRequestsFlowContext
|
||||
incomingRoute, outgoingRoute *router.Route
|
||||
}
|
||||
|
||||
// HandleIBDRootHashRequests listens to appmessage.MsgRequestIBDRootHashMessage messages and sends
|
||||
// the IBD root hash as response.
|
||||
func HandleIBDRootHashRequests(context HandleIBDRootHashRequestsFlowContext, incomingRoute,
|
||||
outgoingRoute *router.Route) error {
|
||||
flow := &handleIBDRootHashRequestsFlow{
|
||||
HandleIBDRootHashRequestsFlowContext: context,
|
||||
incomingRoute: incomingRoute,
|
||||
outgoingRoute: outgoingRoute,
|
||||
}
|
||||
|
||||
return flow.start()
|
||||
}
|
||||
|
||||
func (flow *handleIBDRootHashRequestsFlow) start() error {
|
||||
for {
|
||||
_, err := flow.incomingRoute.Dequeue()
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
log.Debugf("Got request for IBD root hash")
|
||||
|
||||
pruningPoint, err := flow.Domain().Consensus().PruningPoint()
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
err = flow.outgoingRoute.Enqueue(appmessage.NewMsgIBDRootHashMessage(pruningPoint))
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
log.Debugf("Sent IBD root hash %s", pruningPoint)
|
||||
}
|
||||
}
|
@ -0,0 +1,51 @@
|
||||
package blockrelay
|
||||
|
||||
import (
|
||||
"github.com/kaspanet/kaspad/app/appmessage"
|
||||
"github.com/kaspanet/kaspad/domain"
|
||||
"github.com/kaspanet/kaspad/infrastructure/network/netadapter/router"
|
||||
)
|
||||
|
||||
// HandlePruningPointHashRequestsFlowContext is the interface for the context needed for the handlePruningPointHashRequestsFlow flow.
|
||||
type HandlePruningPointHashRequestsFlowContext interface {
|
||||
Domain() domain.Domain
|
||||
}
|
||||
|
||||
type handlePruningPointHashRequestsFlow struct {
|
||||
HandlePruningPointHashRequestsFlowContext
|
||||
incomingRoute, outgoingRoute *router.Route
|
||||
}
|
||||
|
||||
// HandlePruningPointHashRequests listens to appmessage.MsgRequestPruningPointHashMessage messages and sends
|
||||
// the pruning point hash as response.
|
||||
func HandlePruningPointHashRequests(context HandlePruningPointHashRequestsFlowContext, incomingRoute,
|
||||
outgoingRoute *router.Route) error {
|
||||
flow := &handlePruningPointHashRequestsFlow{
|
||||
HandlePruningPointHashRequestsFlowContext: context,
|
||||
incomingRoute: incomingRoute,
|
||||
outgoingRoute: outgoingRoute,
|
||||
}
|
||||
|
||||
return flow.start()
|
||||
}
|
||||
|
||||
func (flow *handlePruningPointHashRequestsFlow) start() error {
|
||||
for {
|
||||
_, err := flow.incomingRoute.Dequeue()
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
log.Debugf("Got request for a pruning point hash")
|
||||
|
||||
pruningPoint, err := flow.Domain().Consensus().PruningPoint()
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
err = flow.outgoingRoute.Enqueue(appmessage.NewPruningPointHashMessage(pruningPoint))
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
log.Debugf("Sent pruning point hash %s", pruningPoint)
|
||||
}
|
||||
}
|
@ -1,117 +0,0 @@
|
||||
package blockrelay
|
||||
|
||||
import (
|
||||
"errors"
|
||||
"github.com/kaspanet/kaspad/app/appmessage"
|
||||
"github.com/kaspanet/kaspad/app/protocol/common"
|
||||
"github.com/kaspanet/kaspad/app/protocol/protocolerrors"
|
||||
"github.com/kaspanet/kaspad/domain"
|
||||
"github.com/kaspanet/kaspad/domain/consensus/ruleerrors"
|
||||
"github.com/kaspanet/kaspad/infrastructure/logger"
|
||||
"github.com/kaspanet/kaspad/infrastructure/network/netadapter/router"
|
||||
)
|
||||
|
||||
// HandleRequestIBDRootUTXOSetAndBlockContext is the interface for the context needed for the HandleRequestIBDRootUTXOSetAndBlock flow.
|
||||
type HandleRequestIBDRootUTXOSetAndBlockContext interface {
|
||||
Domain() domain.Domain
|
||||
}
|
||||
|
||||
type handleRequestIBDRootUTXOSetAndBlockFlow struct {
|
||||
HandleRequestIBDRootUTXOSetAndBlockContext
|
||||
incomingRoute, outgoingRoute *router.Route
|
||||
}
|
||||
|
||||
// HandleRequestIBDRootUTXOSetAndBlock listens to appmessage.MsgRequestIBDRootUTXOSetAndBlock messages and sends
|
||||
// the IBD root UTXO set and block body.
|
||||
func HandleRequestIBDRootUTXOSetAndBlock(context HandleRequestIBDRootUTXOSetAndBlockContext, incomingRoute,
|
||||
outgoingRoute *router.Route) error {
|
||||
flow := &handleRequestIBDRootUTXOSetAndBlockFlow{
|
||||
HandleRequestIBDRootUTXOSetAndBlockContext: context,
|
||||
incomingRoute: incomingRoute,
|
||||
outgoingRoute: outgoingRoute,
|
||||
}
|
||||
|
||||
return flow.start()
|
||||
}
|
||||
|
||||
func (flow *handleRequestIBDRootUTXOSetAndBlockFlow) start() error {
|
||||
for {
|
||||
message, err := flow.incomingRoute.Dequeue()
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
msgRequestIBDRootUTXOSetAndBlock, ok := message.(*appmessage.MsgRequestIBDRootUTXOSetAndBlock)
|
||||
if !ok {
|
||||
return protocolerrors.Errorf(true, "received unexpected message type. "+
|
||||
"expected: %s, got: %s", appmessage.CmdRequestIBDRootUTXOSetAndBlock, message.Command())
|
||||
}
|
||||
|
||||
finishMeasuring := logger.LogAndMeasureExecutionTime(log, "handleRequestIBDRootUTXOSetAndBlockFlow")
|
||||
log.Debugf("Got request for IBDRoot UTXOSet and Block")
|
||||
|
||||
serializedUTXOSet, err := flow.Domain().Consensus().GetPruningPointUTXOSet(msgRequestIBDRootUTXOSetAndBlock.IBDRoot)
|
||||
if err != nil {
|
||||
if errors.Is(err, ruleerrors.ErrWrongPruningPointHash) {
|
||||
err = flow.outgoingRoute.Enqueue(appmessage.NewMsgIBDRootNotFound())
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
continue
|
||||
}
|
||||
}
|
||||
log.Debugf("Retrieved utxo set for pruning block %s", msgRequestIBDRootUTXOSetAndBlock.IBDRoot)
|
||||
|
||||
block, err := flow.Domain().Consensus().GetBlock(msgRequestIBDRootUTXOSetAndBlock.IBDRoot)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
log.Debugf("Retrieved pruning block %s", msgRequestIBDRootUTXOSetAndBlock.IBDRoot)
|
||||
|
||||
err = flow.outgoingRoute.Enqueue(appmessage.NewMsgIBDBlock(appmessage.DomainBlockToMsgBlock(block)))
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
// Send the UTXO set in `step`-sized chunks
|
||||
const step = 1024 * 1024 // 1MB
|
||||
offset := 0
|
||||
chunksSent := 0
|
||||
for offset < len(serializedUTXOSet) {
|
||||
var chunk []byte
|
||||
if offset+step < len(serializedUTXOSet) {
|
||||
chunk = serializedUTXOSet[offset : offset+step]
|
||||
} else {
|
||||
chunk = serializedUTXOSet[offset:]
|
||||
}
|
||||
|
||||
err = flow.outgoingRoute.Enqueue(appmessage.NewMsgIBDRootUTXOSetChunk(chunk))
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
offset += step
|
||||
chunksSent++
|
||||
|
||||
// Wait for the peer to request more chunks every `ibdBatchSize` chunks
|
||||
if chunksSent%ibdBatchSize == 0 {
|
||||
message, err := flow.incomingRoute.DequeueWithTimeout(common.DefaultTimeout)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
_, ok := message.(*appmessage.MsgRequestNextIBDRootUTXOSetChunk)
|
||||
if !ok {
|
||||
return protocolerrors.Errorf(true, "received unexpected message type. "+
|
||||
"expected: %s, got: %s", appmessage.CmdRequestNextIBDRootUTXOSetChunk, message.Command())
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
err = flow.outgoingRoute.Enqueue(appmessage.NewMsgDoneIBDRootUTXOSetChunks())
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
finishMeasuring()
|
||||
}
|
||||
}
|
@ -0,0 +1,143 @@
|
||||
package blockrelay
|
||||
|
||||
import (
|
||||
"errors"
|
||||
"github.com/kaspanet/kaspad/app/appmessage"
|
||||
"github.com/kaspanet/kaspad/app/protocol/common"
|
||||
"github.com/kaspanet/kaspad/app/protocol/protocolerrors"
|
||||
"github.com/kaspanet/kaspad/domain"
|
||||
"github.com/kaspanet/kaspad/domain/consensus/ruleerrors"
|
||||
"github.com/kaspanet/kaspad/infrastructure/logger"
|
||||
"github.com/kaspanet/kaspad/infrastructure/network/netadapter/router"
|
||||
)
|
||||
|
||||
// HandleRequestPruningPointUTXOSetAndBlockContext is the interface for the context needed for the HandleRequestPruningPointUTXOSetAndBlock flow.
|
||||
type HandleRequestPruningPointUTXOSetAndBlockContext interface {
|
||||
Domain() domain.Domain
|
||||
}
|
||||
|
||||
type handleRequestPruningPointUTXOSetAndBlockFlow struct {
|
||||
HandleRequestPruningPointUTXOSetAndBlockContext
|
||||
incomingRoute, outgoingRoute *router.Route
|
||||
}
|
||||
|
||||
// HandleRequestPruningPointUTXOSetAndBlock listens to appmessage.MsgRequestPruningPointUTXOSetAndBlock messages and sends
|
||||
// the pruning point UTXO set and block body.
|
||||
func HandleRequestPruningPointUTXOSetAndBlock(context HandleRequestPruningPointUTXOSetAndBlockContext, incomingRoute,
|
||||
outgoingRoute *router.Route) error {
|
||||
flow := &handleRequestPruningPointUTXOSetAndBlockFlow{
|
||||
HandleRequestPruningPointUTXOSetAndBlockContext: context,
|
||||
incomingRoute: incomingRoute,
|
||||
outgoingRoute: outgoingRoute,
|
||||
}
|
||||
|
||||
return flow.start()
|
||||
}
|
||||
|
||||
func (flow *handleRequestPruningPointUTXOSetAndBlockFlow) start() error {
|
||||
for {
|
||||
msgRequestPruningPointUTXOSetAndBlock, err := flow.waitForRequestPruningPointUTXOSetAndBlockMessages()
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
err = flow.handleRequestPruningPointUTXOSetAndBlockMessage(msgRequestPruningPointUTXOSetAndBlock)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
func (flow *handleRequestPruningPointUTXOSetAndBlockFlow) handleRequestPruningPointUTXOSetAndBlockMessage(
|
||||
msgRequestPruningPointUTXOSetAndBlock *appmessage.MsgRequestPruningPointUTXOSetAndBlock) error {
|
||||
|
||||
onEnd := logger.LogAndMeasureExecutionTime(log, "handleRequestPruningPointUTXOSetAndBlockFlow")
|
||||
defer onEnd()
|
||||
|
||||
log.Debugf("Got request for PruningPointHash UTXOSet and Block")
|
||||
|
||||
err := flow.sendPruningPointBlock(msgRequestPruningPointUTXOSetAndBlock)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
return flow.sendPruningPointUTXOSet(msgRequestPruningPointUTXOSetAndBlock)
|
||||
}
|
||||
|
||||
func (flow *handleRequestPruningPointUTXOSetAndBlockFlow) waitForRequestPruningPointUTXOSetAndBlockMessages() (
|
||||
*appmessage.MsgRequestPruningPointUTXOSetAndBlock, error) {
|
||||
|
||||
message, err := flow.incomingRoute.Dequeue()
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
msgRequestPruningPointUTXOSetAndBlock, ok := message.(*appmessage.MsgRequestPruningPointUTXOSetAndBlock)
|
||||
if !ok {
|
||||
return nil, protocolerrors.Errorf(true, "received unexpected message type. "+
|
||||
"expected: %s, got: %s", appmessage.CmdRequestPruningPointUTXOSetAndBlock, message.Command())
|
||||
}
|
||||
return msgRequestPruningPointUTXOSetAndBlock, nil
|
||||
}
|
||||
|
||||
func (flow *handleRequestPruningPointUTXOSetAndBlockFlow) sendPruningPointBlock(
|
||||
msgRequestPruningPointUTXOSetAndBlock *appmessage.MsgRequestPruningPointUTXOSetAndBlock) error {
|
||||
|
||||
block, err := flow.Domain().Consensus().GetBlock(msgRequestPruningPointUTXOSetAndBlock.PruningPointHash)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
log.Debugf("Retrieved pruning block %s", msgRequestPruningPointUTXOSetAndBlock.PruningPointHash)
|
||||
|
||||
return flow.outgoingRoute.Enqueue(appmessage.NewMsgIBDBlock(appmessage.DomainBlockToMsgBlock(block)))
|
||||
}
|
||||
|
||||
func (flow *handleRequestPruningPointUTXOSetAndBlockFlow) sendPruningPointUTXOSet(
|
||||
msgRequestPruningPointUTXOSetAndBlock *appmessage.MsgRequestPruningPointUTXOSetAndBlock) error {
|
||||
|
||||
// Send the UTXO set in `step`-sized chunks
|
||||
const step = 1000
|
||||
offset := 0
|
||||
chunksSent := 0
|
||||
for {
|
||||
pruningPointUTXOs, err := flow.Domain().Consensus().GetPruningPointUTXOs(
|
||||
msgRequestPruningPointUTXOSetAndBlock.PruningPointHash, offset, step)
|
||||
if err != nil {
|
||||
if errors.Is(err, ruleerrors.ErrWrongPruningPointHash) {
|
||||
return flow.outgoingRoute.Enqueue(appmessage.NewMsgUnexpectedPruningPoint())
|
||||
}
|
||||
}
|
||||
|
||||
log.Debugf("Retrieved %d UTXOs for pruning block %s",
|
||||
len(pruningPointUTXOs), msgRequestPruningPointUTXOSetAndBlock.PruningPointHash)
|
||||
|
||||
outpointAndUTXOEntryPairs :=
|
||||
appmessage.DomainOutpointAndUTXOEntryPairsToOutpointAndUTXOEntryPairs(pruningPointUTXOs)
|
||||
err = flow.outgoingRoute.Enqueue(appmessage.NewMsgPruningPointUTXOSetChunk(outpointAndUTXOEntryPairs))
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
if len(pruningPointUTXOs) < step {
|
||||
log.Debugf("Finished sending UTXOs for pruning block %s",
|
||||
msgRequestPruningPointUTXOSetAndBlock.PruningPointHash)
|
||||
|
||||
return flow.outgoingRoute.Enqueue(appmessage.NewMsgDonePruningPointUTXOSetChunks())
|
||||
}
|
||||
|
||||
offset += step
|
||||
chunksSent++
|
||||
|
||||
// Wait for the peer to request more chunks every `ibdBatchSize` chunks
|
||||
if chunksSent%ibdBatchSize == 0 {
|
||||
message, err := flow.incomingRoute.DequeueWithTimeout(common.DefaultTimeout)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
_, ok := message.(*appmessage.MsgRequestNextPruningPointUTXOSetChunk)
|
||||
if !ok {
|
||||
return protocolerrors.Errorf(true, "received unexpected message type. "+
|
||||
"expected: %s, got: %s", appmessage.CmdRequestNextPruningPointUTXOSetChunk, message.Command())
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
@ -1,6 +1,7 @@
|
||||
package blockrelay
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"github.com/kaspanet/kaspad/infrastructure/logger"
|
||||
"time"
|
||||
|
||||
@ -288,7 +289,7 @@ func (flow *handleRelayInvsFlow) processHeader(msgBlockHeader *appmessage.MsgBlo
|
||||
|
||||
func (flow *handleRelayInvsFlow) syncPruningPointUTXOSet() (bool, error) {
|
||||
log.Debugf("Checking if a new pruning point is available")
|
||||
err := flow.outgoingRoute.Enqueue(appmessage.NewMsgRequestIBDRootHashMessage())
|
||||
err := flow.outgoingRoute.Enqueue(appmessage.NewMsgRequestPruningPointHashMessage())
|
||||
if err != nil {
|
||||
return false, err
|
||||
}
|
||||
@ -296,36 +297,36 @@ func (flow *handleRelayInvsFlow) syncPruningPointUTXOSet() (bool, error) {
|
||||
if err != nil {
|
||||
return false, err
|
||||
}
|
||||
msgIBDRootHash, ok := message.(*appmessage.MsgIBDRootHashMessage)
|
||||
msgPruningPointHash, ok := message.(*appmessage.MsgPruningPointHashMessage)
|
||||
if !ok {
|
||||
return false, protocolerrors.Errorf(true, "received unexpected message type. "+
|
||||
"expected: %s, got: %s", appmessage.CmdIBDRootHash, message.Command())
|
||||
"expected: %s, got: %s", appmessage.CmdPruningPointHash, message.Command())
|
||||
}
|
||||
|
||||
blockInfo, err := flow.Domain().Consensus().GetBlockInfo(msgIBDRootHash.Hash)
|
||||
blockInfo, err := flow.Domain().Consensus().GetBlockInfo(msgPruningPointHash.Hash)
|
||||
if err != nil {
|
||||
return false, err
|
||||
}
|
||||
|
||||
if blockInfo.BlockStatus != externalapi.StatusHeaderOnly {
|
||||
log.Debugf("Already has the block data of the new suggested pruning point %s", msgIBDRootHash.Hash)
|
||||
log.Debugf("Already has the block data of the new suggested pruning point %s", msgPruningPointHash.Hash)
|
||||
return true, nil
|
||||
}
|
||||
|
||||
log.Infof("Checking if the suggested pruning point %s is compatible to the node DAG", msgIBDRootHash.Hash)
|
||||
isValid, err := flow.Domain().Consensus().IsValidPruningPoint(msgIBDRootHash.Hash)
|
||||
log.Infof("Checking if the suggested pruning point %s is compatible to the node DAG", msgPruningPointHash.Hash)
|
||||
isValid, err := flow.Domain().Consensus().IsValidPruningPoint(msgPruningPointHash.Hash)
|
||||
if err != nil {
|
||||
return false, err
|
||||
}
|
||||
|
||||
if !isValid {
|
||||
log.Infof("The suggested pruning point %s is incompatible to this node DAG, so stopping IBD with this"+
|
||||
" peer", msgIBDRootHash.Hash)
|
||||
" peer", msgPruningPointHash.Hash)
|
||||
return false, nil
|
||||
}
|
||||
|
||||
log.Info("Fetching the pruning point UTXO set")
|
||||
succeed, err := flow.fetchMissingUTXOSet(msgIBDRootHash.Hash)
|
||||
succeed, err := flow.fetchMissingUTXOSet(msgPruningPointHash.Hash)
|
||||
if err != nil {
|
||||
return false, err
|
||||
}
|
||||
@ -339,94 +340,118 @@ func (flow *handleRelayInvsFlow) syncPruningPointUTXOSet() (bool, error) {
|
||||
return true, nil
|
||||
}
|
||||
|
||||
func (flow *handleRelayInvsFlow) fetchMissingUTXOSet(ibdRootHash *externalapi.DomainHash) (succeed bool, err error) {
|
||||
err = flow.outgoingRoute.Enqueue(appmessage.NewMsgRequestIBDRootUTXOSetAndBlock(ibdRootHash))
|
||||
func (flow *handleRelayInvsFlow) fetchMissingUTXOSet(pruningPointHash *externalapi.DomainHash) (succeed bool, err error) {
|
||||
defer func() {
|
||||
err := flow.Domain().Consensus().ClearImportedPruningPointData()
|
||||
if err != nil {
|
||||
panic(fmt.Sprintf("failed to clear imported pruning point data: %s", err))
|
||||
}
|
||||
}()
|
||||
|
||||
err = flow.outgoingRoute.Enqueue(appmessage.NewMsgRequestPruningPointUTXOSetAndBlock(pruningPointHash))
|
||||
if err != nil {
|
||||
return false, err
|
||||
}
|
||||
|
||||
utxoSet, block, found, err := flow.receiveIBDRootUTXOSetAndBlock()
|
||||
block, err := flow.receivePruningPointBlock()
|
||||
if err != nil {
|
||||
return false, err
|
||||
}
|
||||
|
||||
if !found {
|
||||
receivedAll, err := flow.receiveAndInsertPruningPointUTXOSet(pruningPointHash)
|
||||
if err != nil {
|
||||
return false, err
|
||||
}
|
||||
if !receivedAll {
|
||||
return false, nil
|
||||
}
|
||||
|
||||
err = flow.Domain().Consensus().ValidateAndInsertPruningPoint(block, utxoSet)
|
||||
err = flow.Domain().Consensus().ValidateAndInsertImportedPruningPoint(block)
|
||||
if err != nil {
|
||||
// TODO: Find a better way to deal with finality conflicts.
|
||||
if errors.Is(err, ruleerrors.ErrSuggestedPruningViolatesFinality) {
|
||||
return false, nil
|
||||
}
|
||||
return false, protocolerrors.ConvertToBanningProtocolErrorIfRuleError(err, "error with IBD root UTXO set")
|
||||
return false, protocolerrors.ConvertToBanningProtocolErrorIfRuleError(err, "error with pruning point UTXO set")
|
||||
}
|
||||
|
||||
return true, nil
|
||||
}
|
||||
|
||||
func (flow *handleRelayInvsFlow) receiveIBDRootUTXOSetAndBlock() ([]byte, *externalapi.DomainBlock, bool, error) {
|
||||
onEnd := logger.LogAndMeasureExecutionTime(log, "receiveIBDRootUTXOSetAndBlock")
|
||||
func (flow *handleRelayInvsFlow) receivePruningPointBlock() (*externalapi.DomainBlock, error) {
|
||||
onEnd := logger.LogAndMeasureExecutionTime(log, "receivePruningPointBlock")
|
||||
defer onEnd()
|
||||
|
||||
message, err := flow.dequeueIncomingMessageAndSkipInvs(common.DefaultTimeout)
|
||||
if err != nil {
|
||||
return nil, nil, false, err
|
||||
return nil, err
|
||||
}
|
||||
|
||||
var block *externalapi.DomainBlock
|
||||
switch message := message.(type) {
|
||||
case *appmessage.MsgIBDBlock:
|
||||
block = appmessage.MsgBlockToDomainBlock(message.MsgBlock)
|
||||
case *appmessage.MsgIBDRootNotFound:
|
||||
return nil, nil, false, nil
|
||||
default:
|
||||
return nil, nil, false,
|
||||
protocolerrors.Errorf(true, "received unexpected message type. "+
|
||||
"expected: %s or %s, got: %s",
|
||||
appmessage.CmdIBDBlock, appmessage.CmdIBDRootNotFound, message.Command(),
|
||||
)
|
||||
ibdBlockMessage, ok := message.(*appmessage.MsgIBDBlock)
|
||||
if !ok {
|
||||
return nil, protocolerrors.Errorf(true, "received unexpected message type. "+
|
||||
"expected: %s, got: %s", appmessage.CmdIBDBlock, message.Command())
|
||||
}
|
||||
log.Debugf("Received IBD root block %s", consensushashing.BlockHash(block))
|
||||
block := appmessage.MsgBlockToDomainBlock(ibdBlockMessage.MsgBlock)
|
||||
|
||||
log.Debugf("Received pruning point block %s", consensushashing.BlockHash(block))
|
||||
|
||||
return block, nil
|
||||
}
|
||||
|
||||
func (flow *handleRelayInvsFlow) receiveAndInsertPruningPointUTXOSet(
|
||||
pruningPointHash *externalapi.DomainHash) (bool, error) {
|
||||
|
||||
onEnd := logger.LogAndMeasureExecutionTime(log, "receiveAndInsertPruningPointUTXOSet")
|
||||
defer onEnd()
|
||||
|
||||
serializedUTXOSet := []byte{}
|
||||
receivedAllChunks := false
|
||||
receivedChunkCount := 0
|
||||
for !receivedAllChunks {
|
||||
receivedUTXOCount := 0
|
||||
for {
|
||||
message, err := flow.dequeueIncomingMessageAndSkipInvs(common.DefaultTimeout)
|
||||
if err != nil {
|
||||
return nil, nil, false, err
|
||||
return false, err
|
||||
}
|
||||
|
||||
switch message := message.(type) {
|
||||
case *appmessage.MsgIBDRootUTXOSetChunk:
|
||||
serializedUTXOSet = append(serializedUTXOSet, message.Chunk...)
|
||||
case *appmessage.MsgDoneIBDRootUTXOSetChunks:
|
||||
receivedAllChunks = true
|
||||
default:
|
||||
return nil, nil, false,
|
||||
protocolerrors.Errorf(true, "received unexpected message type. "+
|
||||
"expected: %s or %s, got: %s",
|
||||
appmessage.CmdIBDRootUTXOSetChunk, appmessage.CmdDoneIBDRootUTXOSetChunks, message.Command(),
|
||||
)
|
||||
case *appmessage.MsgPruningPointUTXOSetChunk:
|
||||
receivedUTXOCount += len(message.OutpointAndUTXOEntryPairs)
|
||||
domainOutpointAndUTXOEntryPairs :=
|
||||
appmessage.OutpointAndUTXOEntryPairsToDomainOutpointAndUTXOEntryPairs(message.OutpointAndUTXOEntryPairs)
|
||||
|
||||
err := flow.Domain().Consensus().AppendImportedPruningPointUTXOs(domainOutpointAndUTXOEntryPairs)
|
||||
if err != nil {
|
||||
return false, err
|
||||
}
|
||||
|
||||
receivedChunkCount++
|
||||
if !receivedAllChunks && receivedChunkCount%ibdBatchSize == 0 {
|
||||
log.Debugf("Received %d UTXO set chunks so far, totaling in %d bytes",
|
||||
receivedChunkCount, len(serializedUTXOSet))
|
||||
if receivedChunkCount%ibdBatchSize == 0 {
|
||||
log.Debugf("Received %d UTXO set chunks so far, totaling in %d UTXOs",
|
||||
receivedChunkCount, receivedUTXOCount)
|
||||
|
||||
requestNextIBDRootUTXOSetChunkMessage := appmessage.NewMsgRequestNextIBDRootUTXOSetChunk()
|
||||
err := flow.outgoingRoute.Enqueue(requestNextIBDRootUTXOSetChunkMessage)
|
||||
requestNextPruningPointUTXOSetChunkMessage := appmessage.NewMsgRequestNextPruningPointUTXOSetChunk()
|
||||
err := flow.outgoingRoute.Enqueue(requestNextPruningPointUTXOSetChunkMessage)
|
||||
if err != nil {
|
||||
return nil, nil, false, err
|
||||
return false, err
|
||||
}
|
||||
}
|
||||
}
|
||||
log.Debugf("Finished receiving the UTXO set. Total bytes: %d", len(serializedUTXOSet))
|
||||
|
||||
return serializedUTXOSet, block, true, nil
|
||||
case *appmessage.MsgDonePruningPointUTXOSetChunks:
|
||||
log.Debugf("Finished receiving the UTXO set. Total UTXOs: %d", receivedUTXOCount)
|
||||
return true, nil
|
||||
|
||||
case *appmessage.MsgUnexpectedPruningPoint:
|
||||
log.Debugf("Could not receive the next UTXO chunk because the pruning point %s "+
|
||||
"is no longer the pruning point of peer %s", pruningPointHash, flow.peer)
|
||||
return false, nil
|
||||
|
||||
default:
|
||||
return false, protocolerrors.Errorf(true, "received unexpected message type. "+
|
||||
"expected: %s or %s or %s, got: %s", appmessage.CmdPruningPointUTXOSetChunk,
|
||||
appmessage.CmdDonePruningPointUTXOSetChunks, appmessage.CmdUnexpectedPruningPoint, message.Command(),
|
||||
)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
func (flow *handleRelayInvsFlow) syncMissingBlockBodies(highHash *externalapi.DomainHash) error {
|
||||
|
@ -137,9 +137,9 @@ func (m *Manager) registerBlockRelayFlows(router *routerpkg.Router, isStopping *
|
||||
return []*flow{
|
||||
m.registerFlow("HandleRelayInvs", router, []appmessage.MessageCommand{
|
||||
appmessage.CmdInvRelayBlock, appmessage.CmdBlock, appmessage.CmdBlockLocator, appmessage.CmdIBDBlock,
|
||||
appmessage.CmdDoneHeaders, appmessage.CmdIBDRootNotFound, appmessage.CmdIBDRootUTXOSetChunk,
|
||||
appmessage.CmdBlockHeaders, appmessage.CmdIBDRootHash, appmessage.CmdIBDBlockLocatorHighestHash,
|
||||
appmessage.CmdDoneIBDRootUTXOSetChunks},
|
||||
appmessage.CmdDoneHeaders, appmessage.CmdUnexpectedPruningPoint, appmessage.CmdPruningPointUTXOSetChunk,
|
||||
appmessage.CmdBlockHeaders, appmessage.CmdPruningPointHash, appmessage.CmdIBDBlockLocatorHighestHash,
|
||||
appmessage.CmdDonePruningPointUTXOSetChunks},
|
||||
isStopping, errChan, func(incomingRoute *routerpkg.Route, peer *peerpkg.Peer) error {
|
||||
return blockrelay.HandleRelayInvs(m.context, incomingRoute,
|
||||
outgoingRoute, peer)
|
||||
@ -166,11 +166,11 @@ func (m *Manager) registerBlockRelayFlows(router *routerpkg.Router, isStopping *
|
||||
},
|
||||
),
|
||||
|
||||
m.registerFlow("HandleRequestIBDRootUTXOSetAndBlock", router,
|
||||
[]appmessage.MessageCommand{appmessage.CmdRequestIBDRootUTXOSetAndBlock,
|
||||
appmessage.CmdRequestNextIBDRootUTXOSetChunk}, isStopping, errChan,
|
||||
m.registerFlow("HandleRequestPruningPointUTXOSetAndBlock", router,
|
||||
[]appmessage.MessageCommand{appmessage.CmdRequestPruningPointUTXOSetAndBlock,
|
||||
appmessage.CmdRequestNextPruningPointUTXOSetChunk}, isStopping, errChan,
|
||||
func(incomingRoute *routerpkg.Route, peer *peerpkg.Peer) error {
|
||||
return blockrelay.HandleRequestIBDRootUTXOSetAndBlock(m.context, incomingRoute, outgoingRoute)
|
||||
return blockrelay.HandleRequestPruningPointUTXOSetAndBlock(m.context, incomingRoute, outgoingRoute)
|
||||
},
|
||||
),
|
||||
|
||||
@ -181,10 +181,10 @@ func (m *Manager) registerBlockRelayFlows(router *routerpkg.Router, isStopping *
|
||||
},
|
||||
),
|
||||
|
||||
m.registerFlow("HandleIBDRootHashRequests", router,
|
||||
[]appmessage.MessageCommand{appmessage.CmdRequestIBDRootHash}, isStopping, errChan,
|
||||
m.registerFlow("HandlePruningPointHashRequests", router,
|
||||
[]appmessage.MessageCommand{appmessage.CmdRequestPruningPointHash}, isStopping, errChan,
|
||||
func(incomingRoute *routerpkg.Route, peer *peerpkg.Peer) error {
|
||||
return blockrelay.HandleIBDRootHashRequests(m.context, incomingRoute, outgoingRoute)
|
||||
return blockrelay.HandlePruningPointHashRequests(m.context, incomingRoute, outgoingRoute)
|
||||
},
|
||||
),
|
||||
|
||||
|
@ -199,7 +199,9 @@ func (s *consensus) GetMissingBlockBodyHashes(highHash *externalapi.DomainHash)
|
||||
return s.syncManager.GetMissingBlockBodyHashes(highHash)
|
||||
}
|
||||
|
||||
func (s *consensus) GetPruningPointUTXOSet(expectedPruningPointHash *externalapi.DomainHash) ([]byte, error) {
|
||||
func (s *consensus) GetPruningPointUTXOs(expectedPruningPointHash *externalapi.DomainHash,
|
||||
offset int, limit int) ([]*externalapi.OutpointAndUTXOEntryPair, error) {
|
||||
|
||||
s.lock.Lock()
|
||||
defer s.lock.Unlock()
|
||||
|
||||
@ -214,11 +216,11 @@ func (s *consensus) GetPruningPointUTXOSet(expectedPruningPointHash *externalapi
|
||||
pruningPointHash)
|
||||
}
|
||||
|
||||
serializedUTXOSet, err := s.pruningStore.PruningPointSerializedUTXOSet(s.databaseContext)
|
||||
pruningPointUTXOs, err := s.pruningStore.PruningPointUTXOs(s.databaseContext, offset, limit)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
return serializedUTXOSet, nil
|
||||
return pruningPointUTXOs, nil
|
||||
}
|
||||
|
||||
func (s *consensus) PruningPoint() (*externalapi.DomainHash, error) {
|
||||
@ -228,11 +230,25 @@ func (s *consensus) PruningPoint() (*externalapi.DomainHash, error) {
|
||||
return s.pruningStore.PruningPoint(s.databaseContext)
|
||||
}
|
||||
|
||||
func (s *consensus) ValidateAndInsertPruningPoint(newPruningPoint *externalapi.DomainBlock, serializedUTXOSet []byte) error {
|
||||
func (s *consensus) ClearImportedPruningPointData() error {
|
||||
s.lock.Lock()
|
||||
defer s.lock.Unlock()
|
||||
|
||||
return s.blockProcessor.ValidateAndInsertPruningPoint(newPruningPoint, serializedUTXOSet)
|
||||
return s.pruningManager.ClearImportedPruningPointData()
|
||||
}
|
||||
|
||||
func (s *consensus) AppendImportedPruningPointUTXOs(outpointAndUTXOEntryPairs []*externalapi.OutpointAndUTXOEntryPair) error {
|
||||
s.lock.Lock()
|
||||
defer s.lock.Unlock()
|
||||
|
||||
return s.pruningManager.AppendImportedPruningPointUTXOs(outpointAndUTXOEntryPairs)
|
||||
}
|
||||
|
||||
func (s *consensus) ValidateAndInsertImportedPruningPoint(newPruningPoint *externalapi.DomainBlock) error {
|
||||
s.lock.Lock()
|
||||
defer s.lock.Unlock()
|
||||
|
||||
return s.blockProcessor.ValidateAndInsertImportedPruningPoint(newPruningPoint)
|
||||
}
|
||||
|
||||
func (s *consensus) GetVirtualSelectedParent() (*externalapi.DomainHash, error) {
|
||||
|
@ -17,6 +17,14 @@ func (dbw *dbManager) Has(key model.DBKey) (bool, error) {
|
||||
return dbw.db.Has(dbKeyToDatabaseKey(key))
|
||||
}
|
||||
|
||||
func (dbw *dbManager) Put(key model.DBKey, value []byte) error {
|
||||
return dbw.db.Put(dbKeyToDatabaseKey(key), value)
|
||||
}
|
||||
|
||||
func (dbw *dbManager) Delete(key model.DBKey) error {
|
||||
return dbw.db.Delete(dbKeyToDatabaseKey(key))
|
||||
}
|
||||
|
||||
func (dbw *dbManager) Cursor(bucket model.DBBucket) (model.DBCursor, error) {
|
||||
cursor, err := dbw.db.Cursor(dbBucketToDatabaseBucket(bucket))
|
||||
if err != nil {
|
||||
|
@ -10,7 +10,7 @@ func utxoCollectionToDBUTXOCollection(utxoCollection model.UTXOCollection) ([]*D
|
||||
items := make([]*DbUtxoCollectionItem, utxoCollection.Len())
|
||||
i := 0
|
||||
utxoIterator := utxoCollection.Iterator()
|
||||
for utxoIterator.Next() {
|
||||
for ok := utxoIterator.First(); ok; ok = utxoIterator.Next() {
|
||||
outpoint, entry, err := utxoIterator.Get()
|
||||
if err != nil {
|
||||
return nil, err
|
||||
|
@ -11,7 +11,6 @@ type consensusStateStore struct {
|
||||
tipsStaging []*externalapi.DomainHash
|
||||
virtualDiffParentsStaging []*externalapi.DomainHash
|
||||
virtualUTXODiffStaging model.UTXODiff
|
||||
virtualUTXOSetStaging model.UTXOCollection
|
||||
|
||||
virtualUTXOSetCache *utxolrucache.LRUCache
|
||||
|
||||
@ -30,7 +29,6 @@ func (css *consensusStateStore) Discard() {
|
||||
css.tipsStaging = nil
|
||||
css.virtualUTXODiffStaging = nil
|
||||
css.virtualDiffParentsStaging = nil
|
||||
css.virtualUTXOSetStaging = nil
|
||||
}
|
||||
|
||||
func (css *consensusStateStore) Commit(dbTx model.DBTransaction) error {
|
||||
@ -48,11 +46,6 @@ func (css *consensusStateStore) Commit(dbTx model.DBTransaction) error {
|
||||
return err
|
||||
}
|
||||
|
||||
err = css.commitVirtualUTXOSet(dbTx)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
css.Discard()
|
||||
|
||||
return nil
|
||||
|
@ -19,22 +19,25 @@ func utxoKey(outpoint *externalapi.DomainOutpoint) (model.DBKey, error) {
|
||||
return utxoSetBucket.Key(serializedOutpoint), nil
|
||||
}
|
||||
|
||||
func (css *consensusStateStore) StageVirtualUTXODiff(virtualUTXODiff model.UTXODiff) error {
|
||||
if css.virtualUTXOSetStaging != nil {
|
||||
return errors.New("cannot stage virtual UTXO diff while virtual UTXO set is staged")
|
||||
}
|
||||
|
||||
func (css *consensusStateStore) StageVirtualUTXODiff(virtualUTXODiff model.UTXODiff) {
|
||||
css.virtualUTXODiffStaging = virtualUTXODiff
|
||||
return nil
|
||||
}
|
||||
|
||||
func (css *consensusStateStore) commitVirtualUTXODiff(dbTx model.DBTransaction) error {
|
||||
hadStartedImportingPruningPointUTXOSet, err := css.HadStartedImportingPruningPointUTXOSet(dbTx)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
if hadStartedImportingPruningPointUTXOSet {
|
||||
return errors.New("cannot commit virtual UTXO diff after starting to import the pruning point UTXO set")
|
||||
}
|
||||
|
||||
if css.virtualUTXODiffStaging == nil {
|
||||
return nil
|
||||
}
|
||||
|
||||
toRemoveIterator := css.virtualUTXODiffStaging.ToRemove().Iterator()
|
||||
for toRemoveIterator.Next() {
|
||||
for ok := toRemoveIterator.First(); ok; ok = toRemoveIterator.Next() {
|
||||
toRemoveOutpoint, _, err := toRemoveIterator.Get()
|
||||
if err != nil {
|
||||
return err
|
||||
@ -53,7 +56,7 @@ func (css *consensusStateStore) commitVirtualUTXODiff(dbTx model.DBTransaction)
|
||||
}
|
||||
|
||||
toAddIterator := css.virtualUTXODiffStaging.ToAdd().Iterator()
|
||||
for toAddIterator.Next() {
|
||||
for ok := toAddIterator.First(); ok; ok = toAddIterator.Next() {
|
||||
toAddOutpoint, toAddEntry, err := toAddIterator.Get()
|
||||
if err != nil {
|
||||
return err
|
||||
@ -80,63 +83,9 @@ func (css *consensusStateStore) commitVirtualUTXODiff(dbTx model.DBTransaction)
|
||||
return nil
|
||||
}
|
||||
|
||||
func (css *consensusStateStore) commitVirtualUTXOSet(dbTx model.DBTransaction) error {
|
||||
if css.virtualUTXOSetStaging == nil {
|
||||
return nil
|
||||
}
|
||||
|
||||
// Clear the existing virtual utxo set in database before adding the new one
|
||||
cursor, err := dbTx.Cursor(utxoSetBucket)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
for cursor.Next() {
|
||||
key, err := cursor.Key()
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
err = dbTx.Delete(key)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
}
|
||||
|
||||
// Now put the new virtualUTXOSet into the database
|
||||
css.virtualUTXOSetCache.Clear()
|
||||
iterator := css.virtualUTXOSetStaging.Iterator()
|
||||
for iterator.Next() {
|
||||
outpoint, utxoEntry, err := iterator.Get()
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
css.virtualUTXOSetCache.Add(outpoint, utxoEntry)
|
||||
dbKey, err := utxoKey(outpoint)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
serializedEntry, err := serializeUTXOEntry(utxoEntry)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
err = dbTx.Put(dbKey, serializedEntry)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
}
|
||||
|
||||
// Note: we don't discard the staging here since that's
|
||||
// being done at the end of Commit()
|
||||
return nil
|
||||
}
|
||||
|
||||
func (css *consensusStateStore) UTXOByOutpoint(dbContext model.DBReader, outpoint *externalapi.DomainOutpoint) (
|
||||
externalapi.UTXOEntry, error) {
|
||||
|
||||
if css.virtualUTXOSetStaging != nil {
|
||||
return css.utxoByOutpointFromStagedVirtualUTXOSet(outpoint)
|
||||
}
|
||||
|
||||
return css.utxoByOutpointFromStagedVirtualUTXODiff(dbContext, outpoint)
|
||||
}
|
||||
|
||||
@ -176,20 +125,7 @@ func (css *consensusStateStore) utxoByOutpointFromStagedVirtualUTXODiff(dbContex
|
||||
return entry, nil
|
||||
}
|
||||
|
||||
func (css *consensusStateStore) utxoByOutpointFromStagedVirtualUTXOSet(outpoint *externalapi.DomainOutpoint) (
|
||||
externalapi.UTXOEntry, error) {
|
||||
if utxoEntry, ok := css.virtualUTXOSetStaging.Get(outpoint); ok {
|
||||
return utxoEntry, nil
|
||||
}
|
||||
|
||||
return nil, errors.Errorf("outpoint was not found")
|
||||
}
|
||||
|
||||
func (css *consensusStateStore) HasUTXOByOutpoint(dbContext model.DBReader, outpoint *externalapi.DomainOutpoint) (bool, error) {
|
||||
if css.virtualUTXOSetStaging != nil {
|
||||
return css.hasUTXOByOutpointFromStagedVirtualUTXOSet(outpoint), nil
|
||||
}
|
||||
|
||||
return css.hasUTXOByOutpointFromStagedVirtualUTXODiff(dbContext, outpoint)
|
||||
}
|
||||
|
||||
@ -213,10 +149,6 @@ func (css *consensusStateStore) hasUTXOByOutpointFromStagedVirtualUTXODiff(dbCon
|
||||
return dbContext.Has(key)
|
||||
}
|
||||
|
||||
func (css *consensusStateStore) hasUTXOByOutpointFromStagedVirtualUTXOSet(outpoint *externalapi.DomainOutpoint) bool {
|
||||
return css.virtualUTXOSetStaging.Contains(outpoint)
|
||||
}
|
||||
|
||||
func (css *consensusStateStore) VirtualUTXOSetIterator(dbContext model.DBReader) (model.ReadOnlyUTXOSetIterator, error) {
|
||||
cursor, err := dbContext.Cursor(utxoSetBucket)
|
||||
if err != nil {
|
||||
@ -239,6 +171,10 @@ func newCursorUTXOSetIterator(cursor model.DBCursor) model.ReadOnlyUTXOSetIterat
|
||||
return &utxoSetIterator{cursor: cursor}
|
||||
}
|
||||
|
||||
func (u utxoSetIterator) First() bool {
|
||||
return u.cursor.First()
|
||||
}
|
||||
|
||||
func (u utxoSetIterator) Next() bool {
|
||||
return u.cursor.Next()
|
||||
}
|
||||
@ -266,25 +202,3 @@ func (u utxoSetIterator) Get() (outpoint *externalapi.DomainOutpoint, utxoEntry
|
||||
|
||||
return outpoint, utxoEntry, nil
|
||||
}
|
||||
|
||||
func (css *consensusStateStore) StageVirtualUTXOSet(virtualUTXOSetIterator model.ReadOnlyUTXOSetIterator) error {
|
||||
if css.virtualUTXODiffStaging != nil {
|
||||
return errors.New("cannot stage virtual UTXO set while virtual UTXO diff is staged")
|
||||
}
|
||||
|
||||
utxoMap := make(map[externalapi.DomainOutpoint]externalapi.UTXOEntry)
|
||||
for virtualUTXOSetIterator.Next() {
|
||||
outpoint, entry, err := virtualUTXOSetIterator.Get()
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
if _, exists := utxoMap[*outpoint]; exists {
|
||||
return errors.Errorf("outpoint %s is found more than once in the given iterator", outpoint)
|
||||
}
|
||||
utxoMap[*outpoint] = entry
|
||||
}
|
||||
css.virtualUTXOSetStaging = utxo.NewUTXOCollection(utxoMap)
|
||||
|
||||
return nil
|
||||
}
|
||||
|
@ -0,0 +1,81 @@
|
||||
package consensusstatestore
|
||||
|
||||
import (
|
||||
"github.com/kaspanet/kaspad/domain/consensus/database"
|
||||
"github.com/kaspanet/kaspad/domain/consensus/model"
|
||||
"github.com/pkg/errors"
|
||||
)
|
||||
|
||||
var importingPruningPointUTXOSetKey = database.MakeBucket(nil).Key([]byte("importing-pruning-point-utxo-set"))
|
||||
|
||||
func (css *consensusStateStore) StartImportingPruningPointUTXOSet(dbContext model.DBWriter) error {
|
||||
return dbContext.Put(importingPruningPointUTXOSetKey, []byte{0})
|
||||
}
|
||||
|
||||
func (css *consensusStateStore) HadStartedImportingPruningPointUTXOSet(dbContext model.DBWriter) (bool, error) {
|
||||
return dbContext.Has(importingPruningPointUTXOSetKey)
|
||||
}
|
||||
|
||||
func (css *consensusStateStore) FinishImportingPruningPointUTXOSet(dbContext model.DBWriter) error {
|
||||
return dbContext.Delete(importingPruningPointUTXOSetKey)
|
||||
}
|
||||
|
||||
func (css *consensusStateStore) ImportPruningPointUTXOSetIntoVirtualUTXOSet(dbContext model.DBWriter,
|
||||
pruningPointUTXOSetIterator model.ReadOnlyUTXOSetIterator) error {
|
||||
|
||||
if css.virtualUTXODiffStaging != nil {
|
||||
return errors.New("cannot import virtual UTXO set while virtual UTXO diff is staged")
|
||||
}
|
||||
|
||||
hadStartedImportingPruningPointUTXOSet, err := css.HadStartedImportingPruningPointUTXOSet(dbContext)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
if !hadStartedImportingPruningPointUTXOSet {
|
||||
return errors.New("cannot import pruning point UTXO set " +
|
||||
"without calling StartImportingPruningPointUTXOSet first")
|
||||
}
|
||||
|
||||
// Clear the cache
|
||||
css.virtualUTXOSetCache.Clear()
|
||||
|
||||
// Delete all the old UTXOs from the database
|
||||
deleteCursor, err := dbContext.Cursor(utxoSetBucket)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
for ok := deleteCursor.First(); ok; ok = deleteCursor.Next() {
|
||||
key, err := deleteCursor.Key()
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
err = dbContext.Delete(key)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
}
|
||||
|
||||
// Insert all the new UTXOs into the database
|
||||
for ok := pruningPointUTXOSetIterator.First(); ok; ok = pruningPointUTXOSetIterator.Next() {
|
||||
outpoint, entry, err := pruningPointUTXOSetIterator.Get()
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
key, err := utxoKey(outpoint)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
serializedUTXOEntry, err := serializeUTXOEntry(entry)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
err = dbContext.Put(key, serializedUTXOEntry)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
@ -0,0 +1,213 @@
|
||||
package pruningstore
|
||||
|
||||
import (
|
||||
"github.com/golang/protobuf/proto"
|
||||
"github.com/kaspanet/kaspad/domain/consensus/database"
|
||||
"github.com/kaspanet/kaspad/domain/consensus/database/serialization"
|
||||
"github.com/kaspanet/kaspad/domain/consensus/model"
|
||||
"github.com/kaspanet/kaspad/domain/consensus/model/externalapi"
|
||||
)
|
||||
|
||||
var importedPruningPointUTXOsBucket = database.MakeBucket([]byte("imported-pruning-point-utxos"))
|
||||
var importedPruningPointMultiset = database.MakeBucket(nil).Key([]byte("imported-pruning-point-multiset"))
|
||||
|
||||
func (ps *pruningStore) ClearImportedPruningPointUTXOs(dbContext model.DBWriter) error {
|
||||
cursor, err := dbContext.Cursor(importedPruningPointUTXOsBucket)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
for ok := cursor.First(); ok; ok = cursor.Next() {
|
||||
key, err := cursor.Key()
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
err = dbContext.Delete(key)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
func (ps *pruningStore) AppendImportedPruningPointUTXOs(dbTx model.DBTransaction,
|
||||
outpointAndUTXOEntryPairs []*externalapi.OutpointAndUTXOEntryPair) error {
|
||||
|
||||
for _, outpointAndUTXOEntryPair := range outpointAndUTXOEntryPairs {
|
||||
key, err := ps.importedPruningPointUTXOKey(outpointAndUTXOEntryPair.Outpoint)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
serializedUTXOEntry, err := serializeUTXOEntry(outpointAndUTXOEntryPair.UTXOEntry)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
err = dbTx.Put(key, serializedUTXOEntry)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
func (ps *pruningStore) ImportedPruningPointUTXOIterator(dbContext model.DBReader) (model.ReadOnlyUTXOSetIterator, error) {
|
||||
cursor, err := dbContext.Cursor(importedPruningPointUTXOsBucket)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
return ps.newCursorUTXOSetIterator(cursor), nil
|
||||
}
|
||||
|
||||
type utxoSetIterator struct {
|
||||
cursor model.DBCursor
|
||||
}
|
||||
|
||||
func (ps *pruningStore) newCursorUTXOSetIterator(cursor model.DBCursor) model.ReadOnlyUTXOSetIterator {
|
||||
return &utxoSetIterator{cursor: cursor}
|
||||
}
|
||||
|
||||
func (u *utxoSetIterator) First() bool {
|
||||
return u.cursor.First()
|
||||
}
|
||||
|
||||
func (u *utxoSetIterator) Next() bool {
|
||||
return u.cursor.Next()
|
||||
}
|
||||
|
||||
func (u *utxoSetIterator) Get() (outpoint *externalapi.DomainOutpoint, utxoEntry externalapi.UTXOEntry, err error) {
|
||||
key, err := u.cursor.Key()
|
||||
if err != nil {
|
||||
panic(err)
|
||||
}
|
||||
|
||||
utxoEntryBytes, err := u.cursor.Value()
|
||||
if err != nil {
|
||||
return nil, nil, err
|
||||
}
|
||||
|
||||
outpoint, err = deserializeOutpoint(key.Suffix())
|
||||
if err != nil {
|
||||
return nil, nil, err
|
||||
}
|
||||
|
||||
utxoEntry, err = deserializeUTXOEntry(utxoEntryBytes)
|
||||
if err != nil {
|
||||
return nil, nil, err
|
||||
}
|
||||
|
||||
return outpoint, utxoEntry, nil
|
||||
}
|
||||
|
||||
func (ps *pruningStore) importedPruningPointUTXOKey(outpoint *externalapi.DomainOutpoint) (model.DBKey, error) {
|
||||
serializedOutpoint, err := serializeOutpoint(outpoint)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
return importedPruningPointUTXOsBucket.Key(serializedOutpoint), nil
|
||||
}
|
||||
|
||||
func serializeOutpoint(outpoint *externalapi.DomainOutpoint) ([]byte, error) {
|
||||
return proto.Marshal(serialization.DomainOutpointToDbOutpoint(outpoint))
|
||||
}
|
||||
|
||||
func serializeUTXOEntry(entry externalapi.UTXOEntry) ([]byte, error) {
|
||||
return proto.Marshal(serialization.UTXOEntryToDBUTXOEntry(entry))
|
||||
}
|
||||
|
||||
func deserializeOutpoint(outpointBytes []byte) (*externalapi.DomainOutpoint, error) {
|
||||
dbOutpoint := &serialization.DbOutpoint{}
|
||||
err := proto.Unmarshal(outpointBytes, dbOutpoint)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
return serialization.DbOutpointToDomainOutpoint(dbOutpoint)
|
||||
}
|
||||
|
||||
func deserializeUTXOEntry(entryBytes []byte) (externalapi.UTXOEntry, error) {
|
||||
dbEntry := &serialization.DbUtxoEntry{}
|
||||
err := proto.Unmarshal(entryBytes, dbEntry)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
return serialization.DBUTXOEntryToUTXOEntry(dbEntry)
|
||||
}
|
||||
|
||||
func (ps *pruningStore) ClearImportedPruningPointMultiset(dbContext model.DBWriter) error {
|
||||
return dbContext.Delete(importedPruningPointMultiset)
|
||||
}
|
||||
|
||||
func (ps *pruningStore) ImportedPruningPointMultiset(dbContext model.DBReader) (model.Multiset, error) {
|
||||
multisetBytes, err := dbContext.Get(importedPruningPointMultiset)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
return ps.deserializeMultiset(multisetBytes)
|
||||
}
|
||||
|
||||
func (ps *pruningStore) UpdateImportedPruningPointMultiset(dbTx model.DBTransaction, multiset model.Multiset) error {
|
||||
multisetBytes, err := ps.serializeMultiset(multiset)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
return dbTx.Put(importedPruningPointMultiset, multisetBytes)
|
||||
}
|
||||
|
||||
func (ps *pruningStore) serializeMultiset(multiset model.Multiset) ([]byte, error) {
|
||||
return proto.Marshal(serialization.MultisetToDBMultiset(multiset))
|
||||
}
|
||||
|
||||
func (ps *pruningStore) deserializeMultiset(multisetBytes []byte) (model.Multiset, error) {
|
||||
dbMultiset := &serialization.DbMultiset{}
|
||||
err := proto.Unmarshal(multisetBytes, dbMultiset)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
return serialization.DBMultisetToMultiset(dbMultiset)
|
||||
}
|
||||
|
||||
func (ps *pruningStore) CommitImportedPruningPointUTXOSet(dbContext model.DBWriter) error {
|
||||
// Delete all the old UTXOs from the database
|
||||
deleteCursor, err := dbContext.Cursor(pruningPointUTXOSetBucket)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
for ok := deleteCursor.First(); ok; ok = deleteCursor.Next() {
|
||||
key, err := deleteCursor.Key()
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
err = dbContext.Delete(key)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
}
|
||||
|
||||
// Insert all the new UTXOs into the database
|
||||
insertCursor, err := dbContext.Cursor(importedPruningPointUTXOsBucket)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
for ok := insertCursor.First(); ok; ok = insertCursor.Next() {
|
||||
importedPruningPointUTXOSetKey, err := insertCursor.Key()
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
pruningPointUTXOSetKey := pruningPointUTXOSetBucket.Key(importedPruningPointUTXOSetKey.Suffix())
|
||||
|
||||
serializedUTXOEntry, err := insertCursor.Value()
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
err = dbContext.Put(pruningPointUTXOSetKey, serializedUTXOEntry)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
@ -10,15 +10,21 @@ import (
|
||||
|
||||
var pruningBlockHashKey = database.MakeBucket(nil).Key([]byte("pruning-block-hash"))
|
||||
var candidatePruningPointHashKey = database.MakeBucket(nil).Key([]byte("candidate-pruning-point-hash"))
|
||||
var pruningSerializedUTXOSetKey = database.MakeBucket(nil).Key([]byte("pruning-utxo-set"))
|
||||
var pruningPointUTXOSetBucket = database.MakeBucket([]byte("pruning-point-utxo-set"))
|
||||
|
||||
// pruningStore represents a store for the current pruning state
|
||||
type pruningStore struct {
|
||||
pruningPointStaging *externalapi.DomainHash
|
||||
pruningPointCandidateStaging *externalapi.DomainHash
|
||||
serializedUTXOSetStaging []byte
|
||||
pruningPointCandidateCache *externalapi.DomainHash
|
||||
pruningPointCache *externalapi.DomainHash
|
||||
pruningPointCandidateStaging *externalapi.DomainHash
|
||||
pruningPointCandidateCache *externalapi.DomainHash
|
||||
|
||||
pruningPointUTXOSetStaging model.ReadOnlyUTXOSetIterator
|
||||
}
|
||||
|
||||
// New instantiates a new PruningStore
|
||||
func New() model.PruningStore {
|
||||
return &pruningStore{}
|
||||
}
|
||||
|
||||
func (ps *pruningStore) StagePruningPointCandidate(candidate *externalapi.DomainHash) {
|
||||
@ -59,24 +65,22 @@ func (ps *pruningStore) HasPruningPointCandidate(dbContext model.DBReader) (bool
|
||||
return dbContext.Has(candidatePruningPointHashKey)
|
||||
}
|
||||
|
||||
// New instantiates a new PruningStore
|
||||
func New() model.PruningStore {
|
||||
return &pruningStore{}
|
||||
// Stage stages the pruning state
|
||||
func (ps *pruningStore) StagePruningPoint(pruningPointBlockHash *externalapi.DomainHash) {
|
||||
ps.pruningPointStaging = pruningPointBlockHash
|
||||
}
|
||||
|
||||
// Stage stages the pruning state
|
||||
func (ps *pruningStore) StagePruningPoint(pruningPointBlockHash *externalapi.DomainHash, pruningPointUTXOSetBytes []byte) {
|
||||
ps.pruningPointStaging = pruningPointBlockHash
|
||||
ps.serializedUTXOSetStaging = pruningPointUTXOSetBytes
|
||||
func (ps *pruningStore) StagePruningPointUTXOSet(pruningPointUTXOSetIterator model.ReadOnlyUTXOSetIterator) {
|
||||
ps.pruningPointUTXOSetStaging = pruningPointUTXOSetIterator
|
||||
}
|
||||
|
||||
func (ps *pruningStore) IsStaged() bool {
|
||||
return ps.pruningPointStaging != nil || ps.serializedUTXOSetStaging != nil
|
||||
return ps.pruningPointStaging != nil || ps.pruningPointUTXOSetStaging != nil
|
||||
}
|
||||
|
||||
func (ps *pruningStore) Discard() {
|
||||
ps.pruningPointStaging = nil
|
||||
ps.serializedUTXOSetStaging = nil
|
||||
ps.pruningPointUTXOSetStaging = nil
|
||||
}
|
||||
|
||||
func (ps *pruningStore) Commit(dbTx model.DBTransaction) error {
|
||||
@ -104,15 +108,43 @@ func (ps *pruningStore) Commit(dbTx model.DBTransaction) error {
|
||||
ps.pruningPointCandidateCache = ps.pruningPointCandidateStaging
|
||||
}
|
||||
|
||||
if ps.serializedUTXOSetStaging != nil {
|
||||
utxoSetBytes, err := ps.serializeUTXOSetBytes(ps.serializedUTXOSetStaging)
|
||||
if ps.pruningPointUTXOSetStaging != nil {
|
||||
// Delete all the old UTXOs from the database
|
||||
deleteCursor, err := dbTx.Cursor(pruningPointUTXOSetBucket)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
err = dbTx.Put(pruningSerializedUTXOSetKey, utxoSetBytes)
|
||||
for ok := deleteCursor.First(); ok; ok = deleteCursor.Next() {
|
||||
key, err := deleteCursor.Key()
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
err = dbTx.Delete(key)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
}
|
||||
|
||||
// Insert all the new UTXOs into the database
|
||||
for ok := ps.pruningPointUTXOSetStaging.First(); ok; ok = ps.pruningPointUTXOSetStaging.Next() {
|
||||
outpoint, entry, err := ps.pruningPointUTXOSetStaging.Get()
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
serializedOutpoint, err := serializeOutpoint(outpoint)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
key := pruningPointUTXOSetBucket.Key(serializedOutpoint)
|
||||
serializedUTXOEntry, err := serializeUTXOEntry(entry)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
err = dbTx.Put(key, serializedUTXOEntry)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
ps.Discard()
|
||||
@ -142,24 +174,6 @@ func (ps *pruningStore) PruningPoint(dbContext model.DBReader) (*externalapi.Dom
|
||||
return pruningPoint, nil
|
||||
}
|
||||
|
||||
// PruningPointSerializedUTXOSet returns the serialized UTXO set of the current pruning point
|
||||
func (ps *pruningStore) PruningPointSerializedUTXOSet(dbContext model.DBReader) ([]byte, error) {
|
||||
if ps.serializedUTXOSetStaging != nil {
|
||||
return ps.serializedUTXOSetStaging, nil
|
||||
}
|
||||
|
||||
dbPruningPointUTXOSetBytes, err := dbContext.Get(pruningSerializedUTXOSetKey)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
pruningPointUTXOSet, err := ps.deserializeUTXOSetBytes(dbPruningPointUTXOSetBytes)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
return pruningPointUTXOSet, nil
|
||||
}
|
||||
|
||||
func (ps *pruningStore) serializeHash(hash *externalapi.DomainHash) ([]byte, error) {
|
||||
return proto.Marshal(serialization.DomainHashToDbHash(hash))
|
||||
}
|
||||
@ -199,3 +213,31 @@ func (ps *pruningStore) HasPruningPoint(dbContext model.DBReader) (bool, error)
|
||||
|
||||
return dbContext.Has(pruningBlockHashKey)
|
||||
}
|
||||
|
||||
func (ps *pruningStore) PruningPointUTXOs(dbContext model.DBReader,
|
||||
offset int, limit int) ([]*externalapi.OutpointAndUTXOEntryPair, error) {
|
||||
|
||||
cursor, err := dbContext.Cursor(pruningPointUTXOSetBucket)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
pruningPointUTXOIterator := ps.newCursorUTXOSetIterator(cursor)
|
||||
|
||||
offsetIndex := 0
|
||||
for offsetIndex < offset && pruningPointUTXOIterator.Next() {
|
||||
offsetIndex++
|
||||
}
|
||||
|
||||
outpointAndUTXOEntryPairs := make([]*externalapi.OutpointAndUTXOEntryPair, 0, limit)
|
||||
for len(outpointAndUTXOEntryPairs) < limit && pruningPointUTXOIterator.Next() {
|
||||
outpoint, utxoEntry, err := pruningPointUTXOIterator.Get()
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
outpointAndUTXOEntryPairs = append(outpointAndUTXOEntryPairs, &externalapi.OutpointAndUTXOEntryPair{
|
||||
Outpoint: outpoint,
|
||||
UTXOEntry: utxoEntry,
|
||||
})
|
||||
}
|
||||
return outpointAndUTXOEntryPairs, nil
|
||||
}
|
||||
|
@ -357,6 +357,15 @@ func (f *factory) NewConsensus(dagParams *dagconfig.Params, db infrastructuredat
|
||||
}
|
||||
}
|
||||
|
||||
err = consensusStateManager.RecoverUTXOIfRequired()
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
err = pruningManager.ClearImportedPruningPointData()
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
return c, nil
|
||||
}
|
||||
|
||||
|
@ -45,6 +45,8 @@ type DBReader interface {
|
||||
|
||||
// DBWriter is an interface to write to the database
|
||||
type DBWriter interface {
|
||||
DBReader
|
||||
|
||||
// Put sets the value for the given key. It overwrites
|
||||
// any previous value for that key.
|
||||
Put(key DBKey, value []byte) error
|
||||
@ -58,7 +60,6 @@ type DBWriter interface {
|
||||
// access that requires an open database transaction
|
||||
type DBTransaction interface {
|
||||
DBWriter
|
||||
DBReader
|
||||
|
||||
// Rollback rolls back whatever changes were made to the
|
||||
// database within this transaction.
|
||||
@ -77,7 +78,7 @@ type DBTransaction interface {
|
||||
// DBManager defines the interface of a database that can begin
|
||||
// transactions and read data.
|
||||
type DBManager interface {
|
||||
DBReader
|
||||
DBWriter
|
||||
|
||||
// Begin begins a new database transaction.
|
||||
Begin() (DBTransaction, error)
|
||||
|
@ -13,9 +13,11 @@ type Consensus interface {
|
||||
|
||||
GetHashesBetween(lowHash, highHash *DomainHash, maxBlueScoreDifference uint64) ([]*DomainHash, error)
|
||||
GetMissingBlockBodyHashes(highHash *DomainHash) ([]*DomainHash, error)
|
||||
GetPruningPointUTXOSet(expectedPruningPointHash *DomainHash) ([]byte, error)
|
||||
GetPruningPointUTXOs(expectedPruningPointHash *DomainHash, offset int, limit int) ([]*OutpointAndUTXOEntryPair, error)
|
||||
PruningPoint() (*DomainHash, error)
|
||||
ValidateAndInsertPruningPoint(newPruningPoint *DomainBlock, serializedUTXOSet []byte) error
|
||||
ClearImportedPruningPointData() error
|
||||
AppendImportedPruningPointUTXOs(outpointAndUTXOEntryPairs []*OutpointAndUTXOEntryPair) error
|
||||
ValidateAndInsertImportedPruningPoint(newPruningPoint *DomainBlock) error
|
||||
GetVirtualSelectedParent() (*DomainHash, error)
|
||||
CreateBlockLocator(lowHash, highHash *DomainHash, limit uint32) (BlockLocator, error)
|
||||
CreateHeadersSelectedChainBlockLocator(lowHash, highHash *DomainHash) (BlockLocator, error)
|
||||
|
@ -11,3 +11,10 @@ type UTXOEntry interface {
|
||||
IsCoinbase() bool
|
||||
Equal(other UTXOEntry) bool
|
||||
}
|
||||
|
||||
// OutpointAndUTXOEntryPair is an outpoint along with its
|
||||
// respective UTXO entry
|
||||
type OutpointAndUTXOEntryPair struct {
|
||||
Outpoint *DomainOutpoint
|
||||
UTXOEntry UTXOEntry
|
||||
}
|
||||
|
@ -7,8 +7,7 @@ type ConsensusStateStore interface {
|
||||
Store
|
||||
IsStaged() bool
|
||||
|
||||
StageVirtualUTXODiff(virtualUTXODiff UTXODiff) error
|
||||
StageVirtualUTXOSet(virtualUTXOSetIterator ReadOnlyUTXOSetIterator) error
|
||||
StageVirtualUTXODiff(virtualUTXODiff UTXODiff)
|
||||
UTXOByOutpoint(dbContext DBReader, outpoint *externalapi.DomainOutpoint) (externalapi.UTXOEntry, error)
|
||||
HasUTXOByOutpoint(dbContext DBReader, outpoint *externalapi.DomainOutpoint) (bool, error)
|
||||
VirtualUTXOSetIterator(dbContext DBReader) (ReadOnlyUTXOSetIterator, error)
|
||||
@ -18,4 +17,9 @@ type ConsensusStateStore interface {
|
||||
|
||||
StageTips(tipHashes []*externalapi.DomainHash)
|
||||
Tips(dbContext DBReader) ([]*externalapi.DomainHash, error)
|
||||
|
||||
StartImportingPruningPointUTXOSet(dbContext DBWriter) error
|
||||
HadStartedImportingPruningPointUTXOSet(dbContext DBWriter) (bool, error)
|
||||
ImportPruningPointUTXOSetIntoVirtualUTXOSet(dbContext DBWriter, pruningPointUTXOSetIterator ReadOnlyUTXOSetIterator) error
|
||||
FinishImportingPruningPointUTXOSet(dbContext DBWriter) error
|
||||
}
|
||||
|
@ -5,12 +5,20 @@ import "github.com/kaspanet/kaspad/domain/consensus/model/externalapi"
|
||||
// PruningStore represents a store for the current pruning state
|
||||
type PruningStore interface {
|
||||
Store
|
||||
StagePruningPoint(pruningPointBlockHash *externalapi.DomainHash, pruningPointUTXOSetBytes []byte)
|
||||
StagePruningPoint(pruningPointBlockHash *externalapi.DomainHash)
|
||||
StagePruningPointUTXOSet(pruningPointUTXOSetIterator ReadOnlyUTXOSetIterator)
|
||||
StagePruningPointCandidate(candidate *externalapi.DomainHash)
|
||||
IsStaged() bool
|
||||
PruningPointCandidate(dbContext DBReader) (*externalapi.DomainHash, error)
|
||||
HasPruningPointCandidate(dbContext DBReader) (bool, error)
|
||||
PruningPoint(dbContext DBReader) (*externalapi.DomainHash, error)
|
||||
HasPruningPoint(dbContext DBReader) (bool, error)
|
||||
PruningPointSerializedUTXOSet(dbContext DBReader) ([]byte, error)
|
||||
ClearImportedPruningPointUTXOs(dbContext DBWriter) error
|
||||
AppendImportedPruningPointUTXOs(dbTx DBTransaction, outpointAndUTXOEntryPairs []*externalapi.OutpointAndUTXOEntryPair) error
|
||||
ImportedPruningPointUTXOIterator(dbContext DBReader) (ReadOnlyUTXOSetIterator, error)
|
||||
ClearImportedPruningPointMultiset(dbContext DBWriter) error
|
||||
ImportedPruningPointMultiset(dbContext DBReader) (Multiset, error)
|
||||
UpdateImportedPruningPointMultiset(dbTx DBTransaction, multiset Multiset) error
|
||||
CommitImportedPruningPointUTXOSet(dbContext DBWriter) error
|
||||
PruningPointUTXOs(dbContext DBReader, offset int, limit int) ([]*externalapi.OutpointAndUTXOEntryPair, error)
|
||||
}
|
||||
|
@ -5,5 +5,5 @@ import "github.com/kaspanet/kaspad/domain/consensus/model/externalapi"
|
||||
// BlockProcessor is responsible for processing incoming blocks
|
||||
type BlockProcessor interface {
|
||||
ValidateAndInsertBlock(block *externalapi.DomainBlock) (*externalapi.BlockInsertionResult, error)
|
||||
ValidateAndInsertPruningPoint(newPruningPoint *externalapi.DomainBlock, serializedUTXOSet []byte) error
|
||||
ValidateAndInsertImportedPruningPoint(newPruningPoint *externalapi.DomainBlock) error
|
||||
}
|
||||
|
@ -6,8 +6,9 @@ import "github.com/kaspanet/kaspad/domain/consensus/model/externalapi"
|
||||
type ConsensusStateManager interface {
|
||||
AddBlock(blockHash *externalapi.DomainHash) (*externalapi.SelectedChainPath, error)
|
||||
PopulateTransactionWithUTXOEntries(transaction *externalapi.DomainTransaction) error
|
||||
UpdatePruningPoint(newPruningPoint *externalapi.DomainBlock, serializedUTXOSet []byte) error
|
||||
ImportPruningPoint(newPruningPoint *externalapi.DomainBlock) error
|
||||
RestorePastUTXOSetIterator(blockHash *externalapi.DomainHash) (ReadOnlyUTXOSetIterator, error)
|
||||
CalculatePastUTXOAndAcceptanceData(blockHash *externalapi.DomainHash) (UTXODiff, externalapi.AcceptanceData, Multiset, error)
|
||||
GetVirtualSelectedParentChainFromBlock(blockHash *externalapi.DomainHash) (*externalapi.SelectedChainPath, error)
|
||||
RecoverUTXOIfRequired() error
|
||||
}
|
||||
|
@ -6,4 +6,6 @@ import "github.com/kaspanet/kaspad/domain/consensus/model/externalapi"
|
||||
type PruningManager interface {
|
||||
UpdatePruningPointByVirtual() error
|
||||
IsValidPruningPoint(blockHash *externalapi.DomainHash) (bool, error)
|
||||
ClearImportedPruningPointData() error
|
||||
AppendImportedPruningPointUTXOs(outpointAndUTXOEntryPairs []*externalapi.OutpointAndUTXOEntryPair) error
|
||||
}
|
||||
|
@ -11,6 +11,7 @@ type ReadOnlyUTXOSet interface {
|
||||
// ReadOnlyUTXOSetIterator is an iterator over all entries in a
|
||||
// ReadOnlyUTXOSet
|
||||
type ReadOnlyUTXOSetIterator interface {
|
||||
First() bool
|
||||
Next() bool
|
||||
Get() (outpoint *externalapi.DomainOutpoint, utxoEntry externalapi.UTXOEntry, err error)
|
||||
}
|
||||
|
@ -137,9 +137,9 @@ func (bp *blockProcessor) ValidateAndInsertBlock(block *externalapi.DomainBlock)
|
||||
return bp.validateAndInsertBlock(block, false)
|
||||
}
|
||||
|
||||
func (bp *blockProcessor) ValidateAndInsertPruningPoint(newPruningPoint *externalapi.DomainBlock, serializedUTXOSet []byte) error {
|
||||
onEnd := logger.LogAndMeasureExecutionTime(log, "ValidateAndInsertPruningPoint")
|
||||
func (bp *blockProcessor) ValidateAndInsertImportedPruningPoint(newPruningPoint *externalapi.DomainBlock) error {
|
||||
onEnd := logger.LogAndMeasureExecutionTime(log, "ValidateAndInsertImportedPruningPoint")
|
||||
defer onEnd()
|
||||
|
||||
return bp.validateAndInsertPruningPoint(newPruningPoint, serializedUTXOSet)
|
||||
return bp.validateAndInsertImportedPruningPoint(newPruningPoint)
|
||||
}
|
||||
|
@ -87,7 +87,7 @@ func (bp *blockProcessor) validateAndInsertBlock(block *externalapi.DomainBlock,
|
||||
if !isHeaderOnlyBlock {
|
||||
// There's no need to update the consensus state manager when
|
||||
// processing the pruning point since it was already handled
|
||||
// in consensusStateManager.UpdatePruningPoint
|
||||
// in consensusStateManager.ImportPruningPoint
|
||||
if !isPruningPoint {
|
||||
// Attempt to add the block to the virtual
|
||||
selectedParentChainChanges, err = bp.consensusStateManager.AddBlock(blockHash)
|
||||
|
@ -7,7 +7,7 @@ import (
|
||||
"github.com/pkg/errors"
|
||||
)
|
||||
|
||||
func (bp *blockProcessor) validateAndInsertPruningPoint(newPruningPoint *externalapi.DomainBlock, serializedUTXOSet []byte) error {
|
||||
func (bp *blockProcessor) validateAndInsertImportedPruningPoint(newPruningPoint *externalapi.DomainBlock) error {
|
||||
log.Info("Checking that the given pruning point is the expected pruning point")
|
||||
|
||||
newPruningPointHash := consensushashing.BlockHash(newPruningPoint)
|
||||
@ -29,7 +29,7 @@ func (bp *blockProcessor) validateAndInsertPruningPoint(newPruningPoint *externa
|
||||
}
|
||||
|
||||
log.Infof("Updating consensus state manager according to the new pruning point %s", newPruningPointHash)
|
||||
err = bp.consensusStateManager.UpdatePruningPoint(newPruningPoint, serializedUTXOSet)
|
||||
err = bp.consensusStateManager.ImportPruningPoint(newPruningPoint)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
@ -1,9 +1,6 @@
|
||||
package blockprocessor_test
|
||||
|
||||
import (
|
||||
"testing"
|
||||
"time"
|
||||
|
||||
"github.com/kaspanet/kaspad/domain/consensus"
|
||||
"github.com/kaspanet/kaspad/domain/consensus/model/externalapi"
|
||||
"github.com/kaspanet/kaspad/domain/consensus/model/testapi"
|
||||
@ -11,10 +8,10 @@ import (
|
||||
"github.com/kaspanet/kaspad/domain/consensus/utils/consensushashing"
|
||||
"github.com/kaspanet/kaspad/domain/consensus/utils/testutils"
|
||||
"github.com/kaspanet/kaspad/domain/consensus/utils/utxo"
|
||||
"github.com/kaspanet/kaspad/domain/consensus/utils/utxoserialization"
|
||||
"github.com/kaspanet/kaspad/domain/dagconfig"
|
||||
"github.com/pkg/errors"
|
||||
"google.golang.org/protobuf/proto"
|
||||
"testing"
|
||||
"time"
|
||||
)
|
||||
|
||||
func addBlock(tcSyncer, tcSyncee testapi.TestConsensus, parentHashes []*externalapi.DomainHash, t *testing.T) *externalapi.DomainHash {
|
||||
@ -39,7 +36,7 @@ func addBlock(tcSyncer, tcSyncee testapi.TestConsensus, parentHashes []*external
|
||||
return consensushashing.BlockHash(block)
|
||||
}
|
||||
|
||||
func TestValidateAndInsertPruningPoint(t *testing.T) {
|
||||
func TestValidateAndInsertImportedPruningPoint(t *testing.T) {
|
||||
testutils.ForAllNets(t, true, func(t *testing.T, params *dagconfig.Params) {
|
||||
// This is done to reduce the pruning depth to 6 blocks
|
||||
finalityDepth := 3
|
||||
@ -95,9 +92,13 @@ func TestValidateAndInsertPruningPoint(t *testing.T) {
|
||||
t.Fatalf("Unexpected pruning point %s", pruningPoint)
|
||||
}
|
||||
|
||||
pruningPointUTXOSet, err := tcSyncer.GetPruningPointUTXOSet(pruningPoint)
|
||||
pruningPointUTXOs, err := tcSyncer.GetPruningPointUTXOs(pruningPoint, 0, 1000)
|
||||
if err != nil {
|
||||
t.Fatalf("GetPruningPointUTXOSet: %+v", err)
|
||||
t.Fatalf("GetPruningPointUTXOs: %+v", err)
|
||||
}
|
||||
err = tcSyncee.AppendImportedPruningPointUTXOs(pruningPointUTXOs)
|
||||
if err != nil {
|
||||
t.Fatalf("AppendImportedPruningPointUTXOs: %+v", err)
|
||||
}
|
||||
|
||||
tip, err := tcSyncer.GetBlock(tipHash)
|
||||
@ -105,8 +106,8 @@ func TestValidateAndInsertPruningPoint(t *testing.T) {
|
||||
t.Fatalf("GetBlock: %+v", err)
|
||||
}
|
||||
|
||||
// Check that ValidateAndInsertPruningPoint fails for invalid pruning point
|
||||
err = tcSyncee.ValidateAndInsertPruningPoint(tip, pruningPointUTXOSet)
|
||||
// Check that ValidateAndInsertImportedPruningPoint fails for invalid pruning point
|
||||
err = tcSyncee.ValidateAndInsertImportedPruningPoint(tip)
|
||||
if !errors.Is(err, ruleerrors.ErrUnexpectedPruningPoint) {
|
||||
t.Fatalf("Unexpected error: %+v", err)
|
||||
}
|
||||
@ -119,27 +120,40 @@ func TestValidateAndInsertPruningPoint(t *testing.T) {
|
||||
invalidPruningPointBlock := pruningPointBlock.Clone()
|
||||
invalidPruningPointBlock.Transactions[0].Version += 1
|
||||
|
||||
// Check that ValidateAndInsertPruningPoint fails for invalid block
|
||||
err = tcSyncee.ValidateAndInsertPruningPoint(invalidPruningPointBlock, pruningPointUTXOSet)
|
||||
// Check that ValidateAndInsertImportedPruningPoint fails for invalid block
|
||||
err = tcSyncee.ValidateAndInsertImportedPruningPoint(invalidPruningPointBlock)
|
||||
if !errors.Is(err, ruleerrors.ErrBadMerkleRoot) {
|
||||
t.Fatalf("Unexpected error: %+v", err)
|
||||
}
|
||||
|
||||
serializedFakeUTXOSet, err := makeSerializedFakeUTXOSet()
|
||||
err = tcSyncee.ClearImportedPruningPointData()
|
||||
if err != nil {
|
||||
t.Fatalf("makeSerializedFakeUTXOSet: %+v", err)
|
||||
t.Fatalf("ClearImportedPruningPointData: %+v", err)
|
||||
}
|
||||
err = tcSyncee.AppendImportedPruningPointUTXOs(makeFakeUTXOs())
|
||||
if err != nil {
|
||||
t.Fatalf("AppendImportedPruningPointUTXOs: %+v", err)
|
||||
}
|
||||
|
||||
// Check that ValidateAndInsertPruningPoint fails if the UTXO commitment doesn't fit the provided UTXO set.
|
||||
err = tcSyncee.ValidateAndInsertPruningPoint(pruningPointBlock, serializedFakeUTXOSet)
|
||||
// Check that ValidateAndInsertImportedPruningPoint fails if the UTXO commitment doesn't fit the provided UTXO set.
|
||||
err = tcSyncee.ValidateAndInsertImportedPruningPoint(pruningPointBlock)
|
||||
if !errors.Is(err, ruleerrors.ErrBadPruningPointUTXOSet) {
|
||||
t.Fatalf("Unexpected error: %+v", err)
|
||||
}
|
||||
|
||||
// Check that ValidateAndInsertPruningPoint works given the right arguments.
|
||||
err = tcSyncee.ValidateAndInsertPruningPoint(pruningPointBlock, pruningPointUTXOSet)
|
||||
err = tcSyncee.ClearImportedPruningPointData()
|
||||
if err != nil {
|
||||
t.Fatalf("ValidateAndInsertPruningPoint: %+v", err)
|
||||
t.Fatalf("ClearImportedPruningPointData: %+v", err)
|
||||
}
|
||||
err = tcSyncee.AppendImportedPruningPointUTXOs(pruningPointUTXOs)
|
||||
if err != nil {
|
||||
t.Fatalf("AppendImportedPruningPointUTXOs: %+v", err)
|
||||
}
|
||||
|
||||
// Check that ValidateAndInsertImportedPruningPoint works given the right arguments.
|
||||
err = tcSyncee.ValidateAndInsertImportedPruningPoint(pruningPointBlock)
|
||||
if err != nil {
|
||||
t.Fatalf("ValidateAndInsertImportedPruningPoint: %+v", err)
|
||||
}
|
||||
|
||||
virtualSelectedParent, err := tcSyncer.GetVirtualSelectedParent()
|
||||
@ -256,9 +270,13 @@ func TestValidateAndInsertPruningPointWithSideBlocks(t *testing.T) {
|
||||
t.Fatalf("Unexpected pruning point %s", pruningPoint)
|
||||
}
|
||||
|
||||
pruningPointUTXOSet, err := tcSyncer.GetPruningPointUTXOSet(pruningPoint)
|
||||
pruningPointUTXOs, err := tcSyncer.GetPruningPointUTXOs(pruningPoint, 0, 1000)
|
||||
if err != nil {
|
||||
t.Fatalf("GetPruningPointUTXOSet: %+v", err)
|
||||
t.Fatalf("GetPruningPointUTXOs: %+v", err)
|
||||
}
|
||||
err = tcSyncee.AppendImportedPruningPointUTXOs(pruningPointUTXOs)
|
||||
if err != nil {
|
||||
t.Fatalf("AppendImportedPruningPointUTXOs: %+v", err)
|
||||
}
|
||||
|
||||
// Check that ValidateAndInsertPruningPoint works.
|
||||
@ -266,7 +284,7 @@ func TestValidateAndInsertPruningPointWithSideBlocks(t *testing.T) {
|
||||
if err != nil {
|
||||
t.Fatalf("GetBlock: %+v", err)
|
||||
}
|
||||
err = tcSyncee.ValidateAndInsertPruningPoint(pruningPointBlock, pruningPointUTXOSet)
|
||||
err = tcSyncee.ValidateAndInsertImportedPruningPoint(pruningPointBlock)
|
||||
if err != nil {
|
||||
t.Fatalf("ValidateAndInsertPruningPoint: %+v", err)
|
||||
}
|
||||
@ -362,33 +380,37 @@ func TestValidateAndInsertPruningPointWithSideBlocks(t *testing.T) {
|
||||
})
|
||||
}
|
||||
|
||||
type fakeUTXOSetIterator struct {
|
||||
nextCalled bool
|
||||
}
|
||||
|
||||
func (f *fakeUTXOSetIterator) Next() bool {
|
||||
if f.nextCalled {
|
||||
return false
|
||||
}
|
||||
f.nextCalled = true
|
||||
return true
|
||||
}
|
||||
|
||||
func (f *fakeUTXOSetIterator) Get() (outpoint *externalapi.DomainOutpoint, utxoEntry externalapi.UTXOEntry, err error) {
|
||||
return &externalapi.DomainOutpoint{
|
||||
TransactionID: *externalapi.NewDomainTransactionIDFromByteArray(&[externalapi.DomainHashSize]byte{0x01}),
|
||||
func makeFakeUTXOs() []*externalapi.OutpointAndUTXOEntryPair {
|
||||
return []*externalapi.OutpointAndUTXOEntryPair{
|
||||
{
|
||||
Outpoint: &externalapi.DomainOutpoint{
|
||||
TransactionID: externalapi.DomainTransactionID{},
|
||||
Index: 0,
|
||||
}, utxo.NewUTXOEntry(1000, &externalapi.ScriptPublicKey{
|
||||
Script: []byte{1, 2, 3},
|
||||
},
|
||||
UTXOEntry: utxo.NewUTXOEntry(
|
||||
0,
|
||||
&externalapi.ScriptPublicKey{
|
||||
Script: nil,
|
||||
Version: 0,
|
||||
}, false, 2000), nil
|
||||
},
|
||||
false,
|
||||
0,
|
||||
),
|
||||
},
|
||||
{
|
||||
Outpoint: &externalapi.DomainOutpoint{
|
||||
TransactionID: externalapi.DomainTransactionID{},
|
||||
Index: 1,
|
||||
},
|
||||
UTXOEntry: utxo.NewUTXOEntry(
|
||||
2,
|
||||
&externalapi.ScriptPublicKey{
|
||||
Script: nil,
|
||||
Version: 0,
|
||||
},
|
||||
true,
|
||||
3,
|
||||
),
|
||||
},
|
||||
}
|
||||
|
||||
func makeSerializedFakeUTXOSet() ([]byte, error) {
|
||||
serializedUtxo, err := utxoserialization.ReadOnlyUTXOSetToProtoUTXOSet(&fakeUTXOSetIterator{})
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
return proto.Marshal(serializedUtxo)
|
||||
}
|
@ -89,7 +89,7 @@ func checkBlockUTXOCommitment(t *testing.T, consensus testapi.TestConsensus, blo
|
||||
|
||||
// Build a Multiset
|
||||
ms := multiset.New()
|
||||
for utxoSetIterator.Next() {
|
||||
for ok := utxoSetIterator.First(); ok; ok = utxoSetIterator.Next() {
|
||||
outpoint, entry, err := utxoSetIterator.Get()
|
||||
if err != nil {
|
||||
t.Fatalf("Error getting from UTXOSet iterator: %+v", err)
|
||||
|
@ -0,0 +1,218 @@
|
||||
package consensusstatemanager
|
||||
|
||||
import (
|
||||
"github.com/kaspanet/kaspad/domain/consensus/model"
|
||||
"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/transactionhelper"
|
||||
"github.com/kaspanet/kaspad/domain/consensus/utils/utxo"
|
||||
"github.com/kaspanet/kaspad/infrastructure/logger"
|
||||
"github.com/pkg/errors"
|
||||
)
|
||||
|
||||
func (csm *consensusStateManager) ImportPruningPoint(newPruningPoint *externalapi.DomainBlock) error {
|
||||
onEnd := logger.LogAndMeasureExecutionTime(log, "ImportPruningPoint")
|
||||
defer onEnd()
|
||||
|
||||
err := csm.importPruningPoint(newPruningPoint)
|
||||
if err != nil {
|
||||
csm.discardImportedPruningPointUTXOSetChanges()
|
||||
return err
|
||||
}
|
||||
|
||||
return csm.applyImportedPruningPointUTXOSet()
|
||||
}
|
||||
|
||||
func (csm *consensusStateManager) importPruningPoint(newPruningPoint *externalapi.DomainBlock) error {
|
||||
log.Debugf("importPruningPoint start")
|
||||
defer log.Debugf("importPruningPoint end")
|
||||
|
||||
newPruningPointHash := consensushashing.BlockHash(newPruningPoint)
|
||||
|
||||
// We ignore the shouldSendNotification return value because we always want to send finality conflict notification
|
||||
// in case the new pruning point violates finality
|
||||
isViolatingFinality, _, err := csm.isViolatingFinality(newPruningPointHash)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
if isViolatingFinality {
|
||||
log.Warnf("Finality Violation Detected! The suggest pruning point %s violates finality!", newPruningPointHash)
|
||||
return errors.Wrapf(ruleerrors.ErrSuggestedPruningViolatesFinality, "%s cannot be a pruning point because "+
|
||||
"it violates finality", newPruningPointHash)
|
||||
}
|
||||
|
||||
importedPruningPointMultiset, err := csm.pruningStore.ImportedPruningPointMultiset(csm.databaseContext)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
newPruningPointHeader, err := csm.blockHeaderStore.BlockHeader(csm.databaseContext, newPruningPointHash)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
log.Debugf("The UTXO commitment of the pruning point: %s",
|
||||
newPruningPointHeader.UTXOCommitment())
|
||||
|
||||
if !newPruningPointHeader.UTXOCommitment().Equal(importedPruningPointMultiset.Hash()) {
|
||||
return errors.Wrapf(ruleerrors.ErrBadPruningPointUTXOSet, "the expected multiset hash of the pruning "+
|
||||
"point UTXO set is %s but got %s", newPruningPointHeader.UTXOCommitment(), *importedPruningPointMultiset.Hash())
|
||||
}
|
||||
log.Debugf("The new pruning point UTXO commitment validation passed")
|
||||
|
||||
log.Debugf("Staging the the pruning point as the only DAG tip")
|
||||
newTips := []*externalapi.DomainHash{newPruningPointHash}
|
||||
csm.consensusStateStore.StageTips(newTips)
|
||||
|
||||
log.Debugf("Setting the pruning point as the only virtual parent")
|
||||
err = csm.dagTopologyManager.SetParents(model.VirtualBlockHash, newTips)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
log.Debugf("Calculating GHOSTDAG for the new virtual")
|
||||
err = csm.ghostdagManager.GHOSTDAG(model.VirtualBlockHash)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
log.Debugf("Deleting all existing virtual diff parents")
|
||||
csm.consensusStateStore.StageVirtualDiffParents(nil)
|
||||
|
||||
log.Debugf("Updating the new pruning point to be the new virtual diff parent with an empty diff")
|
||||
err = csm.stageDiff(newPruningPointHash, utxo.NewUTXODiff(), nil)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
log.Debugf("Staging the new pruning point")
|
||||
csm.pruningStore.StagePruningPoint(newPruningPointHash)
|
||||
|
||||
log.Debugf("Populating the pruning point with UTXO entries")
|
||||
importedPruningPointUTXOIterator, err := csm.pruningStore.ImportedPruningPointUTXOIterator(csm.databaseContext)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
// Clone the pruningPoint block here because validateBlockTransactionsAgainstPastUTXO
|
||||
// assumes that the block UTXOEntries are pre-filled during further validations
|
||||
newPruningPointClone := newPruningPoint.Clone()
|
||||
err = csm.populateTransactionWithUTXOEntriesFromUTXOSet(newPruningPointClone, importedPruningPointUTXOIterator)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
// Before we manually mark the new pruning point as valid, we validate that all of its transactions are valid
|
||||
// against the provided UTXO set.
|
||||
log.Debugf("Validating that the pruning point is UTXO valid")
|
||||
newPruningPointSelectedParentMedianTime, err := csm.pastMedianTimeManager.PastMedianTime(newPruningPointHash)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
log.Tracef("The past median time of pruning block %s is %d",
|
||||
newPruningPointHash, newPruningPointSelectedParentMedianTime)
|
||||
|
||||
for i, transaction := range newPruningPointClone.Transactions {
|
||||
transactionID := consensushashing.TransactionID(transaction)
|
||||
log.Tracef("Validating transaction %s in pruning block %s against "+
|
||||
"the pruning point's past UTXO", transactionID, newPruningPointHash)
|
||||
if i == transactionhelper.CoinbaseTransactionIndex {
|
||||
log.Tracef("Skipping transaction %s because it is the coinbase", transactionID)
|
||||
continue
|
||||
}
|
||||
log.Tracef("Validating transaction %s and populating it with mass and fee", transactionID)
|
||||
err = csm.transactionValidator.ValidateTransactionInContextAndPopulateMassAndFee(
|
||||
transaction, newPruningPointHash, newPruningPointSelectedParentMedianTime)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
log.Tracef("Validation against the pruning point's past UTXO "+
|
||||
"passed for transaction %s", transactionID)
|
||||
}
|
||||
|
||||
log.Debugf("Staging the new pruning point as %s", externalapi.StatusUTXOValid)
|
||||
csm.blockStatusStore.Stage(newPruningPointHash, externalapi.StatusUTXOValid)
|
||||
|
||||
log.Debugf("Staging the new pruning point multiset")
|
||||
csm.multisetStore.Stage(newPruningPointHash, importedPruningPointMultiset)
|
||||
return nil
|
||||
}
|
||||
|
||||
func (csm *consensusStateManager) discardImportedPruningPointUTXOSetChanges() {
|
||||
for _, store := range csm.stores {
|
||||
store.Discard()
|
||||
}
|
||||
}
|
||||
|
||||
func (csm *consensusStateManager) applyImportedPruningPointUTXOSet() error {
|
||||
dbTx, err := csm.databaseContext.Begin()
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
for _, store := range csm.stores {
|
||||
err = store.Commit(dbTx)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
}
|
||||
|
||||
log.Debugf("Starting to import virtual UTXO set and pruning point utxo set")
|
||||
err = csm.consensusStateStore.StartImportingPruningPointUTXOSet(dbTx)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
log.Debugf("Committing all staged data for imported pruning point")
|
||||
err = dbTx.Commit()
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
return csm.importVirtualUTXOSetAndPruningPointUTXOSet()
|
||||
}
|
||||
|
||||
func (csm *consensusStateManager) importVirtualUTXOSetAndPruningPointUTXOSet() error {
|
||||
onEnd := logger.LogAndMeasureExecutionTime(log, "importVirtualUTXOSetAndPruningPointUTXOSet")
|
||||
defer onEnd()
|
||||
|
||||
log.Debugf("Getting an iterator into the imported pruning point utxo set")
|
||||
pruningPointUTXOSetIterator, err := csm.pruningStore.ImportedPruningPointUTXOIterator(csm.databaseContext)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
log.Debugf("Importing the virtual UTXO set")
|
||||
err = csm.consensusStateStore.ImportPruningPointUTXOSetIntoVirtualUTXOSet(csm.databaseContext, pruningPointUTXOSetIterator)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
log.Debugf("Importing the new pruning point UTXO set")
|
||||
err = csm.pruningStore.CommitImportedPruningPointUTXOSet(csm.databaseContext)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
log.Debugf("Finishing to import virtual UTXO set and pruning point UTXO set")
|
||||
return csm.consensusStateStore.FinishImportingPruningPointUTXOSet(csm.databaseContext)
|
||||
}
|
||||
|
||||
func (csm *consensusStateManager) RecoverUTXOIfRequired() error {
|
||||
hadStartedImportingPruningPointUTXOSet, err := csm.consensusStateStore.HadStartedImportingPruningPointUTXOSet(csm.databaseContext)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
if !hadStartedImportingPruningPointUTXOSet {
|
||||
return nil
|
||||
}
|
||||
|
||||
log.Warnf("Unimported pruning point UTXO set detected. Attempting to recover...")
|
||||
err = csm.importVirtualUTXOSetAndPruningPointUTXOSet()
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
log.Warnf("Unimported UTXO set successfully recovered")
|
||||
return nil
|
||||
}
|
@ -75,3 +75,49 @@ func (csm *consensusStateManager) populateTransactionWithUTXOEntriesFromVirtualO
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
func (csm *consensusStateManager) populateTransactionWithUTXOEntriesFromUTXOSet(
|
||||
pruningPoint *externalapi.DomainBlock, iterator model.ReadOnlyUTXOSetIterator) error {
|
||||
|
||||
// Collect the required outpoints from the block
|
||||
outpointsForPopulation := make(map[externalapi.DomainOutpoint]interface{})
|
||||
for _, transaction := range pruningPoint.Transactions {
|
||||
for _, input := range transaction.Inputs {
|
||||
outpointsForPopulation[input.PreviousOutpoint] = struct{}{}
|
||||
}
|
||||
}
|
||||
|
||||
// Collect the UTXO entries from the iterator
|
||||
outpointsToUTXOEntries := make(map[externalapi.DomainOutpoint]externalapi.UTXOEntry, len(outpointsForPopulation))
|
||||
for ok := iterator.First(); ok; ok = iterator.Next() {
|
||||
outpoint, utxoEntry, err := iterator.Get()
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
outpointValue := *outpoint
|
||||
if _, ok := outpointsForPopulation[outpointValue]; ok {
|
||||
outpointsToUTXOEntries[outpointValue] = utxoEntry
|
||||
}
|
||||
if len(outpointsForPopulation) == len(outpointsToUTXOEntries) {
|
||||
break
|
||||
}
|
||||
}
|
||||
|
||||
// Populate the block with the collected UTXO entries
|
||||
var missingOutpoints []*externalapi.DomainOutpoint
|
||||
for _, transaction := range pruningPoint.Transactions {
|
||||
for _, input := range transaction.Inputs {
|
||||
utxoEntry, ok := outpointsToUTXOEntries[input.PreviousOutpoint]
|
||||
if !ok {
|
||||
missingOutpoints = append(missingOutpoints, &input.PreviousOutpoint)
|
||||
continue
|
||||
}
|
||||
input.UTXOEntry = utxoEntry
|
||||
}
|
||||
}
|
||||
|
||||
if len(missingOutpoints) > 0 {
|
||||
return ruleerrors.NewErrMissingTxOut(missingOutpoints)
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
@ -1,174 +0,0 @@
|
||||
package consensusstatemanager
|
||||
|
||||
import (
|
||||
"github.com/golang/protobuf/proto"
|
||||
"github.com/kaspanet/kaspad/domain/consensus/model"
|
||||
"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/serialization"
|
||||
"github.com/kaspanet/kaspad/domain/consensus/utils/utxo"
|
||||
"github.com/kaspanet/kaspad/domain/consensus/utils/utxoserialization"
|
||||
"github.com/kaspanet/kaspad/infrastructure/logger"
|
||||
"github.com/pkg/errors"
|
||||
)
|
||||
|
||||
func (csm *consensusStateManager) UpdatePruningPoint(newPruningPoint *externalapi.DomainBlock, serializedUTXOSet []byte) error {
|
||||
onEnd := logger.LogAndMeasureExecutionTime(log, "UpdatePruningPoint")
|
||||
defer onEnd()
|
||||
|
||||
err := csm.updatePruningPoint(newPruningPoint, serializedUTXOSet)
|
||||
if err != nil {
|
||||
csm.discardSetPruningPointUTXOSetChanges()
|
||||
return err
|
||||
}
|
||||
|
||||
return csm.commitSetPruningPointUTXOSetAll()
|
||||
}
|
||||
|
||||
func (csm *consensusStateManager) updatePruningPoint(newPruningPoint *externalapi.DomainBlock, serializedUTXOSet []byte) error {
|
||||
log.Debugf("updatePruningPoint start")
|
||||
defer log.Debugf("updatePruningPoint end")
|
||||
|
||||
newPruningPointHash := consensushashing.BlockHash(newPruningPoint)
|
||||
|
||||
// We ignore the shouldSendNotification return value because we always want to send finality conflict notification
|
||||
// in case the new pruning point violates finality
|
||||
isViolatingFinality, _, err := csm.isViolatingFinality(newPruningPointHash)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
if isViolatingFinality {
|
||||
log.Warnf("Finality Violation Detected! The suggest pruning point %s violates finality!", newPruningPointHash)
|
||||
return errors.Wrapf(ruleerrors.ErrSuggestedPruningViolatesFinality, "%s cannot be a pruning point because "+
|
||||
"it violates finality", newPruningPointHash)
|
||||
}
|
||||
|
||||
protoUTXOSet := &utxoserialization.ProtoUTXOSet{}
|
||||
err = proto.Unmarshal(serializedUTXOSet, protoUTXOSet)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
utxoSetMultiSet, err := utxoserialization.CalculateMultisetFromProtoUTXOSet(protoUTXOSet)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
log.Debugf("Calculated multiset for given UTXO set: %s", utxoSetMultiSet.Hash())
|
||||
|
||||
newPruningPointHeader, err := csm.blockHeaderStore.BlockHeader(csm.databaseContext, newPruningPointHash)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
log.Debugf("The UTXO commitment of the pruning point: %s",
|
||||
newPruningPointHeader.UTXOCommitment())
|
||||
|
||||
if !newPruningPointHeader.UTXOCommitment().Equal(utxoSetMultiSet.Hash()) {
|
||||
return errors.Wrapf(ruleerrors.ErrBadPruningPointUTXOSet, "the expected multiset hash of the pruning "+
|
||||
"point UTXO set is %s but got %s", newPruningPointHeader.UTXOCommitment(), *utxoSetMultiSet.Hash())
|
||||
}
|
||||
log.Debugf("The new pruning point UTXO commitment validation passed")
|
||||
|
||||
newTips := []*externalapi.DomainHash{newPruningPointHash}
|
||||
|
||||
log.Debugf("Staging the the pruning point as the only DAG tip")
|
||||
csm.consensusStateStore.StageTips(newTips)
|
||||
|
||||
log.Debugf("Setting the pruning point as the only virtual parent")
|
||||
err = csm.dagTopologyManager.SetParents(model.VirtualBlockHash, newTips)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
log.Debugf("Calculating GHOSTDAG for the new virtual")
|
||||
err = csm.ghostdagManager.GHOSTDAG(model.VirtualBlockHash)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
log.Debugf("Staging the virtual UTXO set")
|
||||
err = csm.consensusStateStore.StageVirtualUTXOSet(protoUTXOSetToReadOnlyUTXOSetIterator(protoUTXOSet))
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
log.Debugf("Deleting all the existing virtual diff parents")
|
||||
csm.consensusStateStore.StageVirtualDiffParents(nil)
|
||||
|
||||
log.Debugf("Updating the new pruning point to be the new virtual diff parent with an empty diff")
|
||||
err = csm.stageDiff(newPruningPointHash, utxo.NewUTXODiff(), nil)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
log.Debugf("Staging the new pruning point and its UTXO set")
|
||||
csm.pruningStore.StagePruningPoint(newPruningPointHash, serializedUTXOSet)
|
||||
|
||||
// Before we manually mark the new pruning point as valid, we validate that all of its transactions are valid
|
||||
// against the provided UTXO set.
|
||||
log.Debugf("Validating that the pruning point is UTXO valid")
|
||||
|
||||
// validateBlockTransactionsAgainstPastUTXO pre-fills the block's transactions inputs, which
|
||||
// are assumed to not be pre-filled during further validations.
|
||||
// Therefore - clone newPruningPoint before passing it to validateBlockTransactionsAgainstPastUTXO
|
||||
err = csm.validateBlockTransactionsAgainstPastUTXO(newPruningPoint.Clone(), utxo.NewUTXODiff())
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
log.Debugf("Staging the new pruning point as %s", externalapi.StatusUTXOValid)
|
||||
csm.blockStatusStore.Stage(newPruningPointHash, externalapi.StatusUTXOValid)
|
||||
|
||||
log.Debugf("Staging the new pruning point multiset")
|
||||
csm.multisetStore.Stage(newPruningPointHash, utxoSetMultiSet)
|
||||
return nil
|
||||
}
|
||||
|
||||
func (csm *consensusStateManager) discardSetPruningPointUTXOSetChanges() {
|
||||
for _, store := range csm.stores {
|
||||
store.Discard()
|
||||
}
|
||||
}
|
||||
|
||||
func (csm *consensusStateManager) commitSetPruningPointUTXOSetAll() error {
|
||||
dbTx, err := csm.databaseContext.Begin()
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
for _, store := range csm.stores {
|
||||
err = store.Commit(dbTx)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
}
|
||||
|
||||
return dbTx.Commit()
|
||||
}
|
||||
|
||||
type protoUTXOSetIterator struct {
|
||||
utxoSet *utxoserialization.ProtoUTXOSet
|
||||
index int
|
||||
}
|
||||
|
||||
func (p *protoUTXOSetIterator) Next() bool {
|
||||
p.index++
|
||||
return p.index < len(p.utxoSet.Utxos)
|
||||
}
|
||||
|
||||
func (p *protoUTXOSetIterator) Get() (outpoint *externalapi.DomainOutpoint, utxoEntry externalapi.UTXOEntry, err error) {
|
||||
entry, outpoint, err := utxo.DeserializeUTXO(p.utxoSet.Utxos[p.index].EntryOutpointPair)
|
||||
if err != nil {
|
||||
if serialization.IsMalformedError(err) {
|
||||
return nil, nil, errors.Wrapf(ruleerrors.ErrMalformedUTXO, "malformed utxo: %s", err)
|
||||
}
|
||||
return nil, nil, err
|
||||
}
|
||||
|
||||
return outpoint, entry, nil
|
||||
}
|
||||
|
||||
func protoUTXOSetToReadOnlyUTXOSetIterator(protoUTXOSet *utxoserialization.ProtoUTXOSet) model.ReadOnlyUTXOSetIterator {
|
||||
return &protoUTXOSetIterator{utxoSet: protoUTXOSet, index: -1}
|
||||
}
|
@ -52,10 +52,7 @@ func (csm *consensusStateManager) updateVirtual(newBlockHash *externalapi.Domain
|
||||
csm.multisetStore.Stage(model.VirtualBlockHash, virtualMultiset)
|
||||
|
||||
log.Debugf("Staging new UTXO diff for the virtual block")
|
||||
err = csm.consensusStateStore.StageVirtualUTXODiff(virtualUTXODiff)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
csm.consensusStateStore.StageVirtualUTXODiff(virtualUTXODiff)
|
||||
|
||||
log.Debugf("Updating the virtual diff parents after adding %s to the DAG", newBlockHash)
|
||||
err = csm.updateVirtualDiffParents(virtualUTXODiff)
|
||||
|
@ -1,17 +1,18 @@
|
||||
package pruningmanager
|
||||
|
||||
import (
|
||||
"github.com/golang/protobuf/proto"
|
||||
"github.com/kaspanet/kaspad/domain/consensus/model"
|
||||
"github.com/kaspanet/kaspad/domain/consensus/model/externalapi"
|
||||
"github.com/kaspanet/kaspad/domain/consensus/utils/utxoserialization"
|
||||
"github.com/kaspanet/kaspad/domain/consensus/utils/multiset"
|
||||
"github.com/kaspanet/kaspad/domain/consensus/utils/utxo"
|
||||
"github.com/kaspanet/kaspad/infrastructure/db/database"
|
||||
"github.com/kaspanet/kaspad/infrastructure/logger"
|
||||
"github.com/pkg/errors"
|
||||
)
|
||||
|
||||
// pruningManager resolves and manages the current pruning point
|
||||
type pruningManager struct {
|
||||
databaseContext model.DBReader
|
||||
databaseContext model.DBManager
|
||||
|
||||
dagTraversalManager model.DAGTraversalManager
|
||||
dagTopologyManager model.DAGTopologyManager
|
||||
@ -36,7 +37,7 @@ type pruningManager struct {
|
||||
|
||||
// New instantiates a new PruningManager
|
||||
func New(
|
||||
databaseContext model.DBReader,
|
||||
databaseContext model.DBManager,
|
||||
|
||||
dagTraversalManager model.DAGTraversalManager,
|
||||
dagTopologyManager model.DAGTopologyManager,
|
||||
@ -310,16 +311,20 @@ func (pm *pruningManager) savePruningPoint(pruningPointHash *externalapi.DomainH
|
||||
onEnd := logger.LogAndMeasureExecutionTime(log, "pruningManager.savePruningPoint")
|
||||
defer onEnd()
|
||||
|
||||
utxoIter, err := pm.consensusStateManager.RestorePastUTXOSetIterator(pruningPointHash)
|
||||
utxoSetIterator, err := pm.consensusStateManager.RestorePastUTXOSetIterator(pruningPointHash)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
serializedUtxo, err := pm.calculateAndValidateSerializedUTXOSet(utxoIter, pruningPointHash)
|
||||
// TODO: This is an assert that takes ~30 seconds to run
|
||||
// It must be removed or optimized before launching testnet
|
||||
err = pm.validateUTXOSetFitsCommitment(utxoSetIterator, pruningPointHash)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
pm.pruningStore.StagePruningPoint(pruningPointHash, serializedUtxo)
|
||||
|
||||
pm.pruningStore.StagePruningPoint(pruningPointHash)
|
||||
pm.pruningStore.StagePruningPointUTXOSet(utxoSetIterator)
|
||||
|
||||
return nil
|
||||
}
|
||||
@ -410,32 +415,24 @@ func (pm *pruningManager) pruningPointCandidate() (*externalapi.DomainHash, erro
|
||||
return pm.pruningStore.PruningPointCandidate(pm.databaseContext)
|
||||
}
|
||||
|
||||
func (pm *pruningManager) calculateAndValidateSerializedUTXOSet(
|
||||
iter model.ReadOnlyUTXOSetIterator, pruningPointHash *externalapi.DomainHash) ([]byte, error) {
|
||||
|
||||
serializedUtxo, err := utxoserialization.ReadOnlyUTXOSetToProtoUTXOSet(iter)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
err = pm.validateUTXOSetFitsCommitment(serializedUtxo, pruningPointHash)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
return proto.Marshal(serializedUtxo)
|
||||
}
|
||||
|
||||
// validateUTXOSetFitsCommitment makes sure that the calculated UTXOSet of the new pruning point fits the commitment.
|
||||
// This is a sanity test, to make sure that kaspad doesn't store, and subsequently sends syncing peers the wrong UTXOSet.
|
||||
func (pm *pruningManager) validateUTXOSetFitsCommitment(
|
||||
serializedUtxo *utxoserialization.ProtoUTXOSet, pruningPointHash *externalapi.DomainHash) error {
|
||||
func (pm *pruningManager) validateUTXOSetFitsCommitment(utxoSetIterator model.ReadOnlyUTXOSetIterator,
|
||||
pruningPointHash *externalapi.DomainHash) error {
|
||||
|
||||
utxoSetMultiSet, err := utxoserialization.CalculateMultisetFromProtoUTXOSet(serializedUtxo)
|
||||
utxoSetMultiset := multiset.New()
|
||||
for ok := utxoSetIterator.First(); ok; ok = utxoSetIterator.Next() {
|
||||
outpoint, entry, err := utxoSetIterator.Get()
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
utxoSetHash := utxoSetMultiSet.Hash()
|
||||
serializedUTXO, err := utxo.SerializeUTXO(entry, outpoint)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
utxoSetMultiset.Add(serializedUTXO)
|
||||
}
|
||||
utxoSetHash := utxoSetMultiset.Hash()
|
||||
|
||||
header, err := pm.blockHeaderStore.BlockHeader(pm.databaseContext, pruningPointHash)
|
||||
if err != nil {
|
||||
@ -459,3 +456,47 @@ func (pm *pruningManager) validateUTXOSetFitsCommitment(
|
||||
func (pm *pruningManager) finalityScore(blueScore uint64) uint64 {
|
||||
return blueScore / pm.finalityInterval
|
||||
}
|
||||
|
||||
func (pm *pruningManager) ClearImportedPruningPointData() error {
|
||||
err := pm.pruningStore.ClearImportedPruningPointMultiset(pm.databaseContext)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
return pm.pruningStore.ClearImportedPruningPointUTXOs(pm.databaseContext)
|
||||
}
|
||||
|
||||
func (pm *pruningManager) AppendImportedPruningPointUTXOs(
|
||||
outpointAndUTXOEntryPairs []*externalapi.OutpointAndUTXOEntryPair) error {
|
||||
|
||||
dbTx, err := pm.databaseContext.Begin()
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
defer dbTx.RollbackUnlessClosed()
|
||||
|
||||
importedMultiset, err := pm.pruningStore.ImportedPruningPointMultiset(dbTx)
|
||||
if err != nil {
|
||||
if !database.IsNotFoundError(err) {
|
||||
return err
|
||||
}
|
||||
importedMultiset = multiset.New()
|
||||
}
|
||||
for _, outpointAndUTXOEntryPair := range outpointAndUTXOEntryPairs {
|
||||
serializedUTXO, err := utxo.SerializeUTXO(outpointAndUTXOEntryPair.UTXOEntry, outpointAndUTXOEntryPair.Outpoint)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
importedMultiset.Add(serializedUTXO)
|
||||
}
|
||||
err = pm.pruningStore.UpdateImportedPruningPointMultiset(dbTx, importedMultiset)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
err = pm.pruningStore.AppendImportedPruningPointUTXOs(dbTx, outpointAndUTXOEntryPairs)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
return dbTx.Commit()
|
||||
}
|
||||
|
@ -29,6 +29,11 @@ func (uc utxoCollection) Iterator() model.ReadOnlyUTXOSetIterator {
|
||||
return &utxoCollectionIterator{index: -1, pairs: pairs}
|
||||
}
|
||||
|
||||
func (uci *utxoCollectionIterator) First() bool {
|
||||
uci.index = 0
|
||||
return len(uci.pairs) > 0
|
||||
}
|
||||
|
||||
func (uci *utxoCollectionIterator) Next() bool {
|
||||
uci.index++
|
||||
return uci.index < len(uci.pairs)
|
||||
|
@ -36,10 +36,31 @@ func IteratorWithDiff(iterator model.ReadOnlyUTXOSetIterator, diff model.UTXODif
|
||||
return &readOnlyUTXOIteratorWithDiff{
|
||||
baseIterator: iterator,
|
||||
diff: d,
|
||||
toAddIterator: d.mutableUTXODiff.toAdd.Iterator(),
|
||||
toAddIterator: d.ToAdd().Iterator(),
|
||||
}, nil
|
||||
}
|
||||
|
||||
func (r *readOnlyUTXOIteratorWithDiff) First() bool {
|
||||
baseNotEmpty := r.baseIterator.First()
|
||||
baseEmpty := !baseNotEmpty
|
||||
|
||||
r.toAddIterator = r.diff.ToAdd().Iterator()
|
||||
toAddEmpty := r.diff.ToAdd().Len() == 0
|
||||
|
||||
if baseEmpty {
|
||||
if toAddEmpty {
|
||||
return false
|
||||
}
|
||||
return r.Next()
|
||||
}
|
||||
|
||||
r.currentOutpoint, r.currentUTXOEntry, r.currentErr = r.baseIterator.Get()
|
||||
if r.diff.mutableUTXODiff.toRemove.containsWithBlueScore(r.currentOutpoint, r.currentUTXOEntry.BlockBlueScore()) {
|
||||
return r.Next()
|
||||
}
|
||||
return true
|
||||
}
|
||||
|
||||
func (r *readOnlyUTXOIteratorWithDiff) Next() bool {
|
||||
for r.baseIterator.Next() { // keep looping until we reach an outpoint/entry pair that is not in r.diff.toRemove
|
||||
r.currentOutpoint, r.currentUTXOEntry, r.currentErr = r.baseIterator.Get()
|
||||
|
@ -1,3 +0,0 @@
|
||||
//go:generate protoc --go_out=. --go-grpc_out=. --go_opt=paths=source_relative --go-grpc_opt=paths=source_relative utxo.proto
|
||||
|
||||
package utxoserialization
|
@ -1,15 +0,0 @@
|
||||
package utxoserialization
|
||||
|
||||
import (
|
||||
"github.com/kaspanet/kaspad/domain/consensus/model"
|
||||
"github.com/kaspanet/kaspad/domain/consensus/utils/multiset"
|
||||
)
|
||||
|
||||
// CalculateMultisetFromProtoUTXOSet calculates the Multiset corresponding to the given ProtuUTXOSet
|
||||
func CalculateMultisetFromProtoUTXOSet(protoUTXOSet *ProtoUTXOSet) (model.Multiset, error) {
|
||||
ms := multiset.New()
|
||||
for _, utxo := range protoUTXOSet.Utxos {
|
||||
ms.Add(utxo.EntryOutpointPair)
|
||||
}
|
||||
return ms, nil
|
||||
}
|
@ -1,30 +0,0 @@
|
||||
package utxoserialization
|
||||
|
||||
import (
|
||||
"github.com/kaspanet/kaspad/domain/consensus/model"
|
||||
"github.com/kaspanet/kaspad/domain/consensus/utils/utxo"
|
||||
)
|
||||
|
||||
// ReadOnlyUTXOSetToProtoUTXOSet converts ReadOnlyUTXOSetIterator to ProtoUTXOSet
|
||||
func ReadOnlyUTXOSetToProtoUTXOSet(iter model.ReadOnlyUTXOSetIterator) (*ProtoUTXOSet, error) {
|
||||
protoUTXOSet := &ProtoUTXOSet{
|
||||
Utxos: []*ProtoUTXO{},
|
||||
}
|
||||
|
||||
for iter.Next() {
|
||||
outpoint, entry, err := iter.Get()
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
serializedUTXOBytes, err := utxo.SerializeUTXO(entry, outpoint)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
protoUTXOSet.Utxos = append(protoUTXOSet.Utxos, &ProtoUTXO{
|
||||
EntryOutpointPair: serializedUTXOBytes,
|
||||
})
|
||||
}
|
||||
return protoUTXOSet, nil
|
||||
}
|
@ -1,217 +0,0 @@
|
||||
// Code generated by protoc-gen-go. DO NOT EDIT.
|
||||
// versions:
|
||||
// protoc-gen-go v1.25.0
|
||||
// protoc v3.12.3
|
||||
// source: utxo.proto
|
||||
|
||||
package utxoserialization
|
||||
|
||||
import (
|
||||
proto "github.com/golang/protobuf/proto"
|
||||
protoreflect "google.golang.org/protobuf/reflect/protoreflect"
|
||||
protoimpl "google.golang.org/protobuf/runtime/protoimpl"
|
||||
reflect "reflect"
|
||||
sync "sync"
|
||||
)
|
||||
|
||||
const (
|
||||
// Verify that this generated code is sufficiently up-to-date.
|
||||
_ = protoimpl.EnforceVersion(20 - protoimpl.MinVersion)
|
||||
// Verify that runtime/protoimpl is sufficiently up-to-date.
|
||||
_ = protoimpl.EnforceVersion(protoimpl.MaxVersion - 20)
|
||||
)
|
||||
|
||||
// This is a compile-time assertion that a sufficiently up-to-date version
|
||||
// of the legacy proto package is being used.
|
||||
const _ = proto.ProtoPackageIsVersion4
|
||||
|
||||
type ProtoUTXO struct {
|
||||
state protoimpl.MessageState
|
||||
sizeCache protoimpl.SizeCache
|
||||
unknownFields protoimpl.UnknownFields
|
||||
|
||||
EntryOutpointPair []byte `protobuf:"bytes,1,opt,name=entryOutpointPair,proto3" json:"entryOutpointPair,omitempty"`
|
||||
}
|
||||
|
||||
func (x *ProtoUTXO) Reset() {
|
||||
*x = ProtoUTXO{}
|
||||
if protoimpl.UnsafeEnabled {
|
||||
mi := &file_utxo_proto_msgTypes[0]
|
||||
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
||||
ms.StoreMessageInfo(mi)
|
||||
}
|
||||
}
|
||||
|
||||
func (x *ProtoUTXO) String() string {
|
||||
return protoimpl.X.MessageStringOf(x)
|
||||
}
|
||||
|
||||
func (*ProtoUTXO) ProtoMessage() {}
|
||||
|
||||
func (x *ProtoUTXO) ProtoReflect() protoreflect.Message {
|
||||
mi := &file_utxo_proto_msgTypes[0]
|
||||
if protoimpl.UnsafeEnabled && x != nil {
|
||||
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
||||
if ms.LoadMessageInfo() == nil {
|
||||
ms.StoreMessageInfo(mi)
|
||||
}
|
||||
return ms
|
||||
}
|
||||
return mi.MessageOf(x)
|
||||
}
|
||||
|
||||
// Deprecated: Use ProtoUTXO.ProtoReflect.Descriptor instead.
|
||||
func (*ProtoUTXO) Descriptor() ([]byte, []int) {
|
||||
return file_utxo_proto_rawDescGZIP(), []int{0}
|
||||
}
|
||||
|
||||
func (x *ProtoUTXO) GetEntryOutpointPair() []byte {
|
||||
if x != nil {
|
||||
return x.EntryOutpointPair
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
type ProtoUTXOSet struct {
|
||||
state protoimpl.MessageState
|
||||
sizeCache protoimpl.SizeCache
|
||||
unknownFields protoimpl.UnknownFields
|
||||
|
||||
Utxos []*ProtoUTXO `protobuf:"bytes,1,rep,name=utxos,proto3" json:"utxos,omitempty"`
|
||||
}
|
||||
|
||||
func (x *ProtoUTXOSet) Reset() {
|
||||
*x = ProtoUTXOSet{}
|
||||
if protoimpl.UnsafeEnabled {
|
||||
mi := &file_utxo_proto_msgTypes[1]
|
||||
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
||||
ms.StoreMessageInfo(mi)
|
||||
}
|
||||
}
|
||||
|
||||
func (x *ProtoUTXOSet) String() string {
|
||||
return protoimpl.X.MessageStringOf(x)
|
||||
}
|
||||
|
||||
func (*ProtoUTXOSet) ProtoMessage() {}
|
||||
|
||||
func (x *ProtoUTXOSet) ProtoReflect() protoreflect.Message {
|
||||
mi := &file_utxo_proto_msgTypes[1]
|
||||
if protoimpl.UnsafeEnabled && x != nil {
|
||||
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
||||
if ms.LoadMessageInfo() == nil {
|
||||
ms.StoreMessageInfo(mi)
|
||||
}
|
||||
return ms
|
||||
}
|
||||
return mi.MessageOf(x)
|
||||
}
|
||||
|
||||
// Deprecated: Use ProtoUTXOSet.ProtoReflect.Descriptor instead.
|
||||
func (*ProtoUTXOSet) Descriptor() ([]byte, []int) {
|
||||
return file_utxo_proto_rawDescGZIP(), []int{1}
|
||||
}
|
||||
|
||||
func (x *ProtoUTXOSet) GetUtxos() []*ProtoUTXO {
|
||||
if x != nil {
|
||||
return x.Utxos
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
var File_utxo_proto protoreflect.FileDescriptor
|
||||
|
||||
var file_utxo_proto_rawDesc = []byte{
|
||||
0x0a, 0x0a, 0x75, 0x74, 0x78, 0x6f, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x12, 0x11, 0x75, 0x74,
|
||||
0x78, 0x6f, 0x73, 0x65, 0x72, 0x69, 0x61, 0x6c, 0x69, 0x7a, 0x61, 0x74, 0x69, 0x6f, 0x6e, 0x22,
|
||||
0x39, 0x0a, 0x09, 0x50, 0x72, 0x6f, 0x74, 0x6f, 0x55, 0x54, 0x58, 0x4f, 0x12, 0x2c, 0x0a, 0x11,
|
||||
0x65, 0x6e, 0x74, 0x72, 0x79, 0x4f, 0x75, 0x74, 0x70, 0x6f, 0x69, 0x6e, 0x74, 0x50, 0x61, 0x69,
|
||||
0x72, 0x18, 0x01, 0x20, 0x01, 0x28, 0x0c, 0x52, 0x11, 0x65, 0x6e, 0x74, 0x72, 0x79, 0x4f, 0x75,
|
||||
0x74, 0x70, 0x6f, 0x69, 0x6e, 0x74, 0x50, 0x61, 0x69, 0x72, 0x22, 0x42, 0x0a, 0x0c, 0x50, 0x72,
|
||||
0x6f, 0x74, 0x6f, 0x55, 0x54, 0x58, 0x4f, 0x53, 0x65, 0x74, 0x12, 0x32, 0x0a, 0x05, 0x75, 0x74,
|
||||
0x78, 0x6f, 0x73, 0x18, 0x01, 0x20, 0x03, 0x28, 0x0b, 0x32, 0x1c, 0x2e, 0x75, 0x74, 0x78, 0x6f,
|
||||
0x73, 0x65, 0x72, 0x69, 0x61, 0x6c, 0x69, 0x7a, 0x61, 0x74, 0x69, 0x6f, 0x6e, 0x2e, 0x50, 0x72,
|
||||
0x6f, 0x74, 0x6f, 0x55, 0x54, 0x58, 0x4f, 0x52, 0x05, 0x75, 0x74, 0x78, 0x6f, 0x73, 0x42, 0x45,
|
||||
0x5a, 0x43, 0x67, 0x69, 0x74, 0x68, 0x75, 0x62, 0x2e, 0x63, 0x6f, 0x6d, 0x2f, 0x6b, 0x61, 0x73,
|
||||
0x70, 0x61, 0x6e, 0x65, 0x74, 0x2f, 0x6b, 0x61, 0x73, 0x70, 0x61, 0x64, 0x2f, 0x64, 0x6f, 0x6d,
|
||||
0x61, 0x69, 0x6e, 0x2f, 0x63, 0x6f, 0x6e, 0x73, 0x65, 0x6e, 0x73, 0x75, 0x73, 0x2f, 0x75, 0x74,
|
||||
0x69, 0x6c, 0x73, 0x2f, 0x75, 0x74, 0x78, 0x6f, 0x73, 0x65, 0x72, 0x69, 0x61, 0x6c, 0x69, 0x7a,
|
||||
0x61, 0x74, 0x69, 0x6f, 0x6e, 0x62, 0x06, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x33,
|
||||
}
|
||||
|
||||
var (
|
||||
file_utxo_proto_rawDescOnce sync.Once
|
||||
file_utxo_proto_rawDescData = file_utxo_proto_rawDesc
|
||||
)
|
||||
|
||||
func file_utxo_proto_rawDescGZIP() []byte {
|
||||
file_utxo_proto_rawDescOnce.Do(func() {
|
||||
file_utxo_proto_rawDescData = protoimpl.X.CompressGZIP(file_utxo_proto_rawDescData)
|
||||
})
|
||||
return file_utxo_proto_rawDescData
|
||||
}
|
||||
|
||||
var file_utxo_proto_msgTypes = make([]protoimpl.MessageInfo, 2)
|
||||
var file_utxo_proto_goTypes = []interface{}{
|
||||
(*ProtoUTXO)(nil), // 0: utxoserialization.ProtoUTXO
|
||||
(*ProtoUTXOSet)(nil), // 1: utxoserialization.ProtoUTXOSet
|
||||
}
|
||||
var file_utxo_proto_depIdxs = []int32{
|
||||
0, // 0: utxoserialization.ProtoUTXOSet.utxos:type_name -> utxoserialization.ProtoUTXO
|
||||
1, // [1:1] is the sub-list for method output_type
|
||||
1, // [1:1] is the sub-list for method input_type
|
||||
1, // [1:1] is the sub-list for extension type_name
|
||||
1, // [1:1] is the sub-list for extension extendee
|
||||
0, // [0:1] is the sub-list for field type_name
|
||||
}
|
||||
|
||||
func init() { file_utxo_proto_init() }
|
||||
func file_utxo_proto_init() {
|
||||
if File_utxo_proto != nil {
|
||||
return
|
||||
}
|
||||
if !protoimpl.UnsafeEnabled {
|
||||
file_utxo_proto_msgTypes[0].Exporter = func(v interface{}, i int) interface{} {
|
||||
switch v := v.(*ProtoUTXO); i {
|
||||
case 0:
|
||||
return &v.state
|
||||
case 1:
|
||||
return &v.sizeCache
|
||||
case 2:
|
||||
return &v.unknownFields
|
||||
default:
|
||||
return nil
|
||||
}
|
||||
}
|
||||
file_utxo_proto_msgTypes[1].Exporter = func(v interface{}, i int) interface{} {
|
||||
switch v := v.(*ProtoUTXOSet); i {
|
||||
case 0:
|
||||
return &v.state
|
||||
case 1:
|
||||
return &v.sizeCache
|
||||
case 2:
|
||||
return &v.unknownFields
|
||||
default:
|
||||
return nil
|
||||
}
|
||||
}
|
||||
}
|
||||
type x struct{}
|
||||
out := protoimpl.TypeBuilder{
|
||||
File: protoimpl.DescBuilder{
|
||||
GoPackagePath: reflect.TypeOf(x{}).PkgPath(),
|
||||
RawDescriptor: file_utxo_proto_rawDesc,
|
||||
NumEnums: 0,
|
||||
NumMessages: 2,
|
||||
NumExtensions: 0,
|
||||
NumServices: 0,
|
||||
},
|
||||
GoTypes: file_utxo_proto_goTypes,
|
||||
DependencyIndexes: file_utxo_proto_depIdxs,
|
||||
MessageInfos: file_utxo_proto_msgTypes,
|
||||
}.Build()
|
||||
File_utxo_proto = out.File
|
||||
file_utxo_proto_rawDesc = nil
|
||||
file_utxo_proto_goTypes = nil
|
||||
file_utxo_proto_depIdxs = nil
|
||||
}
|
@ -1,12 +0,0 @@
|
||||
syntax = "proto3";
|
||||
package utxoserialization;
|
||||
|
||||
option go_package = "github.com/kaspanet/kaspad/domain/consensus/utils/utxoserialization";
|
||||
|
||||
message ProtoUTXO {
|
||||
bytes entryOutpointPair = 1;
|
||||
}
|
||||
|
||||
message ProtoUTXOSet {
|
||||
repeated ProtoUTXO utxos = 1;
|
||||
}
|
File diff suppressed because it is too large
Load Diff
@ -28,17 +28,17 @@ message KaspadMessage {
|
||||
VersionMessage version = 20;
|
||||
TransactionNotFoundMessage transactionNotFound = 21;
|
||||
RejectMessage reject = 22;
|
||||
RequestIBDRootUTXOSetAndBlockMessage requestIBDRootUTXOSetAndBlock = 24;
|
||||
IbdRootUtxoSetChunkMessage ibdRootUtxoSetChunk = 25;
|
||||
RequestPruningPointUTXOSetAndBlockMessage requestPruningPointUTXOSetAndBlock = 24;
|
||||
PruningPointUtxoSetChunkMessage pruningPointUtxoSetChunk = 25;
|
||||
RequestIBDBlocksMessage requestIBDBlocks = 26;
|
||||
IBDRootNotFoundMessage ibdRootNotFound = 27;
|
||||
RequestIBDRootHashMessage requestIBDRootHash = 28;
|
||||
IBDRootHashMessage ibdRootHash = 29;
|
||||
UnexpectedPruningPointMessage unexpectedPruningPoint = 27;
|
||||
RequestPruningPointHashMessage requestPruningPointHash = 28;
|
||||
PruningPointHashMessage pruningPointHash = 29;
|
||||
IbdBlockLocatorMessage ibdBlockLocator = 30;
|
||||
IbdBlockLocatorHighestHashMessage ibdBlockLocatorHighestHash = 31;
|
||||
BlockHeadersMessage blockHeaders = 32;
|
||||
RequestNextIbdRootUtxoSetChunkMessage requestNextIbdRootUtxoSetChunk = 33;
|
||||
DoneIbdRootUtxoSetChunksMessage doneIbdRootUtxoSetChunks = 34;
|
||||
RequestNextPruningPointUtxoSetChunkMessage requestNextPruningPointUtxoSetChunk = 33;
|
||||
DonePruningPointUtxoSetChunksMessage donePruningPointUtxoSetChunks = 34;
|
||||
|
||||
GetCurrentNetworkRequestMessage getCurrentNetworkRequest = 1001;
|
||||
GetCurrentNetworkResponseMessage getCurrentNetworkResponse = 1002;
|
||||
|
@ -1594,16 +1594,16 @@ func (x *RejectMessage) GetReason() string {
|
||||
return ""
|
||||
}
|
||||
|
||||
type RequestIBDRootUTXOSetAndBlockMessage struct {
|
||||
type RequestPruningPointUTXOSetAndBlockMessage struct {
|
||||
state protoimpl.MessageState
|
||||
sizeCache protoimpl.SizeCache
|
||||
unknownFields protoimpl.UnknownFields
|
||||
|
||||
IbdRoot *Hash `protobuf:"bytes,1,opt,name=ibdRoot,proto3" json:"ibdRoot,omitempty"`
|
||||
PruningPointHash *Hash `protobuf:"bytes,1,opt,name=pruningPointHash,proto3" json:"pruningPointHash,omitempty"`
|
||||
}
|
||||
|
||||
func (x *RequestIBDRootUTXOSetAndBlockMessage) Reset() {
|
||||
*x = RequestIBDRootUTXOSetAndBlockMessage{}
|
||||
func (x *RequestPruningPointUTXOSetAndBlockMessage) Reset() {
|
||||
*x = RequestPruningPointUTXOSetAndBlockMessage{}
|
||||
if protoimpl.UnsafeEnabled {
|
||||
mi := &file_p2p_proto_msgTypes[28]
|
||||
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
||||
@ -1611,13 +1611,13 @@ func (x *RequestIBDRootUTXOSetAndBlockMessage) Reset() {
|
||||
}
|
||||
}
|
||||
|
||||
func (x *RequestIBDRootUTXOSetAndBlockMessage) String() string {
|
||||
func (x *RequestPruningPointUTXOSetAndBlockMessage) String() string {
|
||||
return protoimpl.X.MessageStringOf(x)
|
||||
}
|
||||
|
||||
func (*RequestIBDRootUTXOSetAndBlockMessage) ProtoMessage() {}
|
||||
func (*RequestPruningPointUTXOSetAndBlockMessage) ProtoMessage() {}
|
||||
|
||||
func (x *RequestIBDRootUTXOSetAndBlockMessage) ProtoReflect() protoreflect.Message {
|
||||
func (x *RequestPruningPointUTXOSetAndBlockMessage) ProtoReflect() protoreflect.Message {
|
||||
mi := &file_p2p_proto_msgTypes[28]
|
||||
if protoimpl.UnsafeEnabled && x != nil {
|
||||
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
||||
@ -1629,28 +1629,28 @@ func (x *RequestIBDRootUTXOSetAndBlockMessage) ProtoReflect() protoreflect.Messa
|
||||
return mi.MessageOf(x)
|
||||
}
|
||||
|
||||
// Deprecated: Use RequestIBDRootUTXOSetAndBlockMessage.ProtoReflect.Descriptor instead.
|
||||
func (*RequestIBDRootUTXOSetAndBlockMessage) Descriptor() ([]byte, []int) {
|
||||
// Deprecated: Use RequestPruningPointUTXOSetAndBlockMessage.ProtoReflect.Descriptor instead.
|
||||
func (*RequestPruningPointUTXOSetAndBlockMessage) Descriptor() ([]byte, []int) {
|
||||
return file_p2p_proto_rawDescGZIP(), []int{28}
|
||||
}
|
||||
|
||||
func (x *RequestIBDRootUTXOSetAndBlockMessage) GetIbdRoot() *Hash {
|
||||
func (x *RequestPruningPointUTXOSetAndBlockMessage) GetPruningPointHash() *Hash {
|
||||
if x != nil {
|
||||
return x.IbdRoot
|
||||
return x.PruningPointHash
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
type IbdRootUtxoSetChunkMessage struct {
|
||||
type PruningPointUtxoSetChunkMessage struct {
|
||||
state protoimpl.MessageState
|
||||
sizeCache protoimpl.SizeCache
|
||||
unknownFields protoimpl.UnknownFields
|
||||
|
||||
Chunk []byte `protobuf:"bytes,1,opt,name=chunk,proto3" json:"chunk,omitempty"`
|
||||
OutpointAndUtxoEntryPairs []*OutpointAndUtxoEntryPair `protobuf:"bytes,1,rep,name=outpointAndUtxoEntryPairs,proto3" json:"outpointAndUtxoEntryPairs,omitempty"`
|
||||
}
|
||||
|
||||
func (x *IbdRootUtxoSetChunkMessage) Reset() {
|
||||
*x = IbdRootUtxoSetChunkMessage{}
|
||||
func (x *PruningPointUtxoSetChunkMessage) Reset() {
|
||||
*x = PruningPointUtxoSetChunkMessage{}
|
||||
if protoimpl.UnsafeEnabled {
|
||||
mi := &file_p2p_proto_msgTypes[29]
|
||||
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
||||
@ -1658,13 +1658,13 @@ func (x *IbdRootUtxoSetChunkMessage) Reset() {
|
||||
}
|
||||
}
|
||||
|
||||
func (x *IbdRootUtxoSetChunkMessage) String() string {
|
||||
func (x *PruningPointUtxoSetChunkMessage) String() string {
|
||||
return protoimpl.X.MessageStringOf(x)
|
||||
}
|
||||
|
||||
func (*IbdRootUtxoSetChunkMessage) ProtoMessage() {}
|
||||
func (*PruningPointUtxoSetChunkMessage) ProtoMessage() {}
|
||||
|
||||
func (x *IbdRootUtxoSetChunkMessage) ProtoReflect() protoreflect.Message {
|
||||
func (x *PruningPointUtxoSetChunkMessage) ProtoReflect() protoreflect.Message {
|
||||
mi := &file_p2p_proto_msgTypes[29]
|
||||
if protoimpl.UnsafeEnabled && x != nil {
|
||||
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
||||
@ -1676,26 +1676,29 @@ func (x *IbdRootUtxoSetChunkMessage) ProtoReflect() protoreflect.Message {
|
||||
return mi.MessageOf(x)
|
||||
}
|
||||
|
||||
// Deprecated: Use IbdRootUtxoSetChunkMessage.ProtoReflect.Descriptor instead.
|
||||
func (*IbdRootUtxoSetChunkMessage) Descriptor() ([]byte, []int) {
|
||||
// Deprecated: Use PruningPointUtxoSetChunkMessage.ProtoReflect.Descriptor instead.
|
||||
func (*PruningPointUtxoSetChunkMessage) Descriptor() ([]byte, []int) {
|
||||
return file_p2p_proto_rawDescGZIP(), []int{29}
|
||||
}
|
||||
|
||||
func (x *IbdRootUtxoSetChunkMessage) GetChunk() []byte {
|
||||
func (x *PruningPointUtxoSetChunkMessage) GetOutpointAndUtxoEntryPairs() []*OutpointAndUtxoEntryPair {
|
||||
if x != nil {
|
||||
return x.Chunk
|
||||
return x.OutpointAndUtxoEntryPairs
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
type RequestNextIbdRootUtxoSetChunkMessage struct {
|
||||
type OutpointAndUtxoEntryPair struct {
|
||||
state protoimpl.MessageState
|
||||
sizeCache protoimpl.SizeCache
|
||||
unknownFields protoimpl.UnknownFields
|
||||
|
||||
Outpoint *Outpoint `protobuf:"bytes,1,opt,name=outpoint,proto3" json:"outpoint,omitempty"`
|
||||
UtxoEntry *UtxoEntry `protobuf:"bytes,2,opt,name=utxoEntry,proto3" json:"utxoEntry,omitempty"`
|
||||
}
|
||||
|
||||
func (x *RequestNextIbdRootUtxoSetChunkMessage) Reset() {
|
||||
*x = RequestNextIbdRootUtxoSetChunkMessage{}
|
||||
func (x *OutpointAndUtxoEntryPair) Reset() {
|
||||
*x = OutpointAndUtxoEntryPair{}
|
||||
if protoimpl.UnsafeEnabled {
|
||||
mi := &file_p2p_proto_msgTypes[30]
|
||||
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
||||
@ -1703,13 +1706,13 @@ func (x *RequestNextIbdRootUtxoSetChunkMessage) Reset() {
|
||||
}
|
||||
}
|
||||
|
||||
func (x *RequestNextIbdRootUtxoSetChunkMessage) String() string {
|
||||
func (x *OutpointAndUtxoEntryPair) String() string {
|
||||
return protoimpl.X.MessageStringOf(x)
|
||||
}
|
||||
|
||||
func (*RequestNextIbdRootUtxoSetChunkMessage) ProtoMessage() {}
|
||||
func (*OutpointAndUtxoEntryPair) ProtoMessage() {}
|
||||
|
||||
func (x *RequestNextIbdRootUtxoSetChunkMessage) ProtoReflect() protoreflect.Message {
|
||||
func (x *OutpointAndUtxoEntryPair) ProtoReflect() protoreflect.Message {
|
||||
mi := &file_p2p_proto_msgTypes[30]
|
||||
if protoimpl.UnsafeEnabled && x != nil {
|
||||
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
||||
@ -1721,19 +1724,38 @@ func (x *RequestNextIbdRootUtxoSetChunkMessage) ProtoReflect() protoreflect.Mess
|
||||
return mi.MessageOf(x)
|
||||
}
|
||||
|
||||
// Deprecated: Use RequestNextIbdRootUtxoSetChunkMessage.ProtoReflect.Descriptor instead.
|
||||
func (*RequestNextIbdRootUtxoSetChunkMessage) Descriptor() ([]byte, []int) {
|
||||
// Deprecated: Use OutpointAndUtxoEntryPair.ProtoReflect.Descriptor instead.
|
||||
func (*OutpointAndUtxoEntryPair) Descriptor() ([]byte, []int) {
|
||||
return file_p2p_proto_rawDescGZIP(), []int{30}
|
||||
}
|
||||
|
||||
type DoneIbdRootUtxoSetChunksMessage struct {
|
||||
func (x *OutpointAndUtxoEntryPair) GetOutpoint() *Outpoint {
|
||||
if x != nil {
|
||||
return x.Outpoint
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
func (x *OutpointAndUtxoEntryPair) GetUtxoEntry() *UtxoEntry {
|
||||
if x != nil {
|
||||
return x.UtxoEntry
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
type UtxoEntry struct {
|
||||
state protoimpl.MessageState
|
||||
sizeCache protoimpl.SizeCache
|
||||
unknownFields protoimpl.UnknownFields
|
||||
|
||||
Amount uint64 `protobuf:"varint,1,opt,name=amount,proto3" json:"amount,omitempty"`
|
||||
ScriptPublicKey *ScriptPublicKey `protobuf:"bytes,2,opt,name=scriptPublicKey,proto3" json:"scriptPublicKey,omitempty"`
|
||||
BlockBlueScore uint64 `protobuf:"varint,3,opt,name=blockBlueScore,proto3" json:"blockBlueScore,omitempty"`
|
||||
IsCoinbase bool `protobuf:"varint,4,opt,name=isCoinbase,proto3" json:"isCoinbase,omitempty"`
|
||||
}
|
||||
|
||||
func (x *DoneIbdRootUtxoSetChunksMessage) Reset() {
|
||||
*x = DoneIbdRootUtxoSetChunksMessage{}
|
||||
func (x *UtxoEntry) Reset() {
|
||||
*x = UtxoEntry{}
|
||||
if protoimpl.UnsafeEnabled {
|
||||
mi := &file_p2p_proto_msgTypes[31]
|
||||
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
||||
@ -1741,13 +1763,13 @@ func (x *DoneIbdRootUtxoSetChunksMessage) Reset() {
|
||||
}
|
||||
}
|
||||
|
||||
func (x *DoneIbdRootUtxoSetChunksMessage) String() string {
|
||||
func (x *UtxoEntry) String() string {
|
||||
return protoimpl.X.MessageStringOf(x)
|
||||
}
|
||||
|
||||
func (*DoneIbdRootUtxoSetChunksMessage) ProtoMessage() {}
|
||||
func (*UtxoEntry) ProtoMessage() {}
|
||||
|
||||
func (x *DoneIbdRootUtxoSetChunksMessage) ProtoReflect() protoreflect.Message {
|
||||
func (x *UtxoEntry) ProtoReflect() protoreflect.Message {
|
||||
mi := &file_p2p_proto_msgTypes[31]
|
||||
if protoimpl.UnsafeEnabled && x != nil {
|
||||
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
||||
@ -1759,11 +1781,115 @@ func (x *DoneIbdRootUtxoSetChunksMessage) ProtoReflect() protoreflect.Message {
|
||||
return mi.MessageOf(x)
|
||||
}
|
||||
|
||||
// Deprecated: Use DoneIbdRootUtxoSetChunksMessage.ProtoReflect.Descriptor instead.
|
||||
func (*DoneIbdRootUtxoSetChunksMessage) Descriptor() ([]byte, []int) {
|
||||
// Deprecated: Use UtxoEntry.ProtoReflect.Descriptor instead.
|
||||
func (*UtxoEntry) Descriptor() ([]byte, []int) {
|
||||
return file_p2p_proto_rawDescGZIP(), []int{31}
|
||||
}
|
||||
|
||||
func (x *UtxoEntry) GetAmount() uint64 {
|
||||
if x != nil {
|
||||
return x.Amount
|
||||
}
|
||||
return 0
|
||||
}
|
||||
|
||||
func (x *UtxoEntry) GetScriptPublicKey() *ScriptPublicKey {
|
||||
if x != nil {
|
||||
return x.ScriptPublicKey
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
func (x *UtxoEntry) GetBlockBlueScore() uint64 {
|
||||
if x != nil {
|
||||
return x.BlockBlueScore
|
||||
}
|
||||
return 0
|
||||
}
|
||||
|
||||
func (x *UtxoEntry) GetIsCoinbase() bool {
|
||||
if x != nil {
|
||||
return x.IsCoinbase
|
||||
}
|
||||
return false
|
||||
}
|
||||
|
||||
type RequestNextPruningPointUtxoSetChunkMessage struct {
|
||||
state protoimpl.MessageState
|
||||
sizeCache protoimpl.SizeCache
|
||||
unknownFields protoimpl.UnknownFields
|
||||
}
|
||||
|
||||
func (x *RequestNextPruningPointUtxoSetChunkMessage) Reset() {
|
||||
*x = RequestNextPruningPointUtxoSetChunkMessage{}
|
||||
if protoimpl.UnsafeEnabled {
|
||||
mi := &file_p2p_proto_msgTypes[32]
|
||||
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
||||
ms.StoreMessageInfo(mi)
|
||||
}
|
||||
}
|
||||
|
||||
func (x *RequestNextPruningPointUtxoSetChunkMessage) String() string {
|
||||
return protoimpl.X.MessageStringOf(x)
|
||||
}
|
||||
|
||||
func (*RequestNextPruningPointUtxoSetChunkMessage) ProtoMessage() {}
|
||||
|
||||
func (x *RequestNextPruningPointUtxoSetChunkMessage) ProtoReflect() protoreflect.Message {
|
||||
mi := &file_p2p_proto_msgTypes[32]
|
||||
if protoimpl.UnsafeEnabled && x != nil {
|
||||
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
||||
if ms.LoadMessageInfo() == nil {
|
||||
ms.StoreMessageInfo(mi)
|
||||
}
|
||||
return ms
|
||||
}
|
||||
return mi.MessageOf(x)
|
||||
}
|
||||
|
||||
// Deprecated: Use RequestNextPruningPointUtxoSetChunkMessage.ProtoReflect.Descriptor instead.
|
||||
func (*RequestNextPruningPointUtxoSetChunkMessage) Descriptor() ([]byte, []int) {
|
||||
return file_p2p_proto_rawDescGZIP(), []int{32}
|
||||
}
|
||||
|
||||
type DonePruningPointUtxoSetChunksMessage struct {
|
||||
state protoimpl.MessageState
|
||||
sizeCache protoimpl.SizeCache
|
||||
unknownFields protoimpl.UnknownFields
|
||||
}
|
||||
|
||||
func (x *DonePruningPointUtxoSetChunksMessage) Reset() {
|
||||
*x = DonePruningPointUtxoSetChunksMessage{}
|
||||
if protoimpl.UnsafeEnabled {
|
||||
mi := &file_p2p_proto_msgTypes[33]
|
||||
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
||||
ms.StoreMessageInfo(mi)
|
||||
}
|
||||
}
|
||||
|
||||
func (x *DonePruningPointUtxoSetChunksMessage) String() string {
|
||||
return protoimpl.X.MessageStringOf(x)
|
||||
}
|
||||
|
||||
func (*DonePruningPointUtxoSetChunksMessage) ProtoMessage() {}
|
||||
|
||||
func (x *DonePruningPointUtxoSetChunksMessage) ProtoReflect() protoreflect.Message {
|
||||
mi := &file_p2p_proto_msgTypes[33]
|
||||
if protoimpl.UnsafeEnabled && x != nil {
|
||||
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
||||
if ms.LoadMessageInfo() == nil {
|
||||
ms.StoreMessageInfo(mi)
|
||||
}
|
||||
return ms
|
||||
}
|
||||
return mi.MessageOf(x)
|
||||
}
|
||||
|
||||
// Deprecated: Use DonePruningPointUtxoSetChunksMessage.ProtoReflect.Descriptor instead.
|
||||
func (*DonePruningPointUtxoSetChunksMessage) Descriptor() ([]byte, []int) {
|
||||
return file_p2p_proto_rawDescGZIP(), []int{33}
|
||||
}
|
||||
|
||||
type RequestIBDBlocksMessage struct {
|
||||
state protoimpl.MessageState
|
||||
sizeCache protoimpl.SizeCache
|
||||
@ -1775,7 +1901,7 @@ type RequestIBDBlocksMessage struct {
|
||||
func (x *RequestIBDBlocksMessage) Reset() {
|
||||
*x = RequestIBDBlocksMessage{}
|
||||
if protoimpl.UnsafeEnabled {
|
||||
mi := &file_p2p_proto_msgTypes[32]
|
||||
mi := &file_p2p_proto_msgTypes[34]
|
||||
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
||||
ms.StoreMessageInfo(mi)
|
||||
}
|
||||
@ -1788,7 +1914,7 @@ func (x *RequestIBDBlocksMessage) String() string {
|
||||
func (*RequestIBDBlocksMessage) ProtoMessage() {}
|
||||
|
||||
func (x *RequestIBDBlocksMessage) ProtoReflect() protoreflect.Message {
|
||||
mi := &file_p2p_proto_msgTypes[32]
|
||||
mi := &file_p2p_proto_msgTypes[34]
|
||||
if protoimpl.UnsafeEnabled && x != nil {
|
||||
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
||||
if ms.LoadMessageInfo() == nil {
|
||||
@ -1801,7 +1927,7 @@ func (x *RequestIBDBlocksMessage) ProtoReflect() protoreflect.Message {
|
||||
|
||||
// Deprecated: Use RequestIBDBlocksMessage.ProtoReflect.Descriptor instead.
|
||||
func (*RequestIBDBlocksMessage) Descriptor() ([]byte, []int) {
|
||||
return file_p2p_proto_rawDescGZIP(), []int{32}
|
||||
return file_p2p_proto_rawDescGZIP(), []int{34}
|
||||
}
|
||||
|
||||
func (x *RequestIBDBlocksMessage) GetHashes() []*Hash {
|
||||
@ -1811,29 +1937,29 @@ func (x *RequestIBDBlocksMessage) GetHashes() []*Hash {
|
||||
return nil
|
||||
}
|
||||
|
||||
type IBDRootNotFoundMessage struct {
|
||||
type UnexpectedPruningPointMessage struct {
|
||||
state protoimpl.MessageState
|
||||
sizeCache protoimpl.SizeCache
|
||||
unknownFields protoimpl.UnknownFields
|
||||
}
|
||||
|
||||
func (x *IBDRootNotFoundMessage) Reset() {
|
||||
*x = IBDRootNotFoundMessage{}
|
||||
func (x *UnexpectedPruningPointMessage) Reset() {
|
||||
*x = UnexpectedPruningPointMessage{}
|
||||
if protoimpl.UnsafeEnabled {
|
||||
mi := &file_p2p_proto_msgTypes[33]
|
||||
mi := &file_p2p_proto_msgTypes[35]
|
||||
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
||||
ms.StoreMessageInfo(mi)
|
||||
}
|
||||
}
|
||||
|
||||
func (x *IBDRootNotFoundMessage) String() string {
|
||||
func (x *UnexpectedPruningPointMessage) String() string {
|
||||
return protoimpl.X.MessageStringOf(x)
|
||||
}
|
||||
|
||||
func (*IBDRootNotFoundMessage) ProtoMessage() {}
|
||||
func (*UnexpectedPruningPointMessage) ProtoMessage() {}
|
||||
|
||||
func (x *IBDRootNotFoundMessage) ProtoReflect() protoreflect.Message {
|
||||
mi := &file_p2p_proto_msgTypes[33]
|
||||
func (x *UnexpectedPruningPointMessage) ProtoReflect() protoreflect.Message {
|
||||
mi := &file_p2p_proto_msgTypes[35]
|
||||
if protoimpl.UnsafeEnabled && x != nil {
|
||||
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
||||
if ms.LoadMessageInfo() == nil {
|
||||
@ -1844,34 +1970,34 @@ func (x *IBDRootNotFoundMessage) ProtoReflect() protoreflect.Message {
|
||||
return mi.MessageOf(x)
|
||||
}
|
||||
|
||||
// Deprecated: Use IBDRootNotFoundMessage.ProtoReflect.Descriptor instead.
|
||||
func (*IBDRootNotFoundMessage) Descriptor() ([]byte, []int) {
|
||||
return file_p2p_proto_rawDescGZIP(), []int{33}
|
||||
// Deprecated: Use UnexpectedPruningPointMessage.ProtoReflect.Descriptor instead.
|
||||
func (*UnexpectedPruningPointMessage) Descriptor() ([]byte, []int) {
|
||||
return file_p2p_proto_rawDescGZIP(), []int{35}
|
||||
}
|
||||
|
||||
type RequestIBDRootHashMessage struct {
|
||||
type RequestPruningPointHashMessage struct {
|
||||
state protoimpl.MessageState
|
||||
sizeCache protoimpl.SizeCache
|
||||
unknownFields protoimpl.UnknownFields
|
||||
}
|
||||
|
||||
func (x *RequestIBDRootHashMessage) Reset() {
|
||||
*x = RequestIBDRootHashMessage{}
|
||||
func (x *RequestPruningPointHashMessage) Reset() {
|
||||
*x = RequestPruningPointHashMessage{}
|
||||
if protoimpl.UnsafeEnabled {
|
||||
mi := &file_p2p_proto_msgTypes[34]
|
||||
mi := &file_p2p_proto_msgTypes[36]
|
||||
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
||||
ms.StoreMessageInfo(mi)
|
||||
}
|
||||
}
|
||||
|
||||
func (x *RequestIBDRootHashMessage) String() string {
|
||||
func (x *RequestPruningPointHashMessage) String() string {
|
||||
return protoimpl.X.MessageStringOf(x)
|
||||
}
|
||||
|
||||
func (*RequestIBDRootHashMessage) ProtoMessage() {}
|
||||
func (*RequestPruningPointHashMessage) ProtoMessage() {}
|
||||
|
||||
func (x *RequestIBDRootHashMessage) ProtoReflect() protoreflect.Message {
|
||||
mi := &file_p2p_proto_msgTypes[34]
|
||||
func (x *RequestPruningPointHashMessage) ProtoReflect() protoreflect.Message {
|
||||
mi := &file_p2p_proto_msgTypes[36]
|
||||
if protoimpl.UnsafeEnabled && x != nil {
|
||||
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
||||
if ms.LoadMessageInfo() == nil {
|
||||
@ -1882,12 +2008,12 @@ func (x *RequestIBDRootHashMessage) ProtoReflect() protoreflect.Message {
|
||||
return mi.MessageOf(x)
|
||||
}
|
||||
|
||||
// Deprecated: Use RequestIBDRootHashMessage.ProtoReflect.Descriptor instead.
|
||||
func (*RequestIBDRootHashMessage) Descriptor() ([]byte, []int) {
|
||||
return file_p2p_proto_rawDescGZIP(), []int{34}
|
||||
// Deprecated: Use RequestPruningPointHashMessage.ProtoReflect.Descriptor instead.
|
||||
func (*RequestPruningPointHashMessage) Descriptor() ([]byte, []int) {
|
||||
return file_p2p_proto_rawDescGZIP(), []int{36}
|
||||
}
|
||||
|
||||
type IBDRootHashMessage struct {
|
||||
type PruningPointHashMessage struct {
|
||||
state protoimpl.MessageState
|
||||
sizeCache protoimpl.SizeCache
|
||||
unknownFields protoimpl.UnknownFields
|
||||
@ -1895,23 +2021,23 @@ type IBDRootHashMessage struct {
|
||||
Hash *Hash `protobuf:"bytes,1,opt,name=hash,proto3" json:"hash,omitempty"`
|
||||
}
|
||||
|
||||
func (x *IBDRootHashMessage) Reset() {
|
||||
*x = IBDRootHashMessage{}
|
||||
func (x *PruningPointHashMessage) Reset() {
|
||||
*x = PruningPointHashMessage{}
|
||||
if protoimpl.UnsafeEnabled {
|
||||
mi := &file_p2p_proto_msgTypes[35]
|
||||
mi := &file_p2p_proto_msgTypes[37]
|
||||
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
||||
ms.StoreMessageInfo(mi)
|
||||
}
|
||||
}
|
||||
|
||||
func (x *IBDRootHashMessage) String() string {
|
||||
func (x *PruningPointHashMessage) String() string {
|
||||
return protoimpl.X.MessageStringOf(x)
|
||||
}
|
||||
|
||||
func (*IBDRootHashMessage) ProtoMessage() {}
|
||||
func (*PruningPointHashMessage) ProtoMessage() {}
|
||||
|
||||
func (x *IBDRootHashMessage) ProtoReflect() protoreflect.Message {
|
||||
mi := &file_p2p_proto_msgTypes[35]
|
||||
func (x *PruningPointHashMessage) ProtoReflect() protoreflect.Message {
|
||||
mi := &file_p2p_proto_msgTypes[37]
|
||||
if protoimpl.UnsafeEnabled && x != nil {
|
||||
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
||||
if ms.LoadMessageInfo() == nil {
|
||||
@ -1922,12 +2048,12 @@ func (x *IBDRootHashMessage) ProtoReflect() protoreflect.Message {
|
||||
return mi.MessageOf(x)
|
||||
}
|
||||
|
||||
// Deprecated: Use IBDRootHashMessage.ProtoReflect.Descriptor instead.
|
||||
func (*IBDRootHashMessage) Descriptor() ([]byte, []int) {
|
||||
return file_p2p_proto_rawDescGZIP(), []int{35}
|
||||
// Deprecated: Use PruningPointHashMessage.ProtoReflect.Descriptor instead.
|
||||
func (*PruningPointHashMessage) Descriptor() ([]byte, []int) {
|
||||
return file_p2p_proto_rawDescGZIP(), []int{37}
|
||||
}
|
||||
|
||||
func (x *IBDRootHashMessage) GetHash() *Hash {
|
||||
func (x *PruningPointHashMessage) GetHash() *Hash {
|
||||
if x != nil {
|
||||
return x.Hash
|
||||
}
|
||||
@ -1946,7 +2072,7 @@ type IbdBlockLocatorMessage struct {
|
||||
func (x *IbdBlockLocatorMessage) Reset() {
|
||||
*x = IbdBlockLocatorMessage{}
|
||||
if protoimpl.UnsafeEnabled {
|
||||
mi := &file_p2p_proto_msgTypes[36]
|
||||
mi := &file_p2p_proto_msgTypes[38]
|
||||
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
||||
ms.StoreMessageInfo(mi)
|
||||
}
|
||||
@ -1959,7 +2085,7 @@ func (x *IbdBlockLocatorMessage) String() string {
|
||||
func (*IbdBlockLocatorMessage) ProtoMessage() {}
|
||||
|
||||
func (x *IbdBlockLocatorMessage) ProtoReflect() protoreflect.Message {
|
||||
mi := &file_p2p_proto_msgTypes[36]
|
||||
mi := &file_p2p_proto_msgTypes[38]
|
||||
if protoimpl.UnsafeEnabled && x != nil {
|
||||
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
||||
if ms.LoadMessageInfo() == nil {
|
||||
@ -1972,7 +2098,7 @@ func (x *IbdBlockLocatorMessage) ProtoReflect() protoreflect.Message {
|
||||
|
||||
// Deprecated: Use IbdBlockLocatorMessage.ProtoReflect.Descriptor instead.
|
||||
func (*IbdBlockLocatorMessage) Descriptor() ([]byte, []int) {
|
||||
return file_p2p_proto_rawDescGZIP(), []int{36}
|
||||
return file_p2p_proto_rawDescGZIP(), []int{38}
|
||||
}
|
||||
|
||||
func (x *IbdBlockLocatorMessage) GetTargetHash() *Hash {
|
||||
@ -2000,7 +2126,7 @@ type IbdBlockLocatorHighestHashMessage struct {
|
||||
func (x *IbdBlockLocatorHighestHashMessage) Reset() {
|
||||
*x = IbdBlockLocatorHighestHashMessage{}
|
||||
if protoimpl.UnsafeEnabled {
|
||||
mi := &file_p2p_proto_msgTypes[37]
|
||||
mi := &file_p2p_proto_msgTypes[39]
|
||||
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
||||
ms.StoreMessageInfo(mi)
|
||||
}
|
||||
@ -2013,7 +2139,7 @@ func (x *IbdBlockLocatorHighestHashMessage) String() string {
|
||||
func (*IbdBlockLocatorHighestHashMessage) ProtoMessage() {}
|
||||
|
||||
func (x *IbdBlockLocatorHighestHashMessage) ProtoReflect() protoreflect.Message {
|
||||
mi := &file_p2p_proto_msgTypes[37]
|
||||
mi := &file_p2p_proto_msgTypes[39]
|
||||
if protoimpl.UnsafeEnabled && x != nil {
|
||||
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
||||
if ms.LoadMessageInfo() == nil {
|
||||
@ -2026,7 +2152,7 @@ func (x *IbdBlockLocatorHighestHashMessage) ProtoReflect() protoreflect.Message
|
||||
|
||||
// Deprecated: Use IbdBlockLocatorHighestHashMessage.ProtoReflect.Descriptor instead.
|
||||
func (*IbdBlockLocatorHighestHashMessage) Descriptor() ([]byte, []int) {
|
||||
return file_p2p_proto_rawDescGZIP(), []int{37}
|
||||
return file_p2p_proto_rawDescGZIP(), []int{39}
|
||||
}
|
||||
|
||||
func (x *IbdBlockLocatorHighestHashMessage) GetHighestHash() *Hash {
|
||||
@ -2047,7 +2173,7 @@ type BlockHeadersMessage struct {
|
||||
func (x *BlockHeadersMessage) Reset() {
|
||||
*x = BlockHeadersMessage{}
|
||||
if protoimpl.UnsafeEnabled {
|
||||
mi := &file_p2p_proto_msgTypes[38]
|
||||
mi := &file_p2p_proto_msgTypes[40]
|
||||
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
||||
ms.StoreMessageInfo(mi)
|
||||
}
|
||||
@ -2060,7 +2186,7 @@ func (x *BlockHeadersMessage) String() string {
|
||||
func (*BlockHeadersMessage) ProtoMessage() {}
|
||||
|
||||
func (x *BlockHeadersMessage) ProtoReflect() protoreflect.Message {
|
||||
mi := &file_p2p_proto_msgTypes[38]
|
||||
mi := &file_p2p_proto_msgTypes[40]
|
||||
if protoimpl.UnsafeEnabled && x != nil {
|
||||
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
||||
if ms.LoadMessageInfo() == nil {
|
||||
@ -2073,7 +2199,7 @@ func (x *BlockHeadersMessage) ProtoReflect() protoreflect.Message {
|
||||
|
||||
// Deprecated: Use BlockHeadersMessage.ProtoReflect.Descriptor instead.
|
||||
func (*BlockHeadersMessage) Descriptor() ([]byte, []int) {
|
||||
return file_p2p_proto_rawDescGZIP(), []int{38}
|
||||
return file_p2p_proto_rawDescGZIP(), []int{40}
|
||||
}
|
||||
|
||||
func (x *BlockHeadersMessage) GetBlockHeaders() []*BlockHeaderMessage {
|
||||
@ -2268,54 +2394,82 @@ var file_p2p_proto_rawDesc = []byte{
|
||||
0x18, 0x0a, 0x20, 0x01, 0x28, 0x09, 0x52, 0x07, 0x6e, 0x65, 0x74, 0x77, 0x6f, 0x72, 0x6b, 0x22,
|
||||
0x27, 0x0a, 0x0d, 0x52, 0x65, 0x6a, 0x65, 0x63, 0x74, 0x4d, 0x65, 0x73, 0x73, 0x61, 0x67, 0x65,
|
||||
0x12, 0x16, 0x0a, 0x06, 0x72, 0x65, 0x61, 0x73, 0x6f, 0x6e, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09,
|
||||
0x52, 0x06, 0x72, 0x65, 0x61, 0x73, 0x6f, 0x6e, 0x22, 0x51, 0x0a, 0x24, 0x52, 0x65, 0x71, 0x75,
|
||||
0x65, 0x73, 0x74, 0x49, 0x42, 0x44, 0x52, 0x6f, 0x6f, 0x74, 0x55, 0x54, 0x58, 0x4f, 0x53, 0x65,
|
||||
0x74, 0x41, 0x6e, 0x64, 0x42, 0x6c, 0x6f, 0x63, 0x6b, 0x4d, 0x65, 0x73, 0x73, 0x61, 0x67, 0x65,
|
||||
0x12, 0x29, 0x0a, 0x07, 0x69, 0x62, 0x64, 0x52, 0x6f, 0x6f, 0x74, 0x18, 0x01, 0x20, 0x01, 0x28,
|
||||
0x0b, 0x32, 0x0f, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x77, 0x69, 0x72, 0x65, 0x2e, 0x48, 0x61,
|
||||
0x73, 0x68, 0x52, 0x07, 0x69, 0x62, 0x64, 0x52, 0x6f, 0x6f, 0x74, 0x22, 0x32, 0x0a, 0x1a, 0x49,
|
||||
0x62, 0x64, 0x52, 0x6f, 0x6f, 0x74, 0x55, 0x74, 0x78, 0x6f, 0x53, 0x65, 0x74, 0x43, 0x68, 0x75,
|
||||
0x6e, 0x6b, 0x4d, 0x65, 0x73, 0x73, 0x61, 0x67, 0x65, 0x12, 0x14, 0x0a, 0x05, 0x63, 0x68, 0x75,
|
||||
0x6e, 0x6b, 0x18, 0x01, 0x20, 0x01, 0x28, 0x0c, 0x52, 0x05, 0x63, 0x68, 0x75, 0x6e, 0x6b, 0x22,
|
||||
0x27, 0x0a, 0x25, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x4e, 0x65, 0x78, 0x74, 0x49, 0x62,
|
||||
0x64, 0x52, 0x6f, 0x6f, 0x74, 0x55, 0x74, 0x78, 0x6f, 0x53, 0x65, 0x74, 0x43, 0x68, 0x75, 0x6e,
|
||||
0x6b, 0x4d, 0x65, 0x73, 0x73, 0x61, 0x67, 0x65, 0x22, 0x21, 0x0a, 0x1f, 0x44, 0x6f, 0x6e, 0x65,
|
||||
0x49, 0x62, 0x64, 0x52, 0x6f, 0x6f, 0x74, 0x55, 0x74, 0x78, 0x6f, 0x53, 0x65, 0x74, 0x43, 0x68,
|
||||
0x75, 0x6e, 0x6b, 0x73, 0x4d, 0x65, 0x73, 0x73, 0x61, 0x67, 0x65, 0x22, 0x42, 0x0a, 0x17, 0x52,
|
||||
0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x49, 0x42, 0x44, 0x42, 0x6c, 0x6f, 0x63, 0x6b, 0x73, 0x4d,
|
||||
0x65, 0x73, 0x73, 0x61, 0x67, 0x65, 0x12, 0x27, 0x0a, 0x06, 0x68, 0x61, 0x73, 0x68, 0x65, 0x73,
|
||||
0x18, 0x01, 0x20, 0x03, 0x28, 0x0b, 0x32, 0x0f, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x77, 0x69,
|
||||
0x72, 0x65, 0x2e, 0x48, 0x61, 0x73, 0x68, 0x52, 0x06, 0x68, 0x61, 0x73, 0x68, 0x65, 0x73, 0x22,
|
||||
0x18, 0x0a, 0x16, 0x49, 0x42, 0x44, 0x52, 0x6f, 0x6f, 0x74, 0x4e, 0x6f, 0x74, 0x46, 0x6f, 0x75,
|
||||
0x6e, 0x64, 0x4d, 0x65, 0x73, 0x73, 0x61, 0x67, 0x65, 0x22, 0x1b, 0x0a, 0x19, 0x52, 0x65, 0x71,
|
||||
0x75, 0x65, 0x73, 0x74, 0x49, 0x42, 0x44, 0x52, 0x6f, 0x6f, 0x74, 0x48, 0x61, 0x73, 0x68, 0x4d,
|
||||
0x65, 0x73, 0x73, 0x61, 0x67, 0x65, 0x22, 0x39, 0x0a, 0x12, 0x49, 0x42, 0x44, 0x52, 0x6f, 0x6f,
|
||||
0x74, 0x48, 0x61, 0x73, 0x68, 0x4d, 0x65, 0x73, 0x73, 0x61, 0x67, 0x65, 0x12, 0x23, 0x0a, 0x04,
|
||||
0x68, 0x61, 0x73, 0x68, 0x18, 0x01, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x0f, 0x2e, 0x70, 0x72, 0x6f,
|
||||
0x74, 0x6f, 0x77, 0x69, 0x72, 0x65, 0x2e, 0x48, 0x61, 0x73, 0x68, 0x52, 0x04, 0x68, 0x61, 0x73,
|
||||
0x68, 0x22, 0x8a, 0x01, 0x0a, 0x16, 0x49, 0x62, 0x64, 0x42, 0x6c, 0x6f, 0x63, 0x6b, 0x4c, 0x6f,
|
||||
0x63, 0x61, 0x74, 0x6f, 0x72, 0x4d, 0x65, 0x73, 0x73, 0x61, 0x67, 0x65, 0x12, 0x2f, 0x0a, 0x0a,
|
||||
0x74, 0x61, 0x72, 0x67, 0x65, 0x74, 0x48, 0x61, 0x73, 0x68, 0x18, 0x01, 0x20, 0x01, 0x28, 0x0b,
|
||||
0x32, 0x0f, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x77, 0x69, 0x72, 0x65, 0x2e, 0x48, 0x61, 0x73,
|
||||
0x68, 0x52, 0x0a, 0x74, 0x61, 0x72, 0x67, 0x65, 0x74, 0x48, 0x61, 0x73, 0x68, 0x12, 0x3f, 0x0a,
|
||||
0x12, 0x62, 0x6c, 0x6f, 0x63, 0x6b, 0x4c, 0x6f, 0x63, 0x61, 0x74, 0x6f, 0x72, 0x48, 0x61, 0x73,
|
||||
0x68, 0x65, 0x73, 0x18, 0x02, 0x20, 0x03, 0x28, 0x0b, 0x32, 0x0f, 0x2e, 0x70, 0x72, 0x6f, 0x74,
|
||||
0x6f, 0x77, 0x69, 0x72, 0x65, 0x2e, 0x48, 0x61, 0x73, 0x68, 0x52, 0x12, 0x62, 0x6c, 0x6f, 0x63,
|
||||
0x6b, 0x4c, 0x6f, 0x63, 0x61, 0x74, 0x6f, 0x72, 0x48, 0x61, 0x73, 0x68, 0x65, 0x73, 0x22, 0x56,
|
||||
0x0a, 0x21, 0x49, 0x62, 0x64, 0x42, 0x6c, 0x6f, 0x63, 0x6b, 0x4c, 0x6f, 0x63, 0x61, 0x74, 0x6f,
|
||||
0x72, 0x48, 0x69, 0x67, 0x68, 0x65, 0x73, 0x74, 0x48, 0x61, 0x73, 0x68, 0x4d, 0x65, 0x73, 0x73,
|
||||
0x61, 0x67, 0x65, 0x12, 0x31, 0x0a, 0x0b, 0x68, 0x69, 0x67, 0x68, 0x65, 0x73, 0x74, 0x48, 0x61,
|
||||
0x73, 0x68, 0x18, 0x01, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x0f, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f,
|
||||
0x77, 0x69, 0x72, 0x65, 0x2e, 0x48, 0x61, 0x73, 0x68, 0x52, 0x0b, 0x68, 0x69, 0x67, 0x68, 0x65,
|
||||
0x73, 0x74, 0x48, 0x61, 0x73, 0x68, 0x22, 0x58, 0x0a, 0x13, 0x42, 0x6c, 0x6f, 0x63, 0x6b, 0x48,
|
||||
0x65, 0x61, 0x64, 0x65, 0x72, 0x73, 0x4d, 0x65, 0x73, 0x73, 0x61, 0x67, 0x65, 0x12, 0x41, 0x0a,
|
||||
0x0c, 0x62, 0x6c, 0x6f, 0x63, 0x6b, 0x48, 0x65, 0x61, 0x64, 0x65, 0x72, 0x73, 0x18, 0x01, 0x20,
|
||||
0x03, 0x28, 0x0b, 0x32, 0x1d, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x77, 0x69, 0x72, 0x65, 0x2e,
|
||||
0x42, 0x6c, 0x6f, 0x63, 0x6b, 0x48, 0x65, 0x61, 0x64, 0x65, 0x72, 0x4d, 0x65, 0x73, 0x73, 0x61,
|
||||
0x67, 0x65, 0x52, 0x0c, 0x62, 0x6c, 0x6f, 0x63, 0x6b, 0x48, 0x65, 0x61, 0x64, 0x65, 0x72, 0x73,
|
||||
0x42, 0x26, 0x5a, 0x24, 0x67, 0x69, 0x74, 0x68, 0x75, 0x62, 0x2e, 0x63, 0x6f, 0x6d, 0x2f, 0x6b,
|
||||
0x61, 0x73, 0x70, 0x61, 0x6e, 0x65, 0x74, 0x2f, 0x6b, 0x61, 0x73, 0x70, 0x61, 0x64, 0x2f, 0x70,
|
||||
0x72, 0x6f, 0x74, 0x6f, 0x77, 0x69, 0x72, 0x65, 0x62, 0x06, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x33,
|
||||
0x52, 0x06, 0x72, 0x65, 0x61, 0x73, 0x6f, 0x6e, 0x22, 0x68, 0x0a, 0x29, 0x52, 0x65, 0x71, 0x75,
|
||||
0x65, 0x73, 0x74, 0x50, 0x72, 0x75, 0x6e, 0x69, 0x6e, 0x67, 0x50, 0x6f, 0x69, 0x6e, 0x74, 0x55,
|
||||
0x54, 0x58, 0x4f, 0x53, 0x65, 0x74, 0x41, 0x6e, 0x64, 0x42, 0x6c, 0x6f, 0x63, 0x6b, 0x4d, 0x65,
|
||||
0x73, 0x73, 0x61, 0x67, 0x65, 0x12, 0x3b, 0x0a, 0x10, 0x70, 0x72, 0x75, 0x6e, 0x69, 0x6e, 0x67,
|
||||
0x50, 0x6f, 0x69, 0x6e, 0x74, 0x48, 0x61, 0x73, 0x68, 0x18, 0x01, 0x20, 0x01, 0x28, 0x0b, 0x32,
|
||||
0x0f, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x77, 0x69, 0x72, 0x65, 0x2e, 0x48, 0x61, 0x73, 0x68,
|
||||
0x52, 0x10, 0x70, 0x72, 0x75, 0x6e, 0x69, 0x6e, 0x67, 0x50, 0x6f, 0x69, 0x6e, 0x74, 0x48, 0x61,
|
||||
0x73, 0x68, 0x22, 0x84, 0x01, 0x0a, 0x1f, 0x50, 0x72, 0x75, 0x6e, 0x69, 0x6e, 0x67, 0x50, 0x6f,
|
||||
0x69, 0x6e, 0x74, 0x55, 0x74, 0x78, 0x6f, 0x53, 0x65, 0x74, 0x43, 0x68, 0x75, 0x6e, 0x6b, 0x4d,
|
||||
0x65, 0x73, 0x73, 0x61, 0x67, 0x65, 0x12, 0x61, 0x0a, 0x19, 0x6f, 0x75, 0x74, 0x70, 0x6f, 0x69,
|
||||
0x6e, 0x74, 0x41, 0x6e, 0x64, 0x55, 0x74, 0x78, 0x6f, 0x45, 0x6e, 0x74, 0x72, 0x79, 0x50, 0x61,
|
||||
0x69, 0x72, 0x73, 0x18, 0x01, 0x20, 0x03, 0x28, 0x0b, 0x32, 0x23, 0x2e, 0x70, 0x72, 0x6f, 0x74,
|
||||
0x6f, 0x77, 0x69, 0x72, 0x65, 0x2e, 0x4f, 0x75, 0x74, 0x70, 0x6f, 0x69, 0x6e, 0x74, 0x41, 0x6e,
|
||||
0x64, 0x55, 0x74, 0x78, 0x6f, 0x45, 0x6e, 0x74, 0x72, 0x79, 0x50, 0x61, 0x69, 0x72, 0x52, 0x19,
|
||||
0x6f, 0x75, 0x74, 0x70, 0x6f, 0x69, 0x6e, 0x74, 0x41, 0x6e, 0x64, 0x55, 0x74, 0x78, 0x6f, 0x45,
|
||||
0x6e, 0x74, 0x72, 0x79, 0x50, 0x61, 0x69, 0x72, 0x73, 0x22, 0x7f, 0x0a, 0x18, 0x4f, 0x75, 0x74,
|
||||
0x70, 0x6f, 0x69, 0x6e, 0x74, 0x41, 0x6e, 0x64, 0x55, 0x74, 0x78, 0x6f, 0x45, 0x6e, 0x74, 0x72,
|
||||
0x79, 0x50, 0x61, 0x69, 0x72, 0x12, 0x2f, 0x0a, 0x08, 0x6f, 0x75, 0x74, 0x70, 0x6f, 0x69, 0x6e,
|
||||
0x74, 0x18, 0x01, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x13, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x77,
|
||||
0x69, 0x72, 0x65, 0x2e, 0x4f, 0x75, 0x74, 0x70, 0x6f, 0x69, 0x6e, 0x74, 0x52, 0x08, 0x6f, 0x75,
|
||||
0x74, 0x70, 0x6f, 0x69, 0x6e, 0x74, 0x12, 0x32, 0x0a, 0x09, 0x75, 0x74, 0x78, 0x6f, 0x45, 0x6e,
|
||||
0x74, 0x72, 0x79, 0x18, 0x02, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x14, 0x2e, 0x70, 0x72, 0x6f, 0x74,
|
||||
0x6f, 0x77, 0x69, 0x72, 0x65, 0x2e, 0x55, 0x74, 0x78, 0x6f, 0x45, 0x6e, 0x74, 0x72, 0x79, 0x52,
|
||||
0x09, 0x75, 0x74, 0x78, 0x6f, 0x45, 0x6e, 0x74, 0x72, 0x79, 0x22, 0xb1, 0x01, 0x0a, 0x09, 0x55,
|
||||
0x74, 0x78, 0x6f, 0x45, 0x6e, 0x74, 0x72, 0x79, 0x12, 0x16, 0x0a, 0x06, 0x61, 0x6d, 0x6f, 0x75,
|
||||
0x6e, 0x74, 0x18, 0x01, 0x20, 0x01, 0x28, 0x04, 0x52, 0x06, 0x61, 0x6d, 0x6f, 0x75, 0x6e, 0x74,
|
||||
0x12, 0x44, 0x0a, 0x0f, 0x73, 0x63, 0x72, 0x69, 0x70, 0x74, 0x50, 0x75, 0x62, 0x6c, 0x69, 0x63,
|
||||
0x4b, 0x65, 0x79, 0x18, 0x02, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x1a, 0x2e, 0x70, 0x72, 0x6f, 0x74,
|
||||
0x6f, 0x77, 0x69, 0x72, 0x65, 0x2e, 0x53, 0x63, 0x72, 0x69, 0x70, 0x74, 0x50, 0x75, 0x62, 0x6c,
|
||||
0x69, 0x63, 0x4b, 0x65, 0x79, 0x52, 0x0f, 0x73, 0x63, 0x72, 0x69, 0x70, 0x74, 0x50, 0x75, 0x62,
|
||||
0x6c, 0x69, 0x63, 0x4b, 0x65, 0x79, 0x12, 0x26, 0x0a, 0x0e, 0x62, 0x6c, 0x6f, 0x63, 0x6b, 0x42,
|
||||
0x6c, 0x75, 0x65, 0x53, 0x63, 0x6f, 0x72, 0x65, 0x18, 0x03, 0x20, 0x01, 0x28, 0x04, 0x52, 0x0e,
|
||||
0x62, 0x6c, 0x6f, 0x63, 0x6b, 0x42, 0x6c, 0x75, 0x65, 0x53, 0x63, 0x6f, 0x72, 0x65, 0x12, 0x1e,
|
||||
0x0a, 0x0a, 0x69, 0x73, 0x43, 0x6f, 0x69, 0x6e, 0x62, 0x61, 0x73, 0x65, 0x18, 0x04, 0x20, 0x01,
|
||||
0x28, 0x08, 0x52, 0x0a, 0x69, 0x73, 0x43, 0x6f, 0x69, 0x6e, 0x62, 0x61, 0x73, 0x65, 0x22, 0x2c,
|
||||
0x0a, 0x2a, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x4e, 0x65, 0x78, 0x74, 0x50, 0x72, 0x75,
|
||||
0x6e, 0x69, 0x6e, 0x67, 0x50, 0x6f, 0x69, 0x6e, 0x74, 0x55, 0x74, 0x78, 0x6f, 0x53, 0x65, 0x74,
|
||||
0x43, 0x68, 0x75, 0x6e, 0x6b, 0x4d, 0x65, 0x73, 0x73, 0x61, 0x67, 0x65, 0x22, 0x26, 0x0a, 0x24,
|
||||
0x44, 0x6f, 0x6e, 0x65, 0x50, 0x72, 0x75, 0x6e, 0x69, 0x6e, 0x67, 0x50, 0x6f, 0x69, 0x6e, 0x74,
|
||||
0x55, 0x74, 0x78, 0x6f, 0x53, 0x65, 0x74, 0x43, 0x68, 0x75, 0x6e, 0x6b, 0x73, 0x4d, 0x65, 0x73,
|
||||
0x73, 0x61, 0x67, 0x65, 0x22, 0x42, 0x0a, 0x17, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x49,
|
||||
0x42, 0x44, 0x42, 0x6c, 0x6f, 0x63, 0x6b, 0x73, 0x4d, 0x65, 0x73, 0x73, 0x61, 0x67, 0x65, 0x12,
|
||||
0x27, 0x0a, 0x06, 0x68, 0x61, 0x73, 0x68, 0x65, 0x73, 0x18, 0x01, 0x20, 0x03, 0x28, 0x0b, 0x32,
|
||||
0x0f, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x77, 0x69, 0x72, 0x65, 0x2e, 0x48, 0x61, 0x73, 0x68,
|
||||
0x52, 0x06, 0x68, 0x61, 0x73, 0x68, 0x65, 0x73, 0x22, 0x1f, 0x0a, 0x1d, 0x55, 0x6e, 0x65, 0x78,
|
||||
0x70, 0x65, 0x63, 0x74, 0x65, 0x64, 0x50, 0x72, 0x75, 0x6e, 0x69, 0x6e, 0x67, 0x50, 0x6f, 0x69,
|
||||
0x6e, 0x74, 0x4d, 0x65, 0x73, 0x73, 0x61, 0x67, 0x65, 0x22, 0x20, 0x0a, 0x1e, 0x52, 0x65, 0x71,
|
||||
0x75, 0x65, 0x73, 0x74, 0x50, 0x72, 0x75, 0x6e, 0x69, 0x6e, 0x67, 0x50, 0x6f, 0x69, 0x6e, 0x74,
|
||||
0x48, 0x61, 0x73, 0x68, 0x4d, 0x65, 0x73, 0x73, 0x61, 0x67, 0x65, 0x22, 0x3e, 0x0a, 0x17, 0x50,
|
||||
0x72, 0x75, 0x6e, 0x69, 0x6e, 0x67, 0x50, 0x6f, 0x69, 0x6e, 0x74, 0x48, 0x61, 0x73, 0x68, 0x4d,
|
||||
0x65, 0x73, 0x73, 0x61, 0x67, 0x65, 0x12, 0x23, 0x0a, 0x04, 0x68, 0x61, 0x73, 0x68, 0x18, 0x01,
|
||||
0x20, 0x01, 0x28, 0x0b, 0x32, 0x0f, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x77, 0x69, 0x72, 0x65,
|
||||
0x2e, 0x48, 0x61, 0x73, 0x68, 0x52, 0x04, 0x68, 0x61, 0x73, 0x68, 0x22, 0x8a, 0x01, 0x0a, 0x16,
|
||||
0x49, 0x62, 0x64, 0x42, 0x6c, 0x6f, 0x63, 0x6b, 0x4c, 0x6f, 0x63, 0x61, 0x74, 0x6f, 0x72, 0x4d,
|
||||
0x65, 0x73, 0x73, 0x61, 0x67, 0x65, 0x12, 0x2f, 0x0a, 0x0a, 0x74, 0x61, 0x72, 0x67, 0x65, 0x74,
|
||||
0x48, 0x61, 0x73, 0x68, 0x18, 0x01, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x0f, 0x2e, 0x70, 0x72, 0x6f,
|
||||
0x74, 0x6f, 0x77, 0x69, 0x72, 0x65, 0x2e, 0x48, 0x61, 0x73, 0x68, 0x52, 0x0a, 0x74, 0x61, 0x72,
|
||||
0x67, 0x65, 0x74, 0x48, 0x61, 0x73, 0x68, 0x12, 0x3f, 0x0a, 0x12, 0x62, 0x6c, 0x6f, 0x63, 0x6b,
|
||||
0x4c, 0x6f, 0x63, 0x61, 0x74, 0x6f, 0x72, 0x48, 0x61, 0x73, 0x68, 0x65, 0x73, 0x18, 0x02, 0x20,
|
||||
0x03, 0x28, 0x0b, 0x32, 0x0f, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x77, 0x69, 0x72, 0x65, 0x2e,
|
||||
0x48, 0x61, 0x73, 0x68, 0x52, 0x12, 0x62, 0x6c, 0x6f, 0x63, 0x6b, 0x4c, 0x6f, 0x63, 0x61, 0x74,
|
||||
0x6f, 0x72, 0x48, 0x61, 0x73, 0x68, 0x65, 0x73, 0x22, 0x56, 0x0a, 0x21, 0x49, 0x62, 0x64, 0x42,
|
||||
0x6c, 0x6f, 0x63, 0x6b, 0x4c, 0x6f, 0x63, 0x61, 0x74, 0x6f, 0x72, 0x48, 0x69, 0x67, 0x68, 0x65,
|
||||
0x73, 0x74, 0x48, 0x61, 0x73, 0x68, 0x4d, 0x65, 0x73, 0x73, 0x61, 0x67, 0x65, 0x12, 0x31, 0x0a,
|
||||
0x0b, 0x68, 0x69, 0x67, 0x68, 0x65, 0x73, 0x74, 0x48, 0x61, 0x73, 0x68, 0x18, 0x01, 0x20, 0x01,
|
||||
0x28, 0x0b, 0x32, 0x0f, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x77, 0x69, 0x72, 0x65, 0x2e, 0x48,
|
||||
0x61, 0x73, 0x68, 0x52, 0x0b, 0x68, 0x69, 0x67, 0x68, 0x65, 0x73, 0x74, 0x48, 0x61, 0x73, 0x68,
|
||||
0x22, 0x58, 0x0a, 0x13, 0x42, 0x6c, 0x6f, 0x63, 0x6b, 0x48, 0x65, 0x61, 0x64, 0x65, 0x72, 0x73,
|
||||
0x4d, 0x65, 0x73, 0x73, 0x61, 0x67, 0x65, 0x12, 0x41, 0x0a, 0x0c, 0x62, 0x6c, 0x6f, 0x63, 0x6b,
|
||||
0x48, 0x65, 0x61, 0x64, 0x65, 0x72, 0x73, 0x18, 0x01, 0x20, 0x03, 0x28, 0x0b, 0x32, 0x1d, 0x2e,
|
||||
0x70, 0x72, 0x6f, 0x74, 0x6f, 0x77, 0x69, 0x72, 0x65, 0x2e, 0x42, 0x6c, 0x6f, 0x63, 0x6b, 0x48,
|
||||
0x65, 0x61, 0x64, 0x65, 0x72, 0x4d, 0x65, 0x73, 0x73, 0x61, 0x67, 0x65, 0x52, 0x0c, 0x62, 0x6c,
|
||||
0x6f, 0x63, 0x6b, 0x48, 0x65, 0x61, 0x64, 0x65, 0x72, 0x73, 0x42, 0x26, 0x5a, 0x24, 0x67, 0x69,
|
||||
0x74, 0x68, 0x75, 0x62, 0x2e, 0x63, 0x6f, 0x6d, 0x2f, 0x6b, 0x61, 0x73, 0x70, 0x61, 0x6e, 0x65,
|
||||
0x74, 0x2f, 0x6b, 0x61, 0x73, 0x70, 0x61, 0x64, 0x2f, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x77, 0x69,
|
||||
0x72, 0x65, 0x62, 0x06, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x33,
|
||||
}
|
||||
|
||||
var (
|
||||
@ -2330,7 +2484,7 @@ func file_p2p_proto_rawDescGZIP() []byte {
|
||||
return file_p2p_proto_rawDescData
|
||||
}
|
||||
|
||||
var file_p2p_proto_msgTypes = make([]protoimpl.MessageInfo, 39)
|
||||
var file_p2p_proto_msgTypes = make([]protoimpl.MessageInfo, 41)
|
||||
var file_p2p_proto_goTypes = []interface{}{
|
||||
(*RequestAddressesMessage)(nil), // 0: protowire.RequestAddressesMessage
|
||||
(*AddressesMessage)(nil), // 1: protowire.AddressesMessage
|
||||
@ -2360,17 +2514,19 @@ var file_p2p_proto_goTypes = []interface{}{
|
||||
(*VerackMessage)(nil), // 25: protowire.VerackMessage
|
||||
(*VersionMessage)(nil), // 26: protowire.VersionMessage
|
||||
(*RejectMessage)(nil), // 27: protowire.RejectMessage
|
||||
(*RequestIBDRootUTXOSetAndBlockMessage)(nil), // 28: protowire.RequestIBDRootUTXOSetAndBlockMessage
|
||||
(*IbdRootUtxoSetChunkMessage)(nil), // 29: protowire.IbdRootUtxoSetChunkMessage
|
||||
(*RequestNextIbdRootUtxoSetChunkMessage)(nil), // 30: protowire.RequestNextIbdRootUtxoSetChunkMessage
|
||||
(*DoneIbdRootUtxoSetChunksMessage)(nil), // 31: protowire.DoneIbdRootUtxoSetChunksMessage
|
||||
(*RequestIBDBlocksMessage)(nil), // 32: protowire.RequestIBDBlocksMessage
|
||||
(*IBDRootNotFoundMessage)(nil), // 33: protowire.IBDRootNotFoundMessage
|
||||
(*RequestIBDRootHashMessage)(nil), // 34: protowire.RequestIBDRootHashMessage
|
||||
(*IBDRootHashMessage)(nil), // 35: protowire.IBDRootHashMessage
|
||||
(*IbdBlockLocatorMessage)(nil), // 36: protowire.IbdBlockLocatorMessage
|
||||
(*IbdBlockLocatorHighestHashMessage)(nil), // 37: protowire.IbdBlockLocatorHighestHashMessage
|
||||
(*BlockHeadersMessage)(nil), // 38: protowire.BlockHeadersMessage
|
||||
(*RequestPruningPointUTXOSetAndBlockMessage)(nil), // 28: protowire.RequestPruningPointUTXOSetAndBlockMessage
|
||||
(*PruningPointUtxoSetChunkMessage)(nil), // 29: protowire.PruningPointUtxoSetChunkMessage
|
||||
(*OutpointAndUtxoEntryPair)(nil), // 30: protowire.OutpointAndUtxoEntryPair
|
||||
(*UtxoEntry)(nil), // 31: protowire.UtxoEntry
|
||||
(*RequestNextPruningPointUtxoSetChunkMessage)(nil), // 32: protowire.RequestNextPruningPointUtxoSetChunkMessage
|
||||
(*DonePruningPointUtxoSetChunksMessage)(nil), // 33: protowire.DonePruningPointUtxoSetChunksMessage
|
||||
(*RequestIBDBlocksMessage)(nil), // 34: protowire.RequestIBDBlocksMessage
|
||||
(*UnexpectedPruningPointMessage)(nil), // 35: protowire.UnexpectedPruningPointMessage
|
||||
(*RequestPruningPointHashMessage)(nil), // 36: protowire.RequestPruningPointHashMessage
|
||||
(*PruningPointHashMessage)(nil), // 37: protowire.PruningPointHashMessage
|
||||
(*IbdBlockLocatorMessage)(nil), // 38: protowire.IbdBlockLocatorMessage
|
||||
(*IbdBlockLocatorHighestHashMessage)(nil), // 39: protowire.IbdBlockLocatorHighestHashMessage
|
||||
(*BlockHeadersMessage)(nil), // 40: protowire.BlockHeadersMessage
|
||||
}
|
||||
var file_p2p_proto_depIdxs = []int32{
|
||||
3, // 0: protowire.RequestAddressesMessage.subnetworkId:type_name -> protowire.SubnetworkId
|
||||
@ -2400,18 +2556,22 @@ var file_p2p_proto_depIdxs = []int32{
|
||||
7, // 24: protowire.InvTransactionsMessage.ids:type_name -> protowire.TransactionId
|
||||
2, // 25: protowire.VersionMessage.address:type_name -> protowire.NetAddress
|
||||
3, // 26: protowire.VersionMessage.subnetworkId:type_name -> protowire.SubnetworkId
|
||||
12, // 27: protowire.RequestIBDRootUTXOSetAndBlockMessage.ibdRoot:type_name -> protowire.Hash
|
||||
12, // 28: protowire.RequestIBDBlocksMessage.hashes:type_name -> protowire.Hash
|
||||
12, // 29: protowire.IBDRootHashMessage.hash:type_name -> protowire.Hash
|
||||
12, // 30: protowire.IbdBlockLocatorMessage.targetHash:type_name -> protowire.Hash
|
||||
12, // 31: protowire.IbdBlockLocatorMessage.blockLocatorHashes:type_name -> protowire.Hash
|
||||
12, // 32: protowire.IbdBlockLocatorHighestHashMessage.highestHash:type_name -> protowire.Hash
|
||||
11, // 33: protowire.BlockHeadersMessage.blockHeaders:type_name -> protowire.BlockHeaderMessage
|
||||
34, // [34:34] is the sub-list for method output_type
|
||||
34, // [34:34] is the sub-list for method input_type
|
||||
34, // [34:34] is the sub-list for extension type_name
|
||||
34, // [34:34] is the sub-list for extension extendee
|
||||
0, // [0:34] is the sub-list for field type_name
|
||||
12, // 27: protowire.RequestPruningPointUTXOSetAndBlockMessage.pruningPointHash:type_name -> protowire.Hash
|
||||
30, // 28: protowire.PruningPointUtxoSetChunkMessage.outpointAndUtxoEntryPairs:type_name -> protowire.OutpointAndUtxoEntryPair
|
||||
6, // 29: protowire.OutpointAndUtxoEntryPair.outpoint:type_name -> protowire.Outpoint
|
||||
31, // 30: protowire.OutpointAndUtxoEntryPair.utxoEntry:type_name -> protowire.UtxoEntry
|
||||
8, // 31: protowire.UtxoEntry.scriptPublicKey:type_name -> protowire.ScriptPublicKey
|
||||
12, // 32: protowire.RequestIBDBlocksMessage.hashes:type_name -> protowire.Hash
|
||||
12, // 33: protowire.PruningPointHashMessage.hash:type_name -> protowire.Hash
|
||||
12, // 34: protowire.IbdBlockLocatorMessage.targetHash:type_name -> protowire.Hash
|
||||
12, // 35: protowire.IbdBlockLocatorMessage.blockLocatorHashes:type_name -> protowire.Hash
|
||||
12, // 36: protowire.IbdBlockLocatorHighestHashMessage.highestHash:type_name -> protowire.Hash
|
||||
11, // 37: protowire.BlockHeadersMessage.blockHeaders:type_name -> protowire.BlockHeaderMessage
|
||||
38, // [38:38] is the sub-list for method output_type
|
||||
38, // [38:38] is the sub-list for method input_type
|
||||
38, // [38:38] is the sub-list for extension type_name
|
||||
38, // [38:38] is the sub-list for extension extendee
|
||||
0, // [0:38] is the sub-list for field type_name
|
||||
}
|
||||
|
||||
func init() { file_p2p_proto_init() }
|
||||
@ -2757,7 +2917,7 @@ func file_p2p_proto_init() {
|
||||
}
|
||||
}
|
||||
file_p2p_proto_msgTypes[28].Exporter = func(v interface{}, i int) interface{} {
|
||||
switch v := v.(*RequestIBDRootUTXOSetAndBlockMessage); i {
|
||||
switch v := v.(*RequestPruningPointUTXOSetAndBlockMessage); i {
|
||||
case 0:
|
||||
return &v.state
|
||||
case 1:
|
||||
@ -2769,7 +2929,7 @@ func file_p2p_proto_init() {
|
||||
}
|
||||
}
|
||||
file_p2p_proto_msgTypes[29].Exporter = func(v interface{}, i int) interface{} {
|
||||
switch v := v.(*IbdRootUtxoSetChunkMessage); i {
|
||||
switch v := v.(*PruningPointUtxoSetChunkMessage); i {
|
||||
case 0:
|
||||
return &v.state
|
||||
case 1:
|
||||
@ -2781,7 +2941,7 @@ func file_p2p_proto_init() {
|
||||
}
|
||||
}
|
||||
file_p2p_proto_msgTypes[30].Exporter = func(v interface{}, i int) interface{} {
|
||||
switch v := v.(*RequestNextIbdRootUtxoSetChunkMessage); i {
|
||||
switch v := v.(*OutpointAndUtxoEntryPair); i {
|
||||
case 0:
|
||||
return &v.state
|
||||
case 1:
|
||||
@ -2793,7 +2953,7 @@ func file_p2p_proto_init() {
|
||||
}
|
||||
}
|
||||
file_p2p_proto_msgTypes[31].Exporter = func(v interface{}, i int) interface{} {
|
||||
switch v := v.(*DoneIbdRootUtxoSetChunksMessage); i {
|
||||
switch v := v.(*UtxoEntry); i {
|
||||
case 0:
|
||||
return &v.state
|
||||
case 1:
|
||||
@ -2805,7 +2965,7 @@ func file_p2p_proto_init() {
|
||||
}
|
||||
}
|
||||
file_p2p_proto_msgTypes[32].Exporter = func(v interface{}, i int) interface{} {
|
||||
switch v := v.(*RequestIBDBlocksMessage); i {
|
||||
switch v := v.(*RequestNextPruningPointUtxoSetChunkMessage); i {
|
||||
case 0:
|
||||
return &v.state
|
||||
case 1:
|
||||
@ -2817,7 +2977,7 @@ func file_p2p_proto_init() {
|
||||
}
|
||||
}
|
||||
file_p2p_proto_msgTypes[33].Exporter = func(v interface{}, i int) interface{} {
|
||||
switch v := v.(*IBDRootNotFoundMessage); i {
|
||||
switch v := v.(*DonePruningPointUtxoSetChunksMessage); i {
|
||||
case 0:
|
||||
return &v.state
|
||||
case 1:
|
||||
@ -2829,7 +2989,7 @@ func file_p2p_proto_init() {
|
||||
}
|
||||
}
|
||||
file_p2p_proto_msgTypes[34].Exporter = func(v interface{}, i int) interface{} {
|
||||
switch v := v.(*RequestIBDRootHashMessage); i {
|
||||
switch v := v.(*RequestIBDBlocksMessage); i {
|
||||
case 0:
|
||||
return &v.state
|
||||
case 1:
|
||||
@ -2841,7 +3001,7 @@ func file_p2p_proto_init() {
|
||||
}
|
||||
}
|
||||
file_p2p_proto_msgTypes[35].Exporter = func(v interface{}, i int) interface{} {
|
||||
switch v := v.(*IBDRootHashMessage); i {
|
||||
switch v := v.(*UnexpectedPruningPointMessage); i {
|
||||
case 0:
|
||||
return &v.state
|
||||
case 1:
|
||||
@ -2853,7 +3013,7 @@ func file_p2p_proto_init() {
|
||||
}
|
||||
}
|
||||
file_p2p_proto_msgTypes[36].Exporter = func(v interface{}, i int) interface{} {
|
||||
switch v := v.(*IbdBlockLocatorMessage); i {
|
||||
switch v := v.(*RequestPruningPointHashMessage); i {
|
||||
case 0:
|
||||
return &v.state
|
||||
case 1:
|
||||
@ -2865,7 +3025,7 @@ func file_p2p_proto_init() {
|
||||
}
|
||||
}
|
||||
file_p2p_proto_msgTypes[37].Exporter = func(v interface{}, i int) interface{} {
|
||||
switch v := v.(*IbdBlockLocatorHighestHashMessage); i {
|
||||
switch v := v.(*PruningPointHashMessage); i {
|
||||
case 0:
|
||||
return &v.state
|
||||
case 1:
|
||||
@ -2877,6 +3037,30 @@ func file_p2p_proto_init() {
|
||||
}
|
||||
}
|
||||
file_p2p_proto_msgTypes[38].Exporter = func(v interface{}, i int) interface{} {
|
||||
switch v := v.(*IbdBlockLocatorMessage); i {
|
||||
case 0:
|
||||
return &v.state
|
||||
case 1:
|
||||
return &v.sizeCache
|
||||
case 2:
|
||||
return &v.unknownFields
|
||||
default:
|
||||
return nil
|
||||
}
|
||||
}
|
||||
file_p2p_proto_msgTypes[39].Exporter = func(v interface{}, i int) interface{} {
|
||||
switch v := v.(*IbdBlockLocatorHighestHashMessage); i {
|
||||
case 0:
|
||||
return &v.state
|
||||
case 1:
|
||||
return &v.sizeCache
|
||||
case 2:
|
||||
return &v.unknownFields
|
||||
default:
|
||||
return nil
|
||||
}
|
||||
}
|
||||
file_p2p_proto_msgTypes[40].Exporter = func(v interface{}, i int) interface{} {
|
||||
switch v := v.(*BlockHeadersMessage); i {
|
||||
case 0:
|
||||
return &v.state
|
||||
@ -2895,7 +3079,7 @@ func file_p2p_proto_init() {
|
||||
GoPackagePath: reflect.TypeOf(x{}).PkgPath(),
|
||||
RawDescriptor: file_p2p_proto_rawDesc,
|
||||
NumEnums: 0,
|
||||
NumMessages: 39,
|
||||
NumMessages: 41,
|
||||
NumExtensions: 0,
|
||||
NumServices: 0,
|
||||
},
|
||||
|
@ -146,31 +146,43 @@ message RejectMessage{
|
||||
string reason = 1;
|
||||
}
|
||||
|
||||
message RequestIBDRootUTXOSetAndBlockMessage{
|
||||
Hash ibdRoot = 1;
|
||||
message RequestPruningPointUTXOSetAndBlockMessage{
|
||||
Hash pruningPointHash = 1;
|
||||
}
|
||||
|
||||
message IbdRootUtxoSetChunkMessage{
|
||||
bytes chunk = 1;
|
||||
message PruningPointUtxoSetChunkMessage{
|
||||
repeated OutpointAndUtxoEntryPair outpointAndUtxoEntryPairs = 1;
|
||||
}
|
||||
|
||||
message RequestNextIbdRootUtxoSetChunkMessage {
|
||||
message OutpointAndUtxoEntryPair{
|
||||
Outpoint outpoint = 1;
|
||||
UtxoEntry utxoEntry = 2;
|
||||
}
|
||||
|
||||
message DoneIbdRootUtxoSetChunksMessage {
|
||||
message UtxoEntry {
|
||||
uint64 amount = 1;
|
||||
ScriptPublicKey scriptPublicKey = 2;
|
||||
uint64 blockBlueScore = 3;
|
||||
bool isCoinbase = 4;
|
||||
}
|
||||
|
||||
message RequestNextPruningPointUtxoSetChunkMessage {
|
||||
}
|
||||
|
||||
message DonePruningPointUtxoSetChunksMessage {
|
||||
}
|
||||
|
||||
message RequestIBDBlocksMessage{
|
||||
repeated Hash hashes = 1;
|
||||
}
|
||||
|
||||
message IBDRootNotFoundMessage{
|
||||
message UnexpectedPruningPointMessage{
|
||||
}
|
||||
|
||||
message RequestIBDRootHashMessage{
|
||||
message RequestPruningPointHashMessage{
|
||||
}
|
||||
|
||||
message IBDRootHashMessage{
|
||||
message PruningPointHashMessage{
|
||||
Hash hash = 1;
|
||||
}
|
||||
|
||||
|
@ -1,12 +0,0 @@
|
||||
package protowire
|
||||
|
||||
import "github.com/kaspanet/kaspad/app/appmessage"
|
||||
|
||||
func (x *KaspadMessage_DoneIbdRootUtxoSetChunks) toAppMessage() (appmessage.Message, error) {
|
||||
return &appmessage.MsgDoneIBDRootUTXOSetChunks{}, nil
|
||||
}
|
||||
|
||||
func (x *KaspadMessage_DoneIbdRootUtxoSetChunks) fromAppMessage(_ *appmessage.MsgDoneIBDRootUTXOSetChunks) error {
|
||||
x.DoneIbdRootUtxoSetChunks = &DoneIbdRootUtxoSetChunksMessage{}
|
||||
return nil
|
||||
}
|
@ -0,0 +1,12 @@
|
||||
package protowire
|
||||
|
||||
import "github.com/kaspanet/kaspad/app/appmessage"
|
||||
|
||||
func (x *KaspadMessage_DonePruningPointUtxoSetChunks) toAppMessage() (appmessage.Message, error) {
|
||||
return &appmessage.MsgDonePruningPointUTXOSetChunks{}, nil
|
||||
}
|
||||
|
||||
func (x *KaspadMessage_DonePruningPointUtxoSetChunks) fromAppMessage(_ *appmessage.MsgDonePruningPointUTXOSetChunks) error {
|
||||
x.DonePruningPointUtxoSetChunks = &DonePruningPointUtxoSetChunksMessage{}
|
||||
return nil
|
||||
}
|
@ -1,19 +0,0 @@
|
||||
package protowire
|
||||
|
||||
import "github.com/kaspanet/kaspad/app/appmessage"
|
||||
|
||||
func (x *KaspadMessage_IbdRootHash) toAppMessage() (appmessage.Message, error) {
|
||||
hash, err := x.IbdRootHash.Hash.toDomain()
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
return &appmessage.MsgIBDRootHashMessage{Hash: hash}, nil
|
||||
}
|
||||
|
||||
func (x *KaspadMessage_IbdRootHash) fromAppMessage(msgIBDRootHash *appmessage.MsgIBDRootHashMessage) error {
|
||||
x.IbdRootHash = &IBDRootHashMessage{
|
||||
Hash: domainHashToProto(msgIBDRootHash.Hash),
|
||||
}
|
||||
return nil
|
||||
}
|
@ -1,11 +0,0 @@
|
||||
package protowire
|
||||
|
||||
import "github.com/kaspanet/kaspad/app/appmessage"
|
||||
|
||||
func (x *KaspadMessage_IbdRootNotFound) toAppMessage() (appmessage.Message, error) {
|
||||
return &appmessage.MsgIBDRootNotFound{}, nil
|
||||
}
|
||||
|
||||
func (x *KaspadMessage_IbdRootNotFound) fromAppMessage(_ *appmessage.MsgIBDRootNotFound) error {
|
||||
return nil
|
||||
}
|
@ -1,16 +0,0 @@
|
||||
package protowire
|
||||
|
||||
import "github.com/kaspanet/kaspad/app/appmessage"
|
||||
|
||||
func (x *KaspadMessage_IbdRootUtxoSetChunk) toAppMessage() (appmessage.Message, error) {
|
||||
return &appmessage.MsgIBDRootUTXOSetChunk{
|
||||
Chunk: x.IbdRootUtxoSetChunk.Chunk,
|
||||
}, nil
|
||||
}
|
||||
|
||||
func (x *KaspadMessage_IbdRootUtxoSetChunk) fromAppMessage(message *appmessage.MsgIBDRootUTXOSetChunk) error {
|
||||
x.IbdRootUtxoSetChunk = &IbdRootUtxoSetChunkMessage{
|
||||
Chunk: message.Chunk,
|
||||
}
|
||||
return nil
|
||||
}
|
@ -0,0 +1,19 @@
|
||||
package protowire
|
||||
|
||||
import "github.com/kaspanet/kaspad/app/appmessage"
|
||||
|
||||
func (x *KaspadMessage_PruningPointHash) toAppMessage() (appmessage.Message, error) {
|
||||
hash, err := x.PruningPointHash.Hash.toDomain()
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
return &appmessage.MsgPruningPointHashMessage{Hash: hash}, nil
|
||||
}
|
||||
|
||||
func (x *KaspadMessage_PruningPointHash) fromAppMessage(msgPruningPointHash *appmessage.MsgPruningPointHashMessage) error {
|
||||
x.PruningPointHash = &PruningPointHashMessage{
|
||||
Hash: domainHashToProto(msgPruningPointHash.Hash),
|
||||
}
|
||||
return nil
|
||||
}
|
@ -0,0 +1,71 @@
|
||||
package protowire
|
||||
|
||||
import (
|
||||
"github.com/kaspanet/kaspad/app/appmessage"
|
||||
"github.com/kaspanet/kaspad/domain/consensus/model/externalapi"
|
||||
"github.com/pkg/errors"
|
||||
"math"
|
||||
)
|
||||
|
||||
func (x *KaspadMessage_PruningPointUtxoSetChunk) toAppMessage() (appmessage.Message, error) {
|
||||
outpointAndUTXOEntryPairs := make([]*appmessage.OutpointAndUTXOEntryPair, len(x.PruningPointUtxoSetChunk.OutpointAndUtxoEntryPairs))
|
||||
for i, outpointAndUTXOEntryPair := range x.PruningPointUtxoSetChunk.OutpointAndUtxoEntryPairs {
|
||||
transactionID, err := outpointAndUTXOEntryPair.Outpoint.TransactionId.toDomain()
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
outpoint := &appmessage.Outpoint{
|
||||
TxID: *transactionID,
|
||||
Index: outpointAndUTXOEntryPair.Outpoint.Index,
|
||||
}
|
||||
if outpointAndUTXOEntryPair.UtxoEntry.ScriptPublicKey.Version > math.MaxUint16 {
|
||||
return nil, errors.Errorf("ScriptPublicKey version is bigger then uint16.")
|
||||
}
|
||||
scriptPublicKey := &externalapi.ScriptPublicKey{
|
||||
Script: outpointAndUTXOEntryPair.UtxoEntry.ScriptPublicKey.Script,
|
||||
Version: uint16(outpointAndUTXOEntryPair.UtxoEntry.ScriptPublicKey.Version),
|
||||
}
|
||||
utxoEntry := &appmessage.UTXOEntry{
|
||||
Amount: outpointAndUTXOEntryPair.UtxoEntry.Amount,
|
||||
ScriptPublicKey: scriptPublicKey,
|
||||
BlockBlueScore: outpointAndUTXOEntryPair.UtxoEntry.BlockBlueScore,
|
||||
IsCoinbase: outpointAndUTXOEntryPair.UtxoEntry.IsCoinbase,
|
||||
}
|
||||
outpointAndUTXOEntryPairs[i] = &appmessage.OutpointAndUTXOEntryPair{
|
||||
Outpoint: outpoint,
|
||||
UTXOEntry: utxoEntry,
|
||||
}
|
||||
}
|
||||
return &appmessage.MsgPruningPointUTXOSetChunk{
|
||||
OutpointAndUTXOEntryPairs: outpointAndUTXOEntryPairs,
|
||||
}, nil
|
||||
}
|
||||
|
||||
func (x *KaspadMessage_PruningPointUtxoSetChunk) fromAppMessage(message *appmessage.MsgPruningPointUTXOSetChunk) error {
|
||||
outpointAndUTXOEntryPairs := make([]*OutpointAndUtxoEntryPair, len(message.OutpointAndUTXOEntryPairs))
|
||||
for i, outpointAndUTXOEntryPair := range message.OutpointAndUTXOEntryPairs {
|
||||
transactionID := domainTransactionIDToProto(&outpointAndUTXOEntryPair.Outpoint.TxID)
|
||||
outpoint := &Outpoint{
|
||||
TransactionId: transactionID,
|
||||
Index: outpointAndUTXOEntryPair.Outpoint.Index,
|
||||
}
|
||||
scriptPublicKey := &ScriptPublicKey{
|
||||
Script: outpointAndUTXOEntryPair.UTXOEntry.ScriptPublicKey.Script,
|
||||
Version: uint32(outpointAndUTXOEntryPair.UTXOEntry.ScriptPublicKey.Version),
|
||||
}
|
||||
utxoEntry := &UtxoEntry{
|
||||
Amount: outpointAndUTXOEntryPair.UTXOEntry.Amount,
|
||||
ScriptPublicKey: scriptPublicKey,
|
||||
BlockBlueScore: outpointAndUTXOEntryPair.UTXOEntry.BlockBlueScore,
|
||||
IsCoinbase: outpointAndUTXOEntryPair.UTXOEntry.IsCoinbase,
|
||||
}
|
||||
outpointAndUTXOEntryPairs[i] = &OutpointAndUtxoEntryPair{
|
||||
Outpoint: outpoint,
|
||||
UtxoEntry: utxoEntry,
|
||||
}
|
||||
}
|
||||
x.PruningPointUtxoSetChunk = &PruningPointUtxoSetChunkMessage{
|
||||
OutpointAndUtxoEntryPairs: outpointAndUTXOEntryPairs,
|
||||
}
|
||||
return nil
|
||||
}
|
@ -1,11 +0,0 @@
|
||||
package protowire
|
||||
|
||||
import "github.com/kaspanet/kaspad/app/appmessage"
|
||||
|
||||
func (x *KaspadMessage_RequestIBDRootHash) toAppMessage() (appmessage.Message, error) {
|
||||
return &appmessage.MsgRequestIBDRootHashMessage{}, nil
|
||||
}
|
||||
|
||||
func (x *KaspadMessage_RequestIBDRootHash) fromAppMessage(_ *appmessage.MsgRequestIBDRootHashMessage) error {
|
||||
return nil
|
||||
}
|
@ -1,20 +0,0 @@
|
||||
package protowire
|
||||
|
||||
import "github.com/kaspanet/kaspad/app/appmessage"
|
||||
|
||||
func (x *KaspadMessage_RequestIBDRootUTXOSetAndBlock) toAppMessage() (appmessage.Message, error) {
|
||||
ibdRoot, err := x.RequestIBDRootUTXOSetAndBlock.IbdRoot.toDomain()
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
return &appmessage.MsgRequestIBDRootUTXOSetAndBlock{IBDRoot: ibdRoot}, nil
|
||||
}
|
||||
|
||||
func (x *KaspadMessage_RequestIBDRootUTXOSetAndBlock) fromAppMessage(
|
||||
msgRequestIBDRootUTXOSetAndBlock *appmessage.MsgRequestIBDRootUTXOSetAndBlock) error {
|
||||
|
||||
x.RequestIBDRootUTXOSetAndBlock = &RequestIBDRootUTXOSetAndBlockMessage{}
|
||||
x.RequestIBDRootUTXOSetAndBlock.IbdRoot = domainHashToProto(msgRequestIBDRootUTXOSetAndBlock.IBDRoot)
|
||||
return nil
|
||||
}
|
@ -1,12 +0,0 @@
|
||||
package protowire
|
||||
|
||||
import "github.com/kaspanet/kaspad/app/appmessage"
|
||||
|
||||
func (x *KaspadMessage_RequestNextIbdRootUtxoSetChunk) toAppMessage() (appmessage.Message, error) {
|
||||
return &appmessage.MsgRequestNextIBDRootUTXOSetChunk{}, nil
|
||||
}
|
||||
|
||||
func (x *KaspadMessage_RequestNextIbdRootUtxoSetChunk) fromAppMessage(message *appmessage.MsgRequestNextIBDRootUTXOSetChunk) error {
|
||||
x.RequestNextIbdRootUtxoSetChunk = &RequestNextIbdRootUtxoSetChunkMessage{}
|
||||
return nil
|
||||
}
|
@ -0,0 +1,12 @@
|
||||
package protowire
|
||||
|
||||
import "github.com/kaspanet/kaspad/app/appmessage"
|
||||
|
||||
func (x *KaspadMessage_RequestNextPruningPointUtxoSetChunk) toAppMessage() (appmessage.Message, error) {
|
||||
return &appmessage.MsgRequestNextPruningPointUTXOSetChunk{}, nil
|
||||
}
|
||||
|
||||
func (x *KaspadMessage_RequestNextPruningPointUtxoSetChunk) fromAppMessage(_ *appmessage.MsgRequestNextPruningPointUTXOSetChunk) error {
|
||||
x.RequestNextPruningPointUtxoSetChunk = &RequestNextPruningPointUtxoSetChunkMessage{}
|
||||
return nil
|
||||
}
|
@ -0,0 +1,11 @@
|
||||
package protowire
|
||||
|
||||
import "github.com/kaspanet/kaspad/app/appmessage"
|
||||
|
||||
func (x *KaspadMessage_RequestPruningPointHash) toAppMessage() (appmessage.Message, error) {
|
||||
return &appmessage.MsgRequestPruningPointHashMessage{}, nil
|
||||
}
|
||||
|
||||
func (x *KaspadMessage_RequestPruningPointHash) fromAppMessage(_ *appmessage.MsgRequestPruningPointHashMessage) error {
|
||||
return nil
|
||||
}
|
@ -0,0 +1,19 @@
|
||||
package protowire
|
||||
|
||||
import "github.com/kaspanet/kaspad/app/appmessage"
|
||||
|
||||
func (x *KaspadMessage_RequestPruningPointUTXOSetAndBlock) toAppMessage() (appmessage.Message, error) {
|
||||
pruningPointHash, err := x.RequestPruningPointUTXOSetAndBlock.PruningPointHash.toDomain()
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
return &appmessage.MsgRequestPruningPointUTXOSetAndBlock{PruningPointHash: pruningPointHash}, nil
|
||||
}
|
||||
|
||||
func (x *KaspadMessage_RequestPruningPointUTXOSetAndBlock) fromAppMessage(
|
||||
msgRequestPruningPointUTXOSetAndBlock *appmessage.MsgRequestPruningPointUTXOSetAndBlock) error {
|
||||
|
||||
x.RequestPruningPointUTXOSetAndBlock = &RequestPruningPointUTXOSetAndBlockMessage{}
|
||||
x.RequestPruningPointUTXOSetAndBlock.PruningPointHash = domainHashToProto(msgRequestPruningPointUTXOSetAndBlock.PruningPointHash)
|
||||
return nil
|
||||
}
|
@ -0,0 +1,11 @@
|
||||
package protowire
|
||||
|
||||
import "github.com/kaspanet/kaspad/app/appmessage"
|
||||
|
||||
func (x *KaspadMessage_UnexpectedPruningPoint) toAppMessage() (appmessage.Message, error) {
|
||||
return &appmessage.MsgUnexpectedPruningPoint{}, nil
|
||||
}
|
||||
|
||||
func (x *KaspadMessage_UnexpectedPruningPoint) fromAppMessage(_ *appmessage.MsgUnexpectedPruningPoint) error {
|
||||
return nil
|
||||
}
|
@ -195,15 +195,15 @@ func toP2PPayload(message appmessage.Message) (isKaspadMessage_Payload, error) {
|
||||
return nil, err
|
||||
}
|
||||
return payload, nil
|
||||
case *appmessage.MsgRequestIBDRootUTXOSetAndBlock:
|
||||
payload := new(KaspadMessage_RequestIBDRootUTXOSetAndBlock)
|
||||
case *appmessage.MsgRequestPruningPointUTXOSetAndBlock:
|
||||
payload := new(KaspadMessage_RequestPruningPointUTXOSetAndBlock)
|
||||
err := payload.fromAppMessage(message)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
return payload, nil
|
||||
case *appmessage.MsgIBDRootUTXOSetChunk:
|
||||
payload := new(KaspadMessage_IbdRootUtxoSetChunk)
|
||||
case *appmessage.MsgPruningPointUTXOSetChunk:
|
||||
payload := new(KaspadMessage_PruningPointUtxoSetChunk)
|
||||
err := payload.fromAppMessage(message)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
@ -216,22 +216,22 @@ func toP2PPayload(message appmessage.Message) (isKaspadMessage_Payload, error) {
|
||||
return nil, err
|
||||
}
|
||||
return payload, nil
|
||||
case *appmessage.MsgIBDRootNotFound:
|
||||
payload := new(KaspadMessage_IbdRootNotFound)
|
||||
case *appmessage.MsgUnexpectedPruningPoint:
|
||||
payload := new(KaspadMessage_UnexpectedPruningPoint)
|
||||
err := payload.fromAppMessage(message)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
return payload, nil
|
||||
case *appmessage.MsgRequestIBDRootHashMessage:
|
||||
payload := new(KaspadMessage_RequestIBDRootHash)
|
||||
case *appmessage.MsgRequestPruningPointHashMessage:
|
||||
payload := new(KaspadMessage_RequestPruningPointHash)
|
||||
err := payload.fromAppMessage(message)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
return payload, nil
|
||||
case *appmessage.MsgIBDRootHashMessage:
|
||||
payload := new(KaspadMessage_IbdRootHash)
|
||||
case *appmessage.MsgPruningPointHashMessage:
|
||||
payload := new(KaspadMessage_PruningPointHash)
|
||||
err := payload.fromAppMessage(message)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
@ -258,15 +258,15 @@ func toP2PPayload(message appmessage.Message) (isKaspadMessage_Payload, error) {
|
||||
return nil, err
|
||||
}
|
||||
return payload, nil
|
||||
case *appmessage.MsgRequestNextIBDRootUTXOSetChunk:
|
||||
payload := new(KaspadMessage_RequestNextIbdRootUtxoSetChunk)
|
||||
case *appmessage.MsgRequestNextPruningPointUTXOSetChunk:
|
||||
payload := new(KaspadMessage_RequestNextPruningPointUtxoSetChunk)
|
||||
err := payload.fromAppMessage(message)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
return payload, nil
|
||||
case *appmessage.MsgDoneIBDRootUTXOSetChunks:
|
||||
payload := new(KaspadMessage_DoneIbdRootUtxoSetChunks)
|
||||
case *appmessage.MsgDonePruningPointUTXOSetChunks:
|
||||
payload := new(KaspadMessage_DonePruningPointUtxoSetChunks)
|
||||
err := payload.fromAppMessage(message)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
|
Loading…
x
Reference in New Issue
Block a user