Alert Source Discuss
🚧 Stagnant Standards Track: Core

EIP-2327: BEGINDATA 操作码

Authors Martin Lundfall (@MrChico)
Created 2019-10-28
Discussion Link https://ethereum-magicians.org/t/new-opcode-begindata/3727

简单总结

引入一个新的操作码 BEGINDATA,它表示合约的剩余字节应被视为数据而不是合约代码,并且不能被执行。

摘要

智能合约通常直接在合约字节码中有效地存储数据。 示例包括构造函数参数、常量变量、编译器元数据以及初始化阶段的合约运行时。 目前,此类数据与普通字节码没有区别,并且 EVM 解释器仍在分析 JUMPDEST。 此 EIP 在字节 0xb6 处引入了一个新的操作码 BEGINDATA,它将剩余的字节码标记为数据,向 EVM 解释器、静态分析工具和链浏览器表明剩余的字节不代表操作码。

动机

BEGINDATA 操作码之前已作为 EIP Subroutines and Static Jumps for the EVM EIP-615 的一部分提出,作为确定合约字节码中跳转表位置的一种方式。 这里它以自己的名义引入,以便将数据从合约的 JUMPDEST 分析中排除,从而不可能跳转到数据。 这使得静态分析工具更容易分析合约,允许反汇编程序、链浏览器和调试器不将数据显示为 INVALID 操作码的混乱,甚至可能对性能产生边际改进。 它还有助于可扩展性,因为它改进了来自其他链的交易的链上评估,因为代码是否符合特定模式的验证不需要进行完整的 jumpdest 分析来查看数据是否未被执行,因此不必符合该模式(由 optimism 项目使用)。 此外,它为诸如 EIP-1712 等建议铺平了道路,以禁止未使用的操作码、跳转表 EIP-615 以及禁止部署具有堆栈使用违规的合约的推测性提案。

规范

在计算合约的有效 JUMPDEST 时,一旦遇到第一个 BEGINDATA,就停止分析。 换句话说:跳转到任何等于或大于第一个 BEGINDATA 位置的代码位置都会导致 BAD_JUMP_DESTINATION 错误。 如果在合约执行期间遇到 BEGINDATA,则它具有与 STOP 相同的语义。 它使用 0 gas。

可以通过 CODECOPYEXTCODECOPY 访问 BEGINDATA 之后的字节。 BEGINDATA 不影响 CODESIZEEXTCODESIZE

理由

选择字节 0xb6 是为了与 EIP-615 对齐。 如果遇到 BEGINDATASTOP 的选择有些随意。 另一种选择是用 out-of-gas 错误中止执行。

向后兼容性

该提案不会更改任何现有合约,除非它们当前的行为依赖于未使用操作码的使用。

由于合约从一开始就一直在使用数据,因此从某种意义上说,所有合约都在使用未使用的操作码, 但他们必须以在执行期间跳过并跳过的方式使用数据。 Solidity 编译器从未生成过这样的代码。 必须评估以其他方式创建的合约 是否可能具有这样的代码结构。

测试用例

测试用例应包括: 1) 一个合约跳转到目标地址 X,其中 X 的 pc 值高于 BEGINDATA 操作码,并且 X 处的字节是 0x5b。 这应该会因 BAD_JUMP_DESTINATION 错误而失败。 2) 一个合约遇到 BEGINDATA 操作码(应停止执行当前调用帧)

实现

暂无。

版权

CC0 下放弃版权及相关权利。

Citation

Please cite this document as:

Martin Lundfall (@MrChico), "EIP-2327: BEGINDATA 操作码 [DRAFT]," Ethereum Improvement Proposals, no. 2327, October 2019. [Online serial]. Available: https://eips.ethereum.org/EIPS/eip-2327.