github.com/MetalBlockchain/metalgo@v1.11.9/snow/engine/snowman/block/vm.go (about)

     1  // Copyright (C) 2019-2024, Ava Labs, Inc. All rights reserved.
     2  // See the file LICENSE for licensing terms.
     3  
     4  package block
     5  
     6  import (
     7  	"context"
     8  
     9  	"github.com/MetalBlockchain/metalgo/ids"
    10  	"github.com/MetalBlockchain/metalgo/snow/consensus/snowman"
    11  	"github.com/MetalBlockchain/metalgo/snow/engine/common"
    12  )
    13  
    14  // ChainVM defines the required functionality of a Snowman VM.
    15  //
    16  // A Snowman VM is responsible for defining the representation of state,
    17  // the representation of operations on that state, the application of operations
    18  // on that state, and the creation of the operations. Consensus will decide on
    19  // if the operation is executed and the order operations are executed in.
    20  //
    21  // For example, suppose we have a VM that tracks an increasing number that
    22  // is agreed upon by the network.
    23  // The state is a single number.
    24  // The operation is setting the number to a new, larger value.
    25  // Applying the operation will save to the database the new value.
    26  // The VM can attempt to issue a new number, of larger value, at any time.
    27  // Consensus will ensure the network agrees on the number at every block height.
    28  type ChainVM interface {
    29  	common.VM
    30  
    31  	Getter
    32  	Parser
    33  
    34  	// Attempt to create a new block from data contained in the VM.
    35  	//
    36  	// If the VM doesn't want to issue a new block, an error should be
    37  	// returned.
    38  	BuildBlock(context.Context) (snowman.Block, error)
    39  
    40  	// Notify the VM of the currently preferred block.
    41  	//
    42  	// This should always be a block that has no children known to consensus.
    43  	SetPreference(ctx context.Context, blkID ids.ID) error
    44  
    45  	// LastAccepted returns the ID of the last accepted block.
    46  	//
    47  	// If no blocks have been accepted by consensus yet, it is assumed there is
    48  	// a definitionally accepted block, the Genesis block, that will be
    49  	// returned.
    50  	LastAccepted(context.Context) (ids.ID, error)
    51  
    52  	// GetBlockIDAtHeight returns:
    53  	// - The ID of the block that was accepted with [height].
    54  	// - database.ErrNotFound if the [height] index is unknown.
    55  	//
    56  	// Note: A returned value of [database.ErrNotFound] typically means that the
    57  	//       underlying VM was state synced and does not have access to the
    58  	//       blockID at [height].
    59  	GetBlockIDAtHeight(ctx context.Context, height uint64) (ids.ID, error)
    60  }
    61  
    62  // Getter defines the functionality for fetching a block by its ID.
    63  type Getter interface {
    64  	// Attempt to load a block.
    65  	//
    66  	// If the block does not exist, database.ErrNotFound should be returned.
    67  	//
    68  	// It is expected that blocks that have been successfully verified should be
    69  	// returned correctly. It is also expected that blocks that have been
    70  	// accepted by the consensus engine should be able to be fetched. It is not
    71  	// required for blocks that have been rejected by the consensus engine to be
    72  	// able to be fetched.
    73  	GetBlock(ctx context.Context, blkID ids.ID) (snowman.Block, error)
    74  }
    75  
    76  // Parser defines the functionality for fetching a block by its bytes.
    77  type Parser interface {
    78  	// Attempt to create a block from a stream of bytes.
    79  	//
    80  	// The block should be represented by the full byte array, without extra
    81  	// bytes.
    82  	//
    83  	// It is expected for all historical blocks to be parseable.
    84  	ParseBlock(ctx context.Context, blockBytes []byte) (snowman.Block, error)
    85  }