types

package
v0.35.10-crescendo-pre... Latest Latest
Warning

This package is not in the latest version of its module.

Go to latest
Published: May 30, 2024 License: AGPL-3.0 Imports: 23 Imported by: 10

Documentation

Index

Constants

View Source
const (
	// tx type 255 is used for direct calls from COAs
	DirectCallTxType = byte(255)

	UnknownCallSubType  = byte(0)
	DepositCallSubType  = byte(1)
	WithdrawCallSubType = byte(2)
	TransferCallSubType = byte(3)
	DeployCallSubType   = byte(4)
	ContractCallSubType = byte(5)

	// Note that these gas values might need to change if we
	// change the transaction (e.g. add accesslist),
	// then it has to be updated to use Intrinsic function
	// to calculate the minimum gas needed to run the transaction.
	IntrinsicFeeForTokenTransfer = gethParams.TxGas

	// 21_000 is the minimum for a transaction + max gas allowed for receive/fallback methods
	DefaultGasLimitForTokenTransfer = IntrinsicFeeForTokenTransfer + 2_300

	// the value is set to the gas limit for transfer to facilitate transfers
	// to smart contract addresses.
	DepositCallGasLimit  = DefaultGasLimitForTokenTransfer
	WithdrawCallGasLimit = DefaultGasLimitForTokenTransfer
)
View Source
const (
	EventTypeBlockExecuted       flow.EventType = "EVM.BlockExecuted"
	EventTypeTransactionExecuted flow.EventType = "EVM.TransactionExecuted"
)
View Source
const AddressLength = gethCommon.AddressLength

AddressLength holds the number of bytes used for each EVM address

View Source
const COAAddressTemplate = "A.%v.EVM.CadenceOwnedAccountCreated"
View Source
const CadenceOwnedAccountCreatedTypeAddressFieldName = "address"
View Source
const FlowEVMSpecialAddressPrefixLen = 12

FlowEVMSpecialAddressPrefixLen captures the number of prefix bytes with constant values for special accounts (extended precompiles and COAs).

The prefix length should insure a high-enough level of security against finding a preimage using the hash function used for EVM addresses generation (Keccak256). This is required to avoid finding an EVM address that is also a valid FlowEVM address. The target (minimal) security in this case is the security level provided by EVM addresses. Since EVM addresses are 160-bits long, they offer only 80 bits of security (collision resistance offers the lowest level). A preimage resistance of 80 bits requires the prefix to be at least 80-bits long (i.e 10 bytes). When used as a prefix in EVM addresses (20-bytes long), a prefix length of 12 bytes leaves a variable part of 8 bytes (64 bits).

View Source
const InvalidTransactionGasCost = 1_000

InvalidTransactionGasCost is a gas cost we charge when a transaction or call fails at validation step. in typical evm environment this doesn't exist given if a transaction is invalid it won't be included and no fees can be charged for users even though the validation has used some resources, in our case given we charge the fees on flow transaction and we are doing on chain validation we can/should charge the user for the validation fee.

Variables

View Source
var (
	// Using leading zeros for prefix helps with the storage compactness.
	//
	// Prefix for the built-in EVM precompiles
	FlowEVMNativePrecompileAddressPrefix = [FlowEVMSpecialAddressPrefixLen]byte{0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}
	// Prefix for the extended precompiles
	FlowEVMExtendedPrecompileAddressPrefix = [FlowEVMSpecialAddressPrefixLen]byte{0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1}
	// Prefix for the COA addresses
	FlowEVMCOAAddressPrefix = [FlowEVMSpecialAddressPrefixLen]byte{0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 2}
)
View Source
var (
	AttoScale                      = 18
	UFixedScale                    = fixedpoint.Fix64Scale
	UFixedToAttoConversionScale    = AttoScale - UFixedScale
	UFixToAttoConversionMultiplier = new(big.Int).Exp(big.NewInt(10), big.NewInt(int64(UFixedToAttoConversionScale)), nil)

	OneFlowInUFix64 = cadence.UFix64(uint64(math.Pow(10, float64(UFixedScale))))
	OneFlowBalance  = Balance(new(big.Int).Exp(big.NewInt(10), big.NewInt(int64(AttoScale)), nil))
	EmptyBalance    = Balance(new(big.Int))
)
View Source
var (
	FlowEVMPreviewNetChainID = big.NewInt(646)
	FlowEVMTestNetChainID    = big.NewInt(545)
	FlowEVMMainNetChainID    = big.NewInt(747)
)
View Source
var (
	DefaultDirectCallBaseGasUsage = uint64(21_000)
	DefaultDirectCallGasPrice     = uint64(0)

	// anything block number above 0 works here
	BlockNumberForEVMRules = big.NewInt(1)
)
View Source
var (
	// ErrInvalidBalance is returned when an invalid balance is provided for transfer (e.g. negative)
	ErrInvalidBalance = errors.New("invalid balance for transfer")

	// ErrInsufficientComputation is returned when not enough computation is
	// left in the context of flow transaction to execute the evm operation.
	ErrInsufficientComputation = errors.New("insufficient computation")

	// ErrUnAuthroizedMethodCall method call, usually emited when calls are called on EOA accounts
	ErrUnAuthroizedMethodCall = errors.New("unauthroized method call")

	// ErrInternalDirecCallFailed is returned when a withdraw or deposit internal call has failed.
	ErrInternalDirectCallFailed = errors.New("internal direct call execution failed")

	// ErrWithdrawBalanceRounding is returned when withdraw call has a balance that could
	// yeild to rounding error, i.e. the balance contains fractions smaller than 10^8 Flow (smallest unit allowed to transfer).
	ErrWithdrawBalanceRounding = errors.New("withdraw failed! the balance is susceptible to the rounding error")

	// ErrUnexpectedEmptyResult is returned when a result is expected to be returned by the emulator
	// but nil has been returned. This should never happen and is a safety error.
	ErrUnexpectedEmptyResult = errors.New("unexpected empty result has been returned")

	// ErrInsufficientTotalSupply is returned when flow token
	// is withdraw request is there but not enough balance is on EVM vault
	// this should never happen but its a saftey measure to protect Flow against EVM issues.
	ErrInsufficientTotalSupply = NewFatalError(errors.New("insufficient total supply"))

	// ErrNotImplemented is a fatal error when something is called that is not implemented
	ErrNotImplemented = NewFatalError(errors.New("a functionality is called that is not implemented"))
)
View Source
var AddressBytesSemaType = sema.ByteArrayType
View Source
var EmptyAddress = Address(gethCommon.Address{})

