EIP-2003: 用于预编译合约实现的 EVMC 模块
Authors | Paweł Bylica (@chfast), Alex Beregszaszi (@axic) |
---|---|
Created | 2019-05-09 |
Discussion Link | https://github.com/ethereum/evmc/issues/259 |
Requires | EIP-1352 |
摘要
EVMC 为以太坊执行引擎指定了一个通用的 API。 此 EIP 指定了一种使用 EVMC VM API 提供以太坊预编译合约实现的方法。
规范
有关完整的 EVMC 规范,请首先访问 EVMC documentation。 此 EIP 基于 EVMC ABI 版本 6 并且与之兼容。
具有预编译合约实现的 EVMC 模块应该:
-
在
get_capabilities()
方法中声明EVMC_CAPABILITY_PRECOMPILES
功能。 -
以下列方式实现
execute()
方法:-
验证传入的执行请求要求:
-
消息类型 (
evmc_message::kind
) 是调用 (EVMC_CALL
)。 -
调用目标地址 (
evmc_message::destination
) 在 EIP-1352 定义的预编译合约范围内。 -
没有提供代码(
code
参数为NULL
,code_size
参数为0
)。
如果未满足要求,则使用
EVMC_REJECTED
状态代码中止执行。 -
-
检查调用目标地址 (
evmc_message::destination
) 是否指向现有的预编译合约。 考虑execute()
的rev
参数请求的 EVM 修订版本 (evmc_revision
)。如果是,则按如下方式执行:
-
检查输入数据 (
evmc_message::input_data
,evmc_message::input_size
) 并计算执行的 gas cost。 -
通过从调用 gas 限制 (
evmc_message::gas
) 中减去 gas cost 来计算执行后剩余的 gas left。 -
如果 gas left 为负数, 则使用
EVMC_OUT_OF_GAS
状态代码中止执行。 -
否则, 执行预编译合约的代码, 返回
EVMC_SUCCESS
状态代码、输出和 gas left (evmc_result::output_data
,evmc_result::output_size
,evmc_result::gas_left
)。
-
-
否则,通过返回
EVMC_SUCCESS
状态代码 和等于调用 gas 限制的 gas left (evmc_message::gas
) 来模拟空代码的执行。
-
允许预编译合约实现返回另外两个 EVMC 错误代码:
EVMC_FAILURE
,如果失败是由 gas 不足以外的原因引起的(例如,输入验证错误)EVMC_REVERT
,如果预编译不想放弃所有提供的 gas(截至 2019 年 5 月,不存在此类预编译)
客户端不需要提供 Host 接口(execute()
的 [evmc_context
] 参数设置为 NULL)。
因此,预编译合约实现绝对不能访问 evmc_context
。
理由
任何预编译合约都不太可能需要访问或修改合约状态。 不要求客户端实现 EVMC Host 接口消除了完全 EVMC 集成所需的大部分工作。
测试用例
EVMC 提供了 evmc-vmtester 工具,用于检查与 EVMC 规范的兼容性。
实现
- 预编译 VM 实现示例
- ewasm precompiles
- 用于预编译的 Aleth 代码
- 用于预编译的 Parity 代码
- 作为 EVMC 预编译模块实现的 EIP-1962
参考
- EVMC – Ethereum Client-VM Connector API
- EVMC documentation
- EVMC VM Implementation Guide
- EIP 1352: 指定预编译/系统合约的受限地址范围
版权
通过 CC0 放弃版权及相关权利。
Citation
Please cite this document as:
Paweł Bylica (@chfast), Alex Beregszaszi (@axic), "EIP-2003: 用于预编译合约实现的 EVMC 模块 [DRAFT]," Ethereum Improvement Proposals, no. 2003, May 2019. [Online serial]. Available: https://eips.ethereum.org/EIPS/eip-2003.