100 lines
4.4 KiB
Nim
100 lines
4.4 KiB
Nim
# Nimbus - Types and helpers used at the boundary of transactions/RPC and EVMC/EVM
|
|
#
|
|
# Copyright (c) 2019-2021 Status Research & Development GmbH
|
|
# Licensed under either of
|
|
# * Apache License, version 2.0, ([LICENSE-APACHE](LICENSE-APACHE) or http://www.apache.org/licenses/LICENSE-2.0)
|
|
# * MIT license ([LICENSE-MIT](LICENSE-MIT) or http://opensource.org/licenses/MIT)
|
|
# at your option. This file may not be copied, modified, or distributed except according to those terms.
|
|
|
|
import
|
|
sets, stint, evmc/evmc, eth/common/eth_types, ../vm_types
|
|
|
|
# Object `TransactionHost` represents "EVMC host" to the EVM. "Host services"
|
|
# manage account state outside EVM such as balance transfers, storage, logs and
|
|
# gas refunds. This object holds transaction state hidden from the EVM, and
|
|
# the EVM passes this around as opaque `evmc_host_context`. To the application
|
|
# outside the EVM, this object represents a computation for a transaction.
|
|
#
|
|
# `Host..` types are like EVMC types, but used in `TransactionHost` code. They
|
|
# occupy the same positions in EVMC functions and objects as the type they map
|
|
# to/from. But `Host..` types match internal APIs in the rest of Nimbus, to
|
|
# minimise the amount of explicit conversions when using them. We could just
|
|
# use the Nimbus types, but these names document their use and also role.
|
|
#
|
|
# `Evmc..` types named here are actual EVMC types. They play a similar role to
|
|
# `Host..` types, except the `Evmc` prefix indicates they are the actual EVMC
|
|
# types and more care applies. Byte order (big/little-endian) may need to be
|
|
# swapped in object fields of these types, and enums respected.
|
|
#
|
|
# When crossing the EVMC API boundary, between internal APIs and EVMC binary
|
|
# interface there have to be type-conversions and some big/little-endian byte
|
|
# swapping. Those conversions are mostly kept out of `TransactionHost` logic
|
|
# and delegated to glue code.
|
|
|
|
type
|
|
HostAddress* = EthAddress # Mapped to/from evmc_address.
|
|
HostKey* = UInt256 # Mapped to/from evmc_bytes32.
|
|
HostValue* = UInt256 # Mapped to/from evmc_bytes32.
|
|
HostBalance* = UInt256 # Mapped to/from evmc_uint256be.
|
|
HostSize* = uint # Mapped to/from csize_t - unsigned!
|
|
HostHash* = Hash256 # Mapped to/from evmc_bytes32.
|
|
HostTopic* = Topic # Mapped to/from evmc_bytes32.
|
|
HostBlockNumber* = BlockNumber # Mapped to/from int64.
|
|
HostGasInt* = GasInt # Mapped to/from int64.
|
|
HostGasPrice* = GasInt # Mapped to/from evmc_uint256be.
|
|
|
|
EvmcStatusCode* = evmc_status_code
|
|
EvmcCallKind* = evmc_call_kind
|
|
EvmcStorageStatus* = evmc_storage_status
|
|
EvmcAccessStatus* = evmc_access_status
|
|
EvmcTxContext* = evmc_tx_context
|
|
EvmcMessage* = evmc_message
|
|
EvmcResult* = evmc_result
|
|
|
|
TransactionHost* = ref object
|
|
vmState*: BaseVMState
|
|
computation*: Computation
|
|
msg*: EvmcMessage
|
|
input*: seq[byte]
|
|
code*: seq[byte]
|
|
cachedTxContext*: bool
|
|
txContext*: EvmcTxContext
|
|
depth*: int
|
|
saveComputation*: seq[Computation]
|
|
hostInterface*: ptr evmc_host_interface
|
|
|
|
# These versions of `toEvmc` and `fromEvmc` don't flip big/little-endian like
|
|
# the older functions in `evmc_helpers`. New code only flips with _explicit_
|
|
# calls to `flip256` where it is wanted.
|
|
|
|
template toEvmc*(n: UInt256): evmc_uint256be =
|
|
cast[evmc_uint256be](n)
|
|
|
|
template toEvmc*(n: Hash256): evmc_bytes32 =
|
|
cast[evmc_bytes32](n)
|
|
|
|
template toEvmc*(address: EthAddress): evmc_address =
|
|
cast[evmc_address](address)
|
|
|
|
template fromEvmc*(n: evmc_uint256be): UInt256 =
|
|
cast[UInt256](n)
|
|
|
|
template fromEvmc*(address: evmc_address): EthAddress =
|
|
cast[EthAddress](address)
|
|
|
|
template flip256*(word256: evmc_uint256be): evmc_uint256be =
|
|
cast[evmc_uint256be](UInt256.fromBytesBE(word256.bytes).toBytes(cpuEndian))
|
|
|
|
template isCreate*(kind: EvmcCallKind): bool =
|
|
kind in {EVMC_CREATE, EVMC_CREATE2}
|
|
|
|
template isZero*(n: evmc_bytes32): bool =
|
|
n == default(evmc_bytes32)
|
|
|
|
# Nim quirks: Exporting `evmc_status_code` (etc) are needed to access the enum
|
|
# values, even though alias `EnumStatusCode` is already exported. Exporting
|
|
# `evmc_flags` won't export the flags, `evmc_flag_bit_shifts` must be used.
|
|
export
|
|
evmc_status_code, evmc_call_kind,
|
|
evmc_flag_bit_shifts, evmc_storage_status, evmc_access_status
|