EmptyAddress is an empty evm address

View Source
var FlowAddressCadenceType = cadence.AddressType
View Source
var FlowAddressSemaType = sema.TheAddressType
View Source
var GenesisBlock = &Block{
	ParentBlockHash: gethCommon.Hash{},
	Height:          uint64(0),
	TotalSupply:     new(big.Int),
	ReceiptRoot:     gethTypes.EmptyRootHash,
}

GenesisBlock is the genesis block in the EVM environment

View Source
var GenesisBlockHash, _ = GenesisBlock.Hash()
View Source
var KeyIndicesSemaType = &sema.VariableSizedType{Type: sema.UInt64Type}
View Source
var PublicPathCadenceType = cadence.PathType
View Source
var PublicPathSemaType = sema.PathType
View Source
var SignaturesSemaType = sema.ByteArrayArrayType
View Source
var SignedDataSemaType = sema.ByteArrayType

Functions

func BalanceConvertionToUFix64ProneToRoundingError added in v0.33.30

func BalanceConvertionToUFix64ProneToRoundingError(bal Balance) bool

BalanceConvertionToUFix64ProneToRoundingError returns true if casting to UFix64 could result in rounding error

func BalanceToBigInt added in v0.33.30

func BalanceToBigInt(bal Balance) *big.Int

BalanceToBigInt convert balance into big int

func COAOwnershipProofSignatureCountFromEncoded added in v0.33.30

func COAOwnershipProofSignatureCountFromEncoded(data []byte) (int, error)

func ConvertBalanceToUFix64 added in v0.33.30

func ConvertBalanceToUFix64(bal Balance) (value cadence.UFix64, roundedOff bool, err error)

ConvertBalanceToUFix64 casts the balance into a UFix64,

Warning! The smallest unit of Flow token that a FlowVault (Cadence) could store is 1e10^-8, so transfering smaller values (or values with smalls fractions) could result in loss in conversion. The rounded flag should be used to prevent loss of assets.

func EVMChainIDFromFlowChainID added in v0.33.30

func EVMChainIDFromFlowChainID(flowChainID flow.ChainID) *big.Int

func IsABackendError added in v0.33.30

func IsABackendError(err error) bool

IsABackendError returns true if the error or any underlying errors is a backend error

func IsACOAAddress added in v0.33.30

func IsACOAAddress(addr Address) bool

IsACOAAddress returns true if the address is a COA address

This test insures `addr` has been generated as a COA address with high probability. Brute forcing an EVM address `addr` to pass the `IsACOAAddress` test is as hard as the bit-length of `FlowEVMCOAAddressPrefix` (here 96 bits). Although this is lower than the protocol-wide security level in Flow (128 bits), it remains higher than the EVM addresses security (80 bits when considering collision attacks)

func IsAFatalError

func IsAFatalError(err error) bool

IsAFatalError returns true if the error or underlying error is of fatal type.

func IsAInsufficientTotalSupplyError

func IsAInsufficientTotalSupplyError(err error) bool

IsAInsufficientTotalSupplyError returns true if the error type is InsufficientTotalSupplyError

func IsAStateError

func IsAStateError(err error) bool

IsAStateError returns true if the error or any underlying errors is a state error

func IsAUnAuthroizedMethodCallError

func IsAUnAuthroizedMethodCallError(err error) bool

IsAUnAuthroizedMethodCallError returns true if the error type is UnAuthroizedMethodCallError

func IsAnExtendedPrecompileAddress added in v0.33.30

func IsAnExtendedPrecompileAddress(addr Address) bool

IsAnExtendedPrecompileAddress returns true if the address is a extended precompile address

func IsWithdrawBalanceRoundingError added in v0.33.30

func IsWithdrawBalanceRoundingError(err error) bool

IsWithdrawBalanceRoundingError returns true if the error type is ErrWithdrawBalanceRounding

Types

type Account

type Account interface {
	// Address returns the address of this account
	Address() Address

	// Balance returns the balance of this account
	Balance() Balance

	// Code returns the code of this account
	Code() Code

	// CodeHash returns the code hash of this account
	CodeHash() []byte

	// Nonce returns the nonce of this account
	Nonce() uint64

	// Deposit deposits the token from the given vault into this account
	Deposit(*FLOWTokenVault)

	// Withdraw withdraws the balance from account and
	// return it as a FlowTokenVault
	// works only for COAs
	Withdraw(Balance) *FLOWTokenVault

	// Transfer is a utility method on top of call for transfering tokens to another account
	Transfer(to Address, balance Balance)

	// Deploy deploys a contract to the environment
	// the new deployed contract would be at the returned
	// result address and the contract data is not controlled by the COA
	// works only for COAs
	Deploy(Code, GasLimit, Balance) *ResultSummary

	// Call calls a smart contract function with the given data.
	// The gas usage is limited by the given gas limit,
	// and the Flow transaction's computation limit.
	// The fees are deducted from the COA
	// and are transferred to the target address.
	// if no data is provided it would behave as transfering tokens to the
	// target address
	// works only for COAs
	Call(Address, Data, GasLimit, Balance) *ResultSummary
}

