Documentation
¶
Overview ¶
bootstrap_sync.go — the node-side wiring for INITIAL SYNC. The blockHandler is both the fetch transport (chainbootstrap.BlockSource) and the execute sink (chainbootstrap.Chain) the engine/chain/bootstrap loop drives, so an EMPTY or BEHIND node converges from its local last-accepted to the network frontier by fetch+execute (re-execute each fetched block; no vote, no cert). When the loop reaches the frontier the driver ENDS the engine's bootstrap phase (FinishBootstrap — only the α-of-K cert-gate finalizes thereafter) and flips bootstrapDone, the REAL ready signal monitorBootstrap gates the chain on. Decomplected from the live cert/vote path: when bsActive is false every method below is inert and the handler behaves exactly as it did before initial sync existed.
bootstrap_trust.go — the SEPARATE trust object for INITIAL SYNC, decomplected from consensus finality.
The mass-recovery DEADLOCK this fixes: the prior FrontierTip required a ⅔-by-stake quorum of the CURRENT total validator set to be CONNECTED before it would name a sync frontier. When the recovery TARGETS are themselves validators (a node that crashed IS one of the 5), taking them down drops connected stake below ⅔ of the whole set — so on a network of 5 equal-weight validators, losing 2 leaves 3 (60% < ⅔) and NO node can ever name a frontier to recover from. Bootstrap trust was braided into consensus finality, and finality's ⅔ rule is mathematically unsatisfiable during a mass outage.
The fix is a type split, NOT a renamed threshold. ConsensusQuorum decides FINALITY (> ⅔ of CURRENT stake — UNCHANGED). BootstrapTrust decides whether a fetched frontier is SAFE TO BEGIN SYNC FROM: a quorum of AUTHENTICATED CONFIGURED beacons that RESPOND, gated by a response FLOOR (MinResponses) and an agreement threshold over the RESPONDERS (not over the whole set). 3 of 5 reachable beacons all agreeing is a valid sync anchor even though 3 of 5 stake is not a finalizing supermajority. The two decisions have different threat models and are different objects.
pchain_height_vm.go — the node-layer boundary that delivers the REAL P-CHAIN EPOCH HEIGHT to the consensus chain engine (the b2 wiring; the LAST QUORUM_FINALITY blocker).
THE BUG IT FIXES. The chain engine pins a block's weighted validator set to a P-CHAIN height (engine/chain: pChainHeightOf → epochHeightLocked → the SINGLE height the set-root commitment, the ⅔-by-stake tally, AND the per-voter pubkey resolution are read at). It reads that height by asserting the VM block to a `PChainHeight() uint64` (consensus block.SignedBlock). A bare VM block — every block the node's plugin VMs (C-Chain EVM, dexvm, …) produce — does NOT expose one, so pChainHeightOf returns 0 and the engine resolves the set at P-chain height 0: the GENESIS set. That is SAFE (non-empty, identical on every node, ≤ current) and UNBRICKS finality, but it FREEZES the epoch at genesis: a validator that JOINED after genesis is absent from set@0, so its vote is dropped and its stake is not counted — finality cannot track a DYNAMIC validator set (a departed genesis majority could even collude). This is the frozen-set caveat Gate D must sign away.
THE FIX. pChainHeightVM wraps the chain's BlockBuilder (the VM the engine builds/parses blocks through) and makes the block the engine sees carry the proposer's P-chain epoch height — WITHOUT changing the inner VM's block format, IDs, or ledger state:
- BuildBlock (proposer): build the inner block, then stamp the proposer's live P-chain epoch height H = max(GetCurrentHeight, parentH) (the proposervm selectChildPChainHeight rule — monotone, ≤ current). Return a pChainHeightBlock whose Bytes() are [magic|H|innerBytes] and whose PChainHeight() is H. Every other method (ID, ParentID, Height, Verify, Accept, …) delegates to the inner block — so the block's IDENTITY and the VM's state are the inner VM's, unchanged.
- ParseBlock (follower): split [magic|H|innerBytes], parse the inner bytes through the inner VM, and re-attach H. Bytes WITHOUT the magic (a raw inner block from a pre-wrapper peer, GetAncestors, or genesis) parse with H=0 → the SAFE genesis-set fallback — never worse than today.
DETERMINISM is the whole point and is why H must travel IN the gossiped bytes. The engine gossips only blk.Bytes(); a follower recovers the block solely via ParseBlock(those bytes). The proposer STAMPS H; every follower ADOPTS the identical H from the envelope — it never recomputes H from its own (skewing) current P-chain view. So every honest node derives the SAME epoch height from the SAME signed block, which is the invariant the engine's cert verifier requires (engine/chain HandleIncomingCert cross-checks the cert's set-root against the set-root WE recompute at OUR epoch height for the block: equal H ⟹ equal root ⟹ the cert verifies; a post-genesis validator's vote+stake now count). A build-time-only stamp would give the proposer a real H but leave followers computing a DIFFERENT root from their own height → the cert is dropped → finality STALLS on a dynamic set (strictly worse than the genesis fallback). That is why the height is carried, not recomputed.
This is a consensus-TRANSPORT framing (an 8-byte height + 4-byte magic prefix on the gossiped bytes), NOT a chain/ledger fork: the inner VM's bytes, block IDs, and execution state are byte-identical, so there is no re-genesis — only a coordinated node upgrade (the whole validator set ships together).
quorum.go — the node-layer wiring that makes the consensus engine's α-of-K quorum-cert finality LIVE (HIGH-4). The consensus engine (luxfi/consensus engine/chain) defines the quorum RULE and the vote/cert topology interfaces; THIS file supplies the concrete node implementations the engine needs:
- blsVoteVerifier — verifies a validator's BLS signature over the canonical vote message against the chain's validator set (the engine is scheme- agnostic; the node injects BLS).
- blsVoteSigner — signs THIS node's accept votes with its staking BLS key so its signature can be collected into a cert.
- validatorStakeSource — supplies per-validator stake so finality is a ⅔-by-STAKE supermajority (HIGH-3), not a raw voter count.
- networkGossiper.BroadcastVote / GossipCert — the QuorumGossiper transport: a follower broadcasts its signed vote to ALL validators and any node that collects α distinct signed votes gossips the assembled cert, so finality never hinges on one node's inbound Chits (liveness; no proposer-freeze).
Inbound votes/certs arrive as app-gossip and are demuxed in blockHandler.Gossip (see manager.go) into engine.HandleIncomingVote / HandleIncomingCert.
Index ¶
- Constants
- Variables
- func NewLinearizeOnInitializeVM(vm consensusvertex.LinearizableVMWithEngine, toEngine chan<- vmcore.Message) *linearizeOnInitializeVM
- type AncestrySource
- type BeaconReply
- type BlockRef
- type BootstrapPolicy
- type BootstrapTrust
- type ChainConfig
- type ChainDBManager
- func (m *ChainDBManager) Close() error
- func (m *ChainDBManager) GetAllChainIDs() []ids.ID
- func (m *ChainDBManager) GetDatabase(chainID ids.ID, chainAlias string) (database.Database, error)
- func (m *ChainDBManager) GetDatabasePrefix(chainID ids.ID) []byte
- func (m *ChainDBManager) GetGlobalDB() database.Database
- func (m *ChainDBManager) GetVMDatabase(chainID ids.ID, chainAlias string) (database.Database, error)
- type ChainDBManagerConfig
- type ChainInfo
- type ChainParameters
- type ChainRouter
- type Checkpoint
- type ConsensusQuorum
- type Engine
- type Frontier
- type Manager
- type ManagerConfig
- type NFTAuthorization
- type Nets
- type QbitEvent
- type Ratio
- type Registrant
- type StakeWeight
Constants ¶
const (
ChainLabel = "chain"
)
Variables ¶
var ( // ErrInsufficientBootstrapResponses: fewer than MinResponses configured beacons answered. // Not a partition-capture-safe quorum — the node must keep waiting for more beacons (or use // an operator checkpoint), never sync from the captured few. INVARIANT 2's response floor. ErrInsufficientBootstrapResponses = errors.New("bootstrap: insufficient configured-beacon responses") // ErrNoBootstrapQuorum: enough beacons responded, but no block clears the agreement threshold // over the responders (a genuine partition, or a transient bleeding-edge split the loop retries). ErrNoBootstrapQuorum = errors.New("bootstrap: no responder-agreed frontier") )
var ( // corely shared VM DB prefix VMDBPrefix = []byte("vm") // Bootstrapping prefixes for LinearizableVMs VertexDBPrefix = []byte("vertex") VertexBootstrappingDBPrefix = []byte("vertex_bs") TxBootstrappingDBPrefix = []byte("tx_bs") BlockBootstrappingDBPrefix = []byte("interval_block_bs") // Bootstrapping prefixes for ChainVMs ChainBootstrappingDBPrefix = []byte("interval_bs") )
var ErrNoPrimaryNetworkConfig = errors.New("no net config for primary network found")
var ErrNotQuorumGossip = errors.New("chains: not a quorum gossip envelope")
ErrNotQuorumGossip signals a payload is not a quorum envelope (so the caller falls through to the block-gossip path).
var ( // ErrSkipped is returned when a linearizable VM is asked to perform // chain VM operations ErrSkipped = errors.New("skipped") )
Functions ¶
func NewLinearizeOnInitializeVM ¶ added in v0.1.1
func NewLinearizeOnInitializeVM(vm consensusvertex.LinearizableVMWithEngine, toEngine chan<- vmcore.Message) *linearizeOnInitializeVM
Types ¶
type AncestrySource ¶ added in v1.30.83
type AncestrySource interface {
// Ancestry returns up to max blocks ending at tip, parsed to (id, height, parent). An empty
// result (no error) means the tip's ancestry was not served — that anchor contributes nothing.
Ancestry(ctx context.Context, tip ids.ID, max int) ([]BlockRef, error)
}
AncestrySource resolves a tip's CONTENT-ADDRESSED ancestry for the ancestor-tolerant tally — the SAME parent-linked descent the sync loop trusts. Injected so the trust DECISION (which beacons count, the response floor, the agreement threshold) stays separate from the transport.
type BeaconReply ¶ added in v1.30.83
type BeaconReply struct {
NodeID ids.NodeID
Tip ids.ID
Weight StakeWeight
}
BeaconReply is one authenticated configured beacon's report of its accepted frontier tip during initial sync. NodeID is authenticated at the transport handshake (a peer cannot forge another's identity); Weight is the beacon's CONFIGURED stake from the trust anchor — NOT a self-reported value. A reply whose NodeID is not in the policy's TrustedBeacons is ignored.
type BlockRef ¶ added in v1.30.83
BlockRef is a parsed block's CONTENT-ADDRESSED identity (id, height, parent) — the only thing the ancestor-tolerant tally needs. Decouples the policy from the VM/block types.
type BootstrapPolicy ¶ added in v1.30.83
type BootstrapPolicy struct {
// TrustedBeacons is the trust anchor: configured-beacon NodeID → configured stake (INVARIANT
// 1). Resolved from --bootstrap-nodes / a finalized P-chain checkpoint / the genesis set —
// never from peer self-report.
TrustedBeacons map[ids.NodeID]StakeWeight
// AgreementThreshold is the fraction of the RESPONDER weight a named block must exceed
// (default 2/3). Over RESPONDERS, not the whole set — that is what permits mass recovery.
AgreementThreshold Ratio
// MinResponses is the FLOOR on distinct configured-beacon responders (INVARIANT 2). Default:
// a MAJORITY of the configured set (the largest floor that still lets a node recover when a
// minority of validators is down). Capped at the set size.
MinResponses int
// MinResponseWeight is an OPTIONAL floor on the total responder weight (0 ⇒ disabled).
MinResponseWeight StakeWeight
// MinResponders is the minimum DISTINCT beacons that must back a NAMED block (default 2), so a
// single beacon cannot alone name the frontier. Capped at the responder count.
MinResponders int
// MinFrontierHeight floors the height the ANCESTOR-TOLERANT path may name (the node's current
// last-accepted height). A common ancestor BELOW where the node already is means the beacons
// agree only on history the node has — a partition above, not a frontier ahead — so it is NOT
// named (→ ErrNoBootstrapQuorum, fail safe), never a false-complete at the stale height. The
// exact fast path is exempt: a tip a responder supermajority actively reports is a real
// frontier even when low (a genuinely fresh network).
MinFrontierHeight uint64
// Checkpoint is the OPTIONAL operator override for the below-floor case (INVARIANT 2). nil ⇒
// reject below the floor.
Checkpoint *Checkpoint
// NamingWindow bounds the ancestry fetched per anchor; MaxAnchors bounds how many distinct
// reported tips are resolved. Both default to the package constants when zero.
NamingWindow int
MaxAnchors int
// NamingTimeout TOTAL-bounds the ancestor-tolerant resolution (all anchor fetches combined) so
// a partition that ANSWERS the frontier query but WITHHOLDS ancestry cannot make the decision
// hang — it returns what it found (or nothing → ErrNoBootstrapQuorum) and the caller's bounded
// retry tries a fresh sample next round. Zero ⇒ the package default.
NamingTimeout time.Duration
// Source resolves content-addressed ancestry for the ancestor-tolerant tally. When nil, the
// policy decides on the exact fast path alone (no split resolution).
Source AncestrySource
}
BootstrapPolicy is the default BootstrapTrust: a CONFIGURED-BEACON quorum with a response FLOOR and an agreement threshold over the RESPONDERS — a SEPARATE object from ConsensusQuorum with a SEPARATE threat model. It does NOT pass "reachable stake" into the ⅔-of-current-stake finality rule (that conflation IS the mass-recovery deadlock). It reuses the ancestor-tolerant common-ancestor tally only for HOW to find the agreed frontier; the ACCEPTANCE gate is the response floor + responder agreement here.
The three invariants:
- INVARIANT 1 (non-circular beacon eligibility): only NodeIDs in TrustedBeacons count, and TrustedBeacons comes from the configured/checkpointed/genesis anchor — NEVER peer self-report. A recovering node never lets arbitrary peers define who is a beacon.
- INVARIANT 2 (a floor prevents partition-capture): MinResponses authenticated beacons must respond before any frontier is named; an attacker who partitions the node down to a few beacons cannot capture the frontier. Below the floor, REJECT (or use Checkpoint).
- INVARIANT 3 (acceptance ≠ finality): the named Frontier is "safe to begin sync from", not finalized. The node independently re-executes the descent before re-entering consensus.
func (*BootstrapPolicy) AcceptsFrontier ¶ added in v1.30.83
func (p *BootstrapPolicy) AcceptsFrontier(ctx context.Context, replies []BeaconReply) (*Frontier, error)
AcceptsFrontier implements BootstrapTrust. It (1) keeps ONLY configured-beacon replies (INVARIANT 1), (2) enforces the MinResponses / MinResponseWeight floor or falls back to the operator checkpoint (INVARIANT 2), then (3) names the highest block a responder supermajority shares via the ancestor-tolerant tally. It never consults the ⅔-of-current-stake finality rule (INVARIANT 3): the decision is the response floor + responder agreement, a separate threat model.
type BootstrapTrust ¶ added in v1.30.83
type BootstrapTrust interface {
// AcceptsFrontier returns the block an empty/behind node may BEGIN SYNCING FROM, selected
// from the authenticated configured beacons' frontier replies — or an error
// (ErrInsufficientBootstrapResponses / ErrNoBootstrapQuorum) when no trusted frontier can be
// named this round. The returned Frontier is a sync ANCHOR, never a consensus certificate
// (see the type comment): the node must still re-execute every block it descends to before
// re-entering live consensus, where ConsensusQuorum alone governs acceptance.
AcceptsFrontier(ctx context.Context, replies []BeaconReply) (*Frontier, error)
}
BootstrapTrust is not a consensus-finality oracle. It selects a weak-subjective sync frontier from authenticated configured beacons. Live block acceptance remains governed exclusively by ConsensusQuorum.
type ChainConfig ¶ added in v0.1.1
ChainConfig is configuration settings for the current execution. [Config] is the user-provided config blob for the chain. [Upgrade] is a chain-specific blob for coordinating upgrades.
type ChainDBManager ¶ added in v1.16.56
type ChainDBManager struct {
// contains filtered or unexported fields
}
ChainDBManager manages chain database access using a single global ZapDB. All chains share one ZapDB instance with prefix-based isolation: 1. Single database - easier to manage, backup, and query across chains 2. Prefix isolation - each chain's data is prefixed by its chainID 3. G-Chain compatible - dgraph can index the entire database for GraphQL queries
func NewChainDBManager ¶ added in v1.16.56
func NewChainDBManager(config ChainDBManagerConfig) *ChainDBManager
NewChainDBManager creates a new chain database manager using a single global ZapDB
func (*ChainDBManager) Close ¶ added in v1.16.56
func (m *ChainDBManager) Close() error
Close is a no-op since the global database lifecycle is managed elsewhere. Chain-specific prefixed databases don't need to be closed separately.
func (*ChainDBManager) GetAllChainIDs ¶ added in v1.16.56
func (m *ChainDBManager) GetAllChainIDs() []ids.ID
GetAllChainIDs returns all chain IDs that have databases allocated. Useful for G-Chain to enumerate chains for indexing.
func (*ChainDBManager) GetDatabase ¶ added in v1.16.56
GetDatabase returns a prefixed database for the given chain. Uses prefix-based isolation on the single global ZapDB.
func (*ChainDBManager) GetDatabasePrefix ¶ added in v1.16.56
func (m *ChainDBManager) GetDatabasePrefix(chainID ids.ID) []byte
GetDatabasePrefix returns the prefix used for a chain's data. This is the chainID bytes, which can be used by G-Chain to iterate chain data.
func (*ChainDBManager) GetGlobalDB ¶ added in v1.16.56
func (m *ChainDBManager) GetGlobalDB() database.Database
GetGlobalDB returns the underlying global database. This is useful for G-Chain (dgraph-powered GraphQL VM) to query across all chains.
func (*ChainDBManager) GetVMDatabase ¶ added in v1.16.56
func (m *ChainDBManager) GetVMDatabase(chainID ids.ID, chainAlias string) (database.Database, error)
GetVMDatabase returns a VM-prefixed database for the given chain. Adds a "vm" prefix within the chain's prefix for VM-specific data.
type ChainDBManagerConfig ¶ added in v1.16.56
type ChainDBManagerConfig struct {
// DB is the global shared database (ZapDB)
DB database.Database
Log log.Logger
}
ChainDBManagerConfig holds configuration for the chain database manager
type ChainInfo ¶ added in v1.24.29
type ChainInfo struct {
ID ids.ID `json:"id"`
Name string `json:"name"`
VMID ids.ID `json:"vmID"`
Bootstrapped bool `json:"bootstrapped"`
}
ChainInfo is the public view of a locally running chain. Returned by Manager.GetChains() and exposed via info.GetChains API.
type ChainParameters ¶
type ChainParameters struct {
// The ID of the blockchain being created.
ID ids.ID
// ID of the Net that validates this blockchain.
ChainID ids.ID
// The genesis data of this blockchain's ledger.
GenesisData []byte
// The ID of the vm this blockchain is running.
VMID ids.ID
// The IDs of the feature extensions this blockchain is running.
FxIDs []ids.ID
// Invariant: Only used when [ID] is the P-chain ID.
CustomBeacons validators.Manager
// Name of the chain (used for HTTP routing alias, e.g., /ext/bc/zoo/rpc)
Name string
}
ChainParameters defines the chain being created
type ChainRouter ¶ added in v1.16.56
type ChainRouter interface {
AddChain(ctx context.Context, chainID ids.ID, handler handler.Handler)
}
ChainRouter is the interface for routing messages to chains. This is defined here to avoid circular imports with the node package.
type Checkpoint ¶ added in v1.30.83
Checkpoint is an operator-pinned (id, height) the recovering node may anchor to when too few beacons respond to form a quorum — the EXPLICIT override for INVARIANT 2's "1 of N reachable" case. Absent (nil) ⇒ the default policy REJECTS rather than trusting a captured minority.
type ConsensusQuorum ¶ added in v1.30.83
type ConsensusQuorum interface {
HasFinality(weight, total StakeWeight) bool
}
ConsensusQuorum decides FINALITY: whether a weight is a finalizing supermajority (> ⅔) of the CURRENT validator set. This is the live-consensus rule; bootstrap does NOT change it. It is a SEPARATE named type from BootstrapTrust precisely so the distinction is explicit and testable: a frontier that AcceptsFrontier admits is "safe to sync from", and in general it does NOT satisfy HasFinality (3 of 5 responders is a valid sync anchor; 3 of 5 stake is not finality).
func DefaultConsensusQuorum ¶ added in v1.30.83
func DefaultConsensusQuorum() ConsensusQuorum
DefaultConsensusQuorum returns the live ⅔-of-current-stake finality rule — the thing bootstrap trust is explicitly NOT. Used by the test suite to prove a bootstrap-accepted frontier does not constitute finality.
type Engine ¶ added in v1.11.14
type Engine interface {
Start(context.Context, bool) error
StopWithError(context.Context, error) error
Context() context.Context
}
Engine represents a consensus engine
type Frontier ¶ added in v1.30.83
type Frontier struct {
ID ids.ID
Height uint64
Weight StakeWeight // responder stake whose accepted chain contains this block
Responders int // distinct configured beacons that backed it
FromCheckpoint bool // selected from an operator checkpoint (too few beacons responded)
}
Frontier is the weak-subjective sync anchor BootstrapTrust selects: the block a node descends to and re-executes. It is NOT a consensus certificate (see BootstrapTrust). Height is the tallied height when named via the ancestor-tolerant path, and 0 (unknown) when named via the exact fast path before any ancestry fetch — the sync loop uses ID; Height is diagnostic.
type Manager ¶
type Manager interface {
ids.Aliaser
// Queues a chain to be created in the future after chain creator is unblocked.
// This is only called from the P-chain thread to create other chains
// Queued chains are created only after P-chain is bootstrapped.
// This assumes only chains in tracked chains are queued.
QueueChainCreation(ChainParameters)
// Add a registrant [r]. Every time a chain is
// created, [r].RegisterChain([new chain]) is called.
AddRegistrant(Registrant)
// Given an alias, return the ID of the chain associated with that alias
Lookup(string) (ids.ID, error)
// Given an alias, return the ID of the VM associated with that alias
LookupVM(string) (ids.ID, error)
// Returns true iff the chain with the given ID exists and is finished bootstrapping
IsBootstrapped(ids.ID) bool
// Starts the chain creator with the initial platform chain parameters, must
// be called once.
StartChainCreator(platformChain ChainParameters) error
// GetChains returns info about all locally running chains.
GetChains() []ChainInfo
// RetryPendingChains re-queues chains that were waiting for the specified VM.
// This is called when a VM is hot-loaded via admin.loadVMs.
RetryPendingChains(vmID ids.ID) int
// GetPendingChains returns the chain parameters waiting for a VM to be loaded.
GetPendingChains(vmID ids.ID) []ChainParameters
Shutdown()
}
Manager manages the chains running on this node. It can:
- Create a chain
- Add a registrant. When a chain is created, each registrant calls RegisterChain with the new chain as the argument.
- Manage the aliases of chains
var TestManager Manager = testManager{}
TestManager implements Manager but does nothing. Always returns nil error. To be used only in tests
type ManagerConfig ¶ added in v0.1.1
type ManagerConfig struct {
SybilProtectionEnabled bool
StakingTLSSigner crypto.Signer
StakingTLSCert *staking.Certificate
StakingBLSKey bls.Signer
TracingEnabled bool
// Must not be used unless [TracingEnabled] is true as this may be nil.
Tracer trace.Tracer
Log log.Logger
LogFactory log.Factory
VMManager vms.Manager // Manage mappings from vm ID --> vm
BlockAcceptorGroup nodeconsensus.AcceptorGroup
TxAcceptorGroup nodeconsensus.AcceptorGroup
VertexAcceptorGroup nodeconsensus.AcceptorGroup
DB database.Database
MsgCreator message.OutboundMsgBuilder // message creator, shared with network
Router ChainRouter // Routes incoming messages to the appropriate chain
Net network.Network // Sends consensus messages to other validators
Validators validators.Manager // Validators validating on this chain
NodeID ids.NodeID // The ID of this node
NetworkID uint32 // ID of the network this node is connected to
PartialSyncPrimaryNetwork bool
Server server.Server // Handles HTTP API calls
AtomicMemory *atomic.Memory
UTXOAssetID ids.ID
SkipBootstrap bool // Skip bootstrapping and start processing immediately
EnableAutomining bool // Enable automining in POA mode
XChainID ids.ID // ID of the X-Chain,
CChainID ids.ID // ID of the C-Chain,
DChainID ids.ID // ID of the D-Chain (DEX),
CriticalChains set.Set[ids.ID] // Chains that can't exit gracefully
// ChainAuthorizations gates per-validator activation of specific chains on
// X-Chain NFT ownership: a validator may track/validate a listed chain
// only if its staking X-address (StakingXAddress) holds the required
// nftfx NFT. A nil/empty map means no chain is NFT-gated, so every chain
// behaves exactly as before. Critical chains are never gated regardless of
// this map. Node wiring (e.g. DChainID -> dex-validator collection) is set
// in node.go; see authorizeChainActivation.
ChainAuthorizations map[ids.ID]NFTAuthorization
// StakingXAddress is this node's X-Chain address derived from its staking
// keys; it is the owner whose UTXOs the NFT-authorization gate inspects.
// Empty when no chain is gated; an empty address with a gated chain causes
// that chain to be opted out (fail closed).
StakingXAddress ids.ShortID
// DexValidator is the operator's opt-in to PARTICIPATE in the D-Chain DEX
// (track/validate it + dial the venue matcher). It is a NECESSARY condition
// for D-Chain activation that composes AND-wise with the NFT gate: the
// D-Chain (DChainID) activates only if DexValidator is true AND the NFT
// requirement (if any) is satisfied. Default false means a node does NOT
// activate the D-Chain even when it is queued by --track-all-chains; the
// activation authority is authorizeChainActivation, not the platformvm
// tracking set. Only the D-Chain consults this flag; every other chain is
// untouched. Sourced from node Config.DexValidator (see node.go).
DexValidator bool
TimeoutManager timeout.Manager // Manages request timeouts when sending messages to other validators
Health health.Registerer
NetConfigs map[ids.ID]nets.Config // ID -> NetConfig
ChainConfigs map[string]ChainConfig // alias -> ChainConfig
// ShutdownNodeFunc allows the chain manager to issue a request to shutdown the node
ShutdownNodeFunc func(exitCode int)
MeterVMEnabled bool // Should each VM be wrapped with a MeterVM
Metrics metrics.MultiGatherer
MeterDBMetrics metrics.MultiGatherer
FrontierPollFrequency time.Duration
ConsensusAppConcurrency int
// Max Time to spend fetching a container and its
// ancestors when responding to a GetAncestors
BootstrapMaxTimeGetAncestors time.Duration
// Max number of containers in an ancestors message sent by this node.
BootstrapAncestorsMaxContainersSent int
// This node will only consider the first [AncestorsMaxContainersReceived]
// containers in an ancestors message it receives.
BootstrapAncestorsMaxContainersReceived int
Upgrades upgrade.Config
// Tracks CPU/disk usage caused by each peer.
ResourceTracker timetracker.ResourceTracker
StateSyncBeacons []ids.NodeID
ChainDataDir string
Nets *Nets
// SecurityProfile is the chain-wide ChainSecurityProfile resolved
// from the genesis pin during node bootstrap (F102). The chain
// manager forwards a ProfileID + ProfileHash pin to every VM
// Initialize call via the VM config bytes so the rpcchainvm plugin
// (coreth C-Chain) inherits the chain-wide posture without
// re-resolving genesis. Closes red-team finding F118.
//
// Nil under classical-compat or pre-locked-profile chains; the
// stamping pass is a no-op in that case.
SecurityProfile *consensusconfig.ChainSecurityProfile
}
type NFTAuthorization ¶ added in v1.30.16
type NFTAuthorization struct {
AssetID ids.ID // X-Chain nftfx asset (the collection)
GroupID uint32 // nftfx group within the collection; 0 = any group
}
NFTAuthorization identifies the X-Chain NFT a validator's staking address must hold to activate (track/validate) a gated chain.
A chain is "gated" when ManagerConfig.ChainAuthorizations has an entry for its blockchain ID. Chains with no entry are ungated and always authorized — so a nil/empty ChainAuthorizations map preserves today's behavior exactly for every chain (P/C/X/Q/D/…).
type Nets ¶ added in v1.16.56
type Nets struct {
// contains filtered or unexported fields
}
Nets holds the currently running chains on this node
func (*Nets) Bootstrapping ¶ added in v1.16.56
Bootstrapping returns the chainIDs of any chains that are still bootstrapping.
type QbitEvent ¶ added in v1.22.81
type QbitEvent struct {
From ids.NodeID // The node that sent the Qbit
BlockID ids.ID // The block being signaled (preferredID)
RequestID uint32 // Request ID for dedup and stale detection
ReceivedAt time.Time // When the Qbit was received
}
QbitEvent is the normalized internal representation of a received Qbit message. This is pure data - no VM calls, no Verify, no Accept derivation. Vote creation happens separately in applyQbit when the block is available.
type Ratio ¶ added in v1.30.83
type Ratio struct{ Num, Den uint64 }
Ratio is an exact rational threshold (e.g. 2/3, 3/4). A value clears it iff value > floorOf(whole) — strictly greater, matching the consensus ⅔ floor's semantics.
type Registrant ¶
type Registrant interface {
// Called when a chain is created
// This function is called before the chain starts processing messages
// [vm] should be a vertex.DAGVM or block.ChainVM
RegisterChain(chainName string, rt *runtime.Runtime, vm vm.VM)
}
Registrant can register the existence of a chain
type StakeWeight ¶ added in v1.30.83
type StakeWeight = uint64
StakeWeight is validator stake in the units the validator manager reports (Weight/Light).