Account is an EVM account, currently three types of accounts are supported on Flow EVM, externally owned accounts (EOAs), smart contract accounts and cadence owned accounts Cadence-owned-account (COA) is a new type of account in the environment, that instead of being managed by public key, it is managed by a resource owned by a Flow account.

In other words, the FVM account who owns the FOA resource can bridge native tokens to and from the account associated with the COA, deploy contracts to the environment, or call methods on contracts without the need to sign a transaction.

type Address

type Address gethCommon.Address

Address is an EVM-compatible address

func COAAddressFromFlowCOACreatedEvent added in v0.33.30

func COAAddressFromFlowCOACreatedEvent(evmContractAddress flow.Address, event flow.Event) (Address, error)

func NewAddress

func NewAddress(addr gethCommon.Address) Address

NewAddress constructs a new Address

func NewAddressFromBytes

func NewAddressFromBytes(inp []byte) Address

NewAddressFromBytes constructs a new address from bytes

func NewAddressFromString

func NewAddressFromString(str string) Address

NewAddressFromString constructs a new address from an string

func (Address) Bytes

func (fa Address) Bytes() []byte

Bytes returns a byte slice for the address

func (Address) String added in v0.33.30

func (fa Address) String() string

String returns the hex encoding of the address it returns empty string if address is empty

func (Address) ToCadenceValue added in v0.33.30

func (a Address) ToCadenceValue() cadence.Array

func (Address) ToCommon

func (fa Address) ToCommon() gethCommon.Address

ToCommon returns the geth address

type AddressAllocator

type AddressAllocator interface {
	// AllocateAddress allocates an address to be used by a COA resource
	AllocateCOAAddress(uuid uint64) Address

	// COAFactoryAddress returns the address for the COA factory
	COAFactoryAddress() Address

	// NativeTokenBridgeAddress returns the address for the native token bridge
	// used for deposit and withdraw calls
	NativeTokenBridgeAddress() Address

	// AllocateAddress allocates an address by index to be used by a precompile contract
	AllocatePrecompileAddress(index uint64) Address
}

AddressAllocator allocates addresses, used by the handler

type Backend

Backend provides a subset of the FVM environment functionality Any error returned by a Backend is expected to be a `FatalError` or a `BackendError`.

type BackendError added in v0.33.30

type BackendError struct {
	// contains filtered or unexported fields
}

BackendError is a non-fatal error wraps errors returned from the backend

func NewBackendError added in v0.33.30

func NewBackendError(rootCause error) BackendError

NewBackendError returns a new BackendError

func (BackendError) Error added in v0.33.30

func (err BackendError) Error() string

func (BackendError) Unwrap added in v0.33.30

func (err BackendError) Unwrap() error

Unwrap unwraps the underlying evm error

type Balance

type Balance *big.Int

Balance represents the balance of an address in the evm environment (Flow EVM), balances are kept in attoflow (1e-18 flow); the smallest denomination of FLOW token (similar to how Wei is used to store Eth) But A Cadence FLOW Vault uses a Cadence.UFix64 to store values in Flow, which means 1e-8 is the smallest value that can be stored on the vault. The balance here considers the highest precision (attoflow) but utility function has been provided for conversion from/to UFix64 to prevent accidental conversion errors and dealing with rounding errors.

func AddBalance added in v0.33.30

func AddBalance(bal1 Balance, bal2 Balance) (Balance, error)

AddBalance balance 2 to balance 1 and returns the result as a new balance

func CopyBalance added in v0.33.30

func CopyBalance(inp Balance) Balance

CopyBalance creates a copy of the balance

func MakeABalanceInFlow added in v0.33.30

func MakeABalanceInFlow(amount uint64) Balance

MakeABalanceInFlow makes a balance object that has `amount` Flow Token in it

func NewBalance added in v0.33.30

func NewBalance(inp *big.Int) Balance

NewBalanceconstructs a new balance from an atto flow value

func NewBalanceFromUFix64 added in v0.33.30

func NewBalanceFromUFix64(inp cadence.UFix64) Balance

NewBalanceFromUFix64 constructs a new balance from flow value (how its stored in Cadence Flow)

func SubBalance added in v0.33.30

func SubBalance(bal1 Balance, bal2 Balance) (Balance, error)

Subtract balance 2 from balance 1 and returns the result as a new balance

type BaseView

type BaseView interface {
	ReadOnlyView

	// Creates a new account
	CreateAccount(
		addr gethCommon.Address,
		balance *big.Int,
		nonce uint64,
		code []byte,
		codeHash gethCommon.Hash,
	) error

	// UpdateAccount updates a account
	UpdateAccount(
		addr gethCommon.Address,
		balance *big.Int,
		nonce uint64,
		code []byte,
		codeHash gethCommon.Hash,
	) error

	// DeleteAccount deletes an account
	DeleteAccount(addr gethCommon.Address) error

	// UpdateSlot updates the value for the given slot in the main storage
	UpdateSlot(
		slot SlotAddress,
		value gethCommon.Hash,
	) error

	// Commit commits the changes
	Commit() error
}

BaseView is a low-level mutable view of the state baseview is usually updated at the commit calls to the higher level view

type Block

type Block struct {
	// the hash of the parent block
	ParentBlockHash gethCommon.Hash

	// Height returns the height of this block
	Height uint64

	// Timestamp is a Unix timestamp in seconds at which the block was created
	// Note that this value must be provided from the FVM Block
	Timestamp uint64

	// holds the total amount of the native token deposited in the evm side. (in attoflow)
	TotalSupply *big.Int

	// ReceiptRoot returns the root hash of the receipts emitted in this block
	// Note that this value won't be unique to each block, for example for the
	// case of empty trie of receipts or a single receipt with no logs and failed state
	// the same receipt root would be reported for block.
	ReceiptRoot gethCommon.Hash

	// transaction hashes
	TransactionHashes []gethCommon.Hash

	// stores gas used by all transactions included in the block.
	TotalGasUsed uint64
}

Block represents a evm block. It captures block info such as height and state

func NewBlock

func NewBlock(
	parentBlockHash gethCommon.Hash,
	height uint64,
	timestamp uint64,
	totalSupply *big.Int,
	receiptRoot gethCommon.Hash,
	txHashes []gethCommon.Hash,
) *Block

NewBlock constructs a new block

func NewBlockFromBytes

func NewBlockFromBytes(encoded []byte) (*Block, error)

NewBlockFromBytes constructs a new block from encoded data

func (*Block) AppendTxHash

func (b *Block) AppendTxHash(txHash gethCommon.Hash)

AppendTxHash appends a transaction hash to the list of transaction hashes of the block

func (*Block) CalculateGasUsage added in v0.33.30

func (b *Block) CalculateGasUsage(results []Result)

CalculateGasUsage sums up all the gas transactions in the block used

func (*Block) Hash

func (b *Block) Hash() (gethCommon.Hash, error)

Hash returns the hash of the block

func (*Block) PopulateReceiptRoot added in v0.33.30

func (b *Block) PopulateReceiptRoot(results []*Result)

PopulateReceiptRoot populates receipt root with the given results

func (*Block) ToBytes

func (b *Block) ToBytes() ([]byte, error)

ToBytes encodes the block into bytes

type BlockContext

type BlockContext struct {
	ChainID                *big.Int
	BlockNumber            uint64
	BlockTimestamp         uint64
	DirectCallBaseGasUsage uint64
	DirectCallGasPrice     uint64
	GasFeeCollector        Address
	GetHashFunc            func(n uint64) gethCommon.Hash
	Random                 gethCommon.Hash

	// a set of extra precompiles to be injected
	ExtraPrecompiles []Precompile
}

BlockContext holds the context needed for the emulator operations

func NewDefaultBlockContext

func NewDefaultBlockContext(BlockNumber uint64) BlockContext

NewDefaultBlockContext returns a new default block context

type BlockEventPayload added in v0.33.30

type BlockEventPayload struct {
	Height            uint64           `cadence:"height"`
	Hash              string           `cadence:"hash"`
	Timestamp         uint64           `cadence:"timestamp"`
	TotalSupply       cadence.Int      `cadence:"totalSupply"`
	TotalGasUsed      uint64           `cadence:"totalGasUsed"`
	ParentBlockHash   string           `cadence:"parentHash"`
	ReceiptRoot       string           `cadence:"receiptRoot"`
	TransactionHashes []cadence.String `cadence:"transactionHashes"`
}

func DecodeBlockEventPayload added in v0.33.30

func DecodeBlockEventPayload(event cadence.Event) (*BlockEventPayload, error)

DecodeBlockEventPayload decodes Cadence event into block event payload.

type BlockHashList added in v0.33.30

type BlockHashList struct {
	// contains filtered or unexported fields
}

BlockHashList holds the last `capacity` number of block hashes in the list

func NewBlockHashList added in v0.33.30

func NewBlockHashList(capacity int) *BlockHashList

NewBlockHashList constructs a new block hash list of the given capacity

func NewBlockHashListFromEncoded added in v0.33.30

func NewBlockHashListFromEncoded(encoded []byte) (*BlockHashList, error)

func (*BlockHashList) BlockHashByHeight added in v0.33.30

func (bhl *BlockHashList) BlockHashByHeight(height uint64) (found bool, bh gethCommon.Hash)

BlockHashByIndex returns the block hash by block height

func (*BlockHashList) Encode added in v0.33.30

func (bhl *BlockHashList) Encode() []byte

func (*BlockHashList) IsEmpty added in v0.33.30

func (bhl *BlockHashList) IsEmpty() bool

IsEmpty returns true if the list is empty

func (*BlockHashList) LastAddedBlockHash added in v0.33.30

func (bhl *BlockHashList) LastAddedBlockHash() gethCommon.Hash

LastAddedBlockHash returns the last block hash added to the list for empty list it returns empty hash value

func (*BlockHashList) MaxAvailableHeight added in v0.33.30

func (bhl *BlockHashList) MaxAvailableHeight() uint64

MaxAvailableHeight returns the max available height in the list

func (*BlockHashList) MinAvailableHeight added in v0.33.30

func (bhl *BlockHashList) MinAvailableHeight() uint64

MinAvailableHeight returns the min available height in the list

func (*BlockHashList) Push added in v0.33.30

func (bhl *BlockHashList) Push(height uint64, bh gethCommon.Hash) error

Push pushes a block hash for the next height to the list. If the list is full, it overwrites the oldest element.

type BlockStore

type BlockStore interface {
	// LatestBlock returns the latest appended block
	LatestBlock() (*Block, error)

	// BlockHash returns the hash of the block at the given height
	BlockHash(height uint64) (gethCommon.Hash, error)

	// BlockProposal returns the block proposal
	BlockProposal() (*Block, error)

	// CommitBlockProposal commits the block proposal and update the chain of blocks
	CommitBlockProposal() error

	// ResetBlockProposal resets the block proposal
	ResetBlockProposal() error
}

BlockStore stores the chain of blocks

type BlockView

type BlockView interface {
	// DirectCall executes a direct call
	DirectCall(call *DirectCall) (*Result, error)

	// RunTransaction executes an evm transaction
	RunTransaction(tx *gethTypes.Transaction) (*Result, error)

	// DryRunTransaction executes unsigned transaction but does not persist the state changes,
	// since transaction is not signed, from address is used as the signer.
	DryRunTransaction(tx *gethTypes.Transaction, from gethCommon.Address) (*Result, error)

	// BatchRunTransactions executes a batch of evm transactions producing
	// a slice of execution Result where each result corresponds to each
	// item in the txs slice.
	BatchRunTransactions(txs []*gethTypes.Transaction) ([]*Result, error)
}

BlockView facilitates execution of a transaction or a direct evm call in the context of a block Any error returned by any of the methods (e.g. stateDB errors) if non-fatal stops the outer flow transaction if fatal stops the node. EVM validation errors and EVM execution errors are part of the returned result and should be handled separately.

type COAOwnershipProof added in v0.33.30

type COAOwnershipProof struct {
	KeyIndices     KeyIndices
	Address        FlowAddress
	CapabilityPath PublicPath
	Signatures     Signatures
}

COAOwnershipProof is a proof that a flow account controls a COA resource. To do so, the flow account (Address is address of this account) provides signatures (with proper total weights) over an arbitary data input set by proof requester. KeyIndicies captures, which account keys has been used for signatures. Beside signatures, it provides the CapabilityPath where the resource EVMAddress capability is stored.

func COAOwnershipProofFromEncoded added in v0.33.30

func COAOwnershipProofFromEncoded(data []byte) (*COAOwnershipProof, error)

func (*COAOwnershipProof) Encode added in v0.33.30

func (p *COAOwnershipProof) Encode() ([]byte, error)

type COAOwnershipProofInContext added in v0.33.30

type COAOwnershipProofInContext struct {
	COAOwnershipProof
	SignedData SignedData
	EVMAddress Address
}

COAOwnershipProofInContext contains all the data needed to verify a COAOwnership proof. The proof is verified by checking the signatures over the input signed data (SignedData), then loading the resource capability from the provided path in the proof, and at last checking if the EVMAddress of the resource matches the provided one.

func NewCOAOwnershipProofInContext added in v0.33.30

func NewCOAOwnershipProofInContext(sd []byte, addr Address, encodedProof []byte) (*COAOwnershipProofInContext, error)

func (*COAOwnershipProofInContext) ToCadenceValues added in v0.33.30

func (proof *COAOwnershipProofInContext) ToCadenceValues() []cadence.Value

type Code

type Code []byte

type ContractHandler

type ContractHandler interface {
	// DeployCOA deploys a Cadence owned account and return the address
	DeployCOA(uuid uint64) Address

	// AccountByAddress returns an account by address
	// if isAuthorized is set, it allows for functionality like `call`, `deploy`
	// should only be set for the cadence owned accounts only.
	AccountByAddress(address Address, isAuthorized bool) Account

	// LastExecutedBlock returns information about the last executed block
	LastExecutedBlock() *Block

	// Run runs a transaction in the evm environment,
	// collects the gas fees, and transfers the gas fees to the given coinbase account.
	Run(tx []byte, coinbase Address) *ResultSummary

	// DryRun simulates execution of the provided RLP-encoded and unsigned transaction.
	// Because the transaction is unsigned the from address is required, since
	// from address is normally derived from the transaction signature.
	// The function should not have any persisted changes made to the state.
	DryRun(tx []byte, from Address) *ResultSummary

	// BatchRun runs transaction batch in the evm environment,
	// collect all the gas fees and transfers the gas fees to the given coinbase account.
	BatchRun(txs [][]byte, coinbase Address) []*ResultSummary

	// FlowTokenAddress returns the address where FLOW token is deployed
	FlowTokenAddress() common.Address

	// EVMContractAddress returns the address where EVM is deployed
	EVMContractAddress() common.Address

	// GenerateResourceUUID generates a new UUID for a resource
	GenerateResourceUUID() uint64
}

ContractHandler handles operations on the evm environment

type Data

type Data []byte

func (Data) AsBigInt

func (d Data) AsBigInt() *big.Int

AsBigInt process the data and return it as a big integer

type DirectCall

type DirectCall struct {
	Type     byte
	SubType  byte
	From     Address
	To       Address
	Data     []byte
	Value    *big.Int
	GasLimit uint64
	Nonce    uint64
}

DirectCall captures all the data related to a direct call to evm direct calls are similar to transactions but they don't have signatures and don't need sequence number checks Note that eventhough we don't check the nonce, it impacts hash calculation and also impacts the address of resulting contract when deployed through direct calls. Users don't have the worry about the nonce, handler sets it to the right value.

func DirectCallFromEncoded added in v0.33.30

func DirectCallFromEncoded(encoded []byte) (*DirectCall, error)

DirectCallFromEncoded constructs a DirectCall from encoded data

func NewContractCall

func NewContractCall(
	caller Address,
	to Address,
	data Data,
	gasLimit uint64,
	value *big.Int,
	nonce uint64,
) *DirectCall

func NewDeployCall

func NewDeployCall(
	caller Address,
	code Code,
	gasLimit uint64,
	value *big.Int,
	nonce uint64,
) *DirectCall

func NewDeployCallWithTargetAddress added in v0.33.30

func NewDeployCallWithTargetAddress(
	caller Address,
	to Address,
	code Code,
	gasLimit uint64,
	value *big.Int,
	nonce uint64,
) *DirectCall

this subtype should only be used internally for deploying contracts at given addresses (e.g. COA account init setup) should not be used for other means.

func NewDepositCall

func NewDepositCall(
	bridge Address,
	address Address,
	amount *big.Int,
	nonce uint64,
) *DirectCall

func NewTransferCall

func NewTransferCall(
	from Address,
	to Address,
	amount *big.Int,
	nonce uint64,
) *DirectCall

func NewWithdrawCall

func NewWithdrawCall(
	bridge Address,
	address Address,
	amount *big.Int,
	nonce uint64,
) *DirectCall

func (*DirectCall) EmptyToField added in v0.33.30

func (dc *DirectCall) EmptyToField() bool

EmptyToField returns true if `to` field contains an empty address

func (*DirectCall) Encode

func (dc *DirectCall) Encode() ([]byte, error)

Encode encodes the direct call it also adds the type as the very first byte, similar to how evm encodes types.

func (*DirectCall) Hash

func (dc *DirectCall) Hash() (gethCommon.Hash, error)

Hash computes the hash of a direct call

func (*DirectCall) Message

func (dc *DirectCall) Message() *gethCore.Message

Message constructs a core.Message from the direct call

func (*DirectCall) Transaction added in v0.33.30

func (dc *DirectCall) Transaction() *gethTypes.Transaction

Transaction constructs a geth.Transaction from the direct call

type Emulator

type Emulator interface {
	// constructs a new block view
	NewReadOnlyBlockView(ctx BlockContext) (ReadOnlyBlockView, error)

	// constructs a new block
	NewBlockView(ctx BlockContext) (BlockView, error)
}

Emulator emulates an evm-compatible chain

type ErrorCode added in v0.33.30

type ErrorCode uint16
const (
	ErrCodeNoError ErrorCode = 0

	// covers all other validation codes that doesn't have an specific code
	ValidationErrCodeMisc ErrorCode = 100

	// general execution error returned for cases that don't have an specific code
	ExecutionErrCodeMisc ErrorCode = 400
)

internal error codes

const (
	// the nonce of the tx is lower than the expected
	ValidationErrCodeNonceTooLow ErrorCode = iota + 201
	// the nonce of the tx is higher than the expected
	ValidationErrCodeNonceTooHigh
	// tx sender account has reached to the maximum nonce
	ValidationErrCodeNonceMax
	// not enough gas is available on the block to include this transaction
	ValidationErrCodeGasLimitReached
	// the transaction sender doesn't have enough funds for transfer(topmost call only).
	ValidationErrCodeInsufficientFundsForTransfer
	// creation transaction provides the init code bigger than init code size limit.
	ValidationErrCodeMaxInitCodeSizeExceeded
	// the total cost of executing a transaction is higher than the balance of the user's account.
	ValidationErrCodeInsufficientFunds
	// overflow detected when calculating the gas usage
	ValidationErrCodeGasUintOverflow
	// the transaction is specified to use less gas than required to start the invocation.
	ValidationErrCodeIntrinsicGas
	// the transaction is not supported in the current network configuration.
	ValidationErrCodeTxTypeNotSupported
	// tip was set to higher than the total fee cap
	ValidationErrCodeTipAboveFeeCap
	// an extremely big numbers is set for the tip field
	ValidationErrCodeTipVeryHigh
	// an extremely big numbers is set for the fee cap field
	ValidationErrCodeFeeCapVeryHigh
	// the transaction fee cap is less than the base fee of the block
	ValidationErrCodeFeeCapTooLow
	// the sender of a transaction is a contract
	ValidationErrCodeSenderNoEOA
	// the transaction fee cap is less than the blob gas fee of the block.
	ValidationErrCodeBlobFeeCapTooLow
)

geth evm core errors (reserved range: [201-300) )

const (
	// execution ran out of gas
	ExecutionErrCodeOutOfGas ErrorCode = iota + 301
	// contract creation code storage out of gas
	ExecutionErrCodeCodeStoreOutOfGas
	// max call depth exceeded
	ExecutionErrCodeDepth
	// insufficient balance for transfer
	ExecutionErrCodeInsufficientBalance
	// contract address collision"
	ExecutionErrCodeContractAddressCollision
	// execution reverted
	ExecutionErrCodeExecutionReverted
	// max initcode size exceeded
	ExecutionErrCodeMaxInitCodeSizeExceeded
	// max code size exceeded
	ExecutionErrCodeMaxCodeSizeExceeded
	// invalid jump destination
	ExecutionErrCodeInvalidJump
	// write protection
	ExecutionErrCodeWriteProtection
	// return data out of bounds
	ExecutionErrCodeReturnDataOutOfBounds
	// gas uint64 overflow
	ExecutionErrCodeGasUintOverflow
	// invalid code: must not begin with 0xef
	ExecutionErrCodeInvalidCode
	// nonce uint64 overflow
	ExecutionErrCodeNonceUintOverflow
)

evm execution errors (reserved range: [301-400) )

func ExecutionErrorCode added in v0.33.30

func ExecutionErrorCode(err error) ErrorCode

func ValidationErrorCode added in v0.33.30

func ValidationErrorCode(err error) ErrorCode

type Event

type Event struct {
	Etype   flow.EventType
	Payload EventPayload
}

func NewBlockEvent added in v0.33.30

func NewBlockEvent(block *Block) *Event

NewBlockEvent creates a new block event with the given block as payload.

func NewTransactionEvent added in v0.33.30

func NewTransactionEvent(
	result *Result,
	payload []byte,
	blockHeight uint64,
	blockHash gethCommon.Hash,
) *Event

NewTransactionEvent creates a new transaction event with the given parameters - result: the result of the transaction execution - payload: the RLP-encoded payload of the transaction - blockHeight: the height of the block where the transaction is included - blockHash: the hash of the block where the transaction is included

type EventPayload

type EventPayload interface {
	// ToCadence converts the event to Cadence event
	ToCadence(location common.Location) (cadence.Event, error)
}

type FLOWTokenVault

type FLOWTokenVault struct {
	// contains filtered or unexported fields
}

FLOWTokenVault holds a balance of flow token

func NewFlowTokenVault

func NewFlowTokenVault(balance Balance) *FLOWTokenVault

func (*FLOWTokenVault) Balance

func (t *FLOWTokenVault) Balance() Balance

func (*FLOWTokenVault) Deposit

func (t *FLOWTokenVault) Deposit(inp *FLOWTokenVault) error

func (*FLOWTokenVault) Withdraw

func (t *FLOWTokenVault) Withdraw(b Balance) (*FLOWTokenVault, error)

type FatalError

type FatalError struct {
	// contains filtered or unexported fields
}

FatalError is used for any error that is not user related and something unusual has happend. Usually we stop the node when this happens given it might have a non-deterministic root.

func NewFatalError

func NewFatalError(rootCause error) FatalError

NewFatalError returns a new FatalError

func (FatalError) Error

func (err FatalError) Error() string

func (FatalError) Unwrap

func (err FatalError) Unwrap() error

Unwrap unwraps the underlying fatal error

type FlowAddress added in v0.33.30

type FlowAddress flow.Address

func (FlowAddress) ToCadenceValue added in v0.33.30

func (addr FlowAddress) ToCadenceValue() cadence.Address

type GasLimit

type GasLimit uint64

type HotView

type HotView interface {
	ReadOnlyView

	// CreateAccount creates a new account
	CreateAccount(gethCommon.Address) error
	// SelfDestruct set the flag for destruction of the account after execution
	SelfDestruct(gethCommon.Address) error

	// SubBalance subtracts the amount from the balance the given address
	SubBalance(gethCommon.Address, *big.Int) error
	// AddBalance adds the amount to the balance of the given address
	AddBalance(gethCommon.Address, *big.Int) error
	// SetNonce sets the nonce for the given address
	SetNonce(gethCommon.Address, uint64) error
	// SetCode sets the code for the given address
	SetCode(gethCommon.Address, []byte) error

	// SetState sets a value for the given slot in the main storage
	SetState(SlotAddress, gethCommon.Hash) error
	// SetTransientState sets a value for the given slot in the transient storage
	SetTransientState(SlotAddress, gethCommon.Hash)

	// AddRefund adds the amount to the total (gas) refund
	AddRefund(uint64) error
	// SubRefund subtracts the amount from the total (gas) refund
	SubRefund(uint64) error

	// AddAddressToAccessList adds an address to the per-transaction access list
	AddAddressToAccessList(addr gethCommon.Address) (addressAdded bool)
	// AddSlotToAccessList adds a slot to the per-transaction access list
	AddSlotToAccessList(SlotAddress) (addressAdded, slotAdded bool)

	// AddLog append a log to the log collection
	AddLog(*gethTypes.Log)
	// AddPreimage adds a preimage to the list of preimages (input -> hash mapping)
	AddPreimage(gethCommon.Hash, []byte)
}

HotView captures a high-level mutable view of the state

type KeyIndices added in v0.33.30

type KeyIndices []uint64

func (KeyIndices) Count added in v0.33.30

func (ki KeyIndices) Count() int

func (KeyIndices) ToCadenceValue added in v0.33.30

func (ki KeyIndices) ToCadenceValue() cadence.Array

type Precompile added in v0.33.30

type Precompile interface {
	gethVM.PrecompiledContract
	Address() Address
}

type PublicPath added in v0.33.30

type PublicPath string

func (PublicPath) ToCadenceValue added in v0.33.30

func (p PublicPath) ToCadenceValue() cadence.Path

type ReadOnlyBlockView

type ReadOnlyBlockView interface {
	// BalanceOf returns the balance of this address
	BalanceOf(address Address) (*big.Int, error)
	// NonceOf returns the nonce of this address
	NonceOf(address Address) (uint64, error)
	// CodeOf returns the code for this address
	CodeOf(address Address) (Code, error)
	// CodeHashOf returns the code hash for this address
	CodeHashOf(address Address) ([]byte, error)
}

ReadOnlyBlockView provides a read only view of a block

type ReadOnlyView

type ReadOnlyView interface {
	// Exist returns true if the address exist in the state
	Exist(gethCommon.Address) (bool, error)
	// IsCreated returns true if address has been created in this tx
	IsCreated(gethCommon.Address) bool
	// HasSelfDestructed returns true if an address has self destructed
	// it also returns the balance of address before selfdestruction call
	HasSelfDestructed(gethCommon.Address) (bool, *big.Int)
	// GetBalance returns the balance of an address
	GetBalance(gethCommon.Address) (*big.Int, error)
	// GetNonce returns the nonce of an address
	GetNonce(gethCommon.Address) (uint64, error)
	// GetCode returns the code of an address
	GetCode(gethCommon.Address) ([]byte, error)
	// GetCodeHash returns the code hash of an address
	GetCodeHash(gethCommon.Address) (gethCommon.Hash, error)
	// GetCodeSize returns the code size of an address
	GetCodeSize(gethCommon.Address) (int, error)
	// GetState returns values for an slot in the main storage
	GetState(SlotAddress) (gethCommon.Hash, error)
	// GetTransientState returns values for an slot transient storage
	GetTransientState(SlotAddress) gethCommon.Hash
	// GetRefund returns the total amount of (gas) refund
	GetRefund() uint64
	// AddressInAccessList checks if an address is in the access list
	AddressInAccessList(gethCommon.Address) bool
	// SlotInAccessList checks if a slot is in the access list
	SlotInAccessList(SlotAddress) (addressOk bool, slotOk bool)
}

ReadOnlyView provides a readonly view of the state

type Result

type Result struct {
	// captures error returned during validation step (pre-checks)
	ValidationError error
	// captures error returned by the EVM
	VMError error
	// type of transaction defined by the evm package
	// see DirectCallTxType as extra type we added type for direct calls.
	TxType uint8
	// total gas consumed during an opeartion
	GasConsumed uint64
	// the address where the contract is deployed (if any)
	DeployedContractAddress *Address
	// returned value from a function call
	ReturnedValue []byte
	// EVM logs (events that are emited by evm)
	Logs []*gethTypes.Log
	// TX hash holdes the cached value of tx hash
	TxHash gethCommon.Hash
	// transaction block inclusion index
	Index uint16
}

Result captures the result of an interaction to the emulator it could be the output of a direct call or output of running an evm transaction. Its more comprehensive than typical evm receipt, usually the receipt generation requires some extra calculation (e.g. Deployed contract address) but we take a different apporach here and include more data so that it requires less work for anyone who tracks and consume results.

func NewInvalidResult added in v0.33.30

func NewInvalidResult(tx *gethTypes.Transaction, err error) *Result

NewInvalidResult creates a new result that hold transaction validation error as well as the defined gas cost for validation.

func (*Result) Failed

func (res *Result) Failed() bool

Failed returns true if transaction has been executed but VM has returned some error

func (*Result) Invalid added in v0.33.30

func (res *Result) Invalid() bool

Invalid returns true if transaction has been rejected

func (*Result) Receipt

func (res *Result) Receipt() *gethTypes.Receipt

Receipt constructs an EVM-style receipt can be used by json-rpc and other integration to be returned.

This is method is also used to construct block receipt root hash which requires the return receipt satisfy RLP encoding and cover these feilds Type (txType), PostState or Status, CumulativeGasUsed, Logs and Logs Bloom and for each log, Address, Topics, Data (consensus fields) During execution we also do fill in BlockNumber, TxIndex, Index (event index)

func (*Result) ResultSummary added in v0.33.30

func (res *Result) ResultSummary() *ResultSummary

ResultSummary constructs a result summary

func (*Result) SetValidationError added in v0.33.30

func (res *Result) SetValidationError(err error)

SetValidationError sets the validation error and also sets the gas used to the fixed invalid gas usage

func (*Result) VMErrorString added in v0.33.30

func (res *Result) VMErrorString() string

returns the VM error as an string, if no error it returns an empty string

type ResultSummary added in v0.33.30

type ResultSummary struct {
	Status                  Status
	ErrorCode               ErrorCode
	GasConsumed             uint64
	DeployedContractAddress *Address
	ReturnedValue           Data
}

ResultSummary summerizes the outcome of a EVM call or tx run

type Signature added in v0.33.30

type Signature []byte

func (Signature) ToCadenceValue added in v0.33.30

func (s Signature) ToCadenceValue() cadence.Array

type Signatures added in v0.33.30

type Signatures []Signature

func (Signatures) Count added in v0.33.30

func (ss Signatures) Count() int

func (Signatures) ToCadenceValue added in v0.33.30

func (ss Signatures) ToCadenceValue() cadence.Array

type SignedData added in v0.33.30

type SignedData []byte

func (SignedData) ToCadenceValue added in v0.33.30

func (sd SignedData) ToCadenceValue() cadence.Array

type SlotAddress

type SlotAddress struct {
	Address gethCommon.Address
	Key     gethCommon.Hash
}

SlotAddress captures an address to a storage slot

type StateDB

type StateDB interface {
	gethVM.StateDB

	// Commit commits the changes
	// setting `finalize` flag
	// calls a subsequent call to Finalize
	// defering finalization and calling it once at the end
	// improves efficiency of batch operations.
	Commit(finalize bool) error

	// Finalize flushes all the changes
	// to the permanent storage
	Finalize() error

	// Logs collects and prepares logs
	Logs(
		blockNumber uint64,
		txHash gethCommon.Hash,
		txIndex uint,
	) []*gethTypes.Log

	// Preimages returns a map of preimages
	Preimages() map[gethCommon.Hash][]byte

	// Reset resets uncommitted changes and transient artifacts such as error, logs,
	// preimages, access lists, ...
	// The method is often called between execution of different transactions
	Reset()
}

StateDB acts as the main interface to the EVM runtime

type StateError

type StateError struct {
	// contains filtered or unexported fields
}

StateError is a non-fatal error, returned when a state operation has failed (e.g. reaching storage interaction limit)

func NewStateError

func NewStateError(rootCause error) StateError

NewStateError returns a new StateError

func (StateError) Error

func (err StateError) Error() string

func (StateError) Unwrap

func (err StateError) Unwrap() error

Unwrap unwraps the underlying evm error

type Status added in v0.33.30

type Status uint8

Status captures the status of an interaction to the emulator

var (
	StatusUnknown Status = 0
	// StatusInvalid shows that the transaction was not a valid
	// transaction and rejected to be executed and included in any block.
	StatusInvalid Status = 1
	// StatusFailed shows that the transaction has been executed,
	// but the output of the execution was an error
	// for this case a block is formed and receipts are available
	StatusFailed Status = 2
	// StatusSuccessful shows that the transaction has been executed and the execution has returned success
	// for this case a block is formed and receipts are available
	StatusSuccessful Status = 3
)

type TransactionEventPayload added in v0.33.30

type TransactionEventPayload struct {
	Hash            string `cadence:"hash"`
	Index           uint16 `cadence:"index"`
	TransactionType uint8  `cadence:"type"`
	Payload         string `cadence:"payload"`
	ErrorCode       uint16 `cadence:"errorCode"`
	GasConsumed     uint64 `cadence:"gasConsumed"`
	ContractAddress string `cadence:"contractAddress"`
	Logs            string `cadence:"logs"`
	BlockHeight     uint64 `cadence:"blockHeight"`
	BlockHash       string `cadence:"blockHash"`
}

func DecodeTransactionEventPayload added in v0.33.30

func DecodeTransactionEventPayload(event cadence.Event) (*TransactionEventPayload, error)

DecodeTransactionEventPayload decodes Cadence event into transaction event payload.

Jump to

Keyboard shortcuts

? : This menu
/ : Search site
f or F : Jump to
y or Y : Canonical URL