EIP-6466: SSZ 回执
将 RLP 回执迁移到 SSZ
Authors | Etan Kissling (@etan-status), Gajinder Singh (@g11tech), Vitalik Buterin (@vbuterin) |
---|---|
Created | 2023-02-08 |
Discussion Link | https://ethereum-magicians.org/t/eip-6466-ssz-receipts/12884 |
Requires | EIP-658, EIP-2718, EIP-6404, EIP-7702 |
Table of Contents
摘要
本 EIP 定义了将 EIP-2718 递归长度前缀 (RLP) 回执迁移到 Simple Serialize (SSZ) 的过程。
动机
RLP 回执存在许多缺点:
-
有限的证明支持: 由于回执数据在线性哈希后作为
receipts_root
Merkle-Patricia Trie (MPT) 的一部分,因此无法有效地证明回执的各个部分,例如日志。 需要提供完整的回执数据对于基于智能合约的应用程序(如 L2 欺诈证明或验证日志数据的客户端应用程序)来说可能代价过高。 -
不必要的有状态性: EIP-658 将回执中的中间后状态
root
替换为布尔值status
代码。 但是,cumulativeGasUsed
同样是有状态的,不必要地复杂化了并行执行交易的工作。 此外,验证单个交易使用的有效 gas 需要多个回执。 -
不完整的数据: JSON-RPC 为回执提供
from
、gasUsed
和contractAddress
字段,但链上回执不包含验证它们所需的的信息。 -
低效的日志布隆: 由于其高误报率,日志布隆机制效率低下。它没有找到足够的实际用途来保证其高存储要求,应该删除。
本 EIP 定义了一种基于 SSZ 的通用回执格式,以解决这些问题。
规范
本文档中使用的关键词“必须(MUST)”、“禁止(MUST NOT)”、“必需(REQUIRED)”、“应(SHALL)”、“不应(SHALL NOT)”、“应该(SHOULD)”、“不应该(SHOULD NOT)”、“推荐(RECOMMENDED)”、“不推荐(NOT RECOMMENDED)”、“可以(MAY)”和“可选(OPTIONAL)”按照 RFC 2119 和 RFC 8174 中的描述进行解释。
现有定义
为了方便参考,此处复制了本文档中使用的现有规范中的定义。
名称 | 值 |
---|---|
MAX_TRANSACTIONS_PER_PAYLOAD |
uint64(2**20) (= 1,048,576) |
MAX_AUTHORIZATION_LIST_SIZE |
uint64(2**16) (= 65,536) |
SSZ_TX_TYPE |
0x1f |
名称 | SSZ 等效项 |
---|---|
Root |
Bytes32 |
ExecutionAddress |
Bytes20 |
GasAmount |
uint64 |
Receipt
容器
所有回执都表示为单个标准化的 SSZ 容器。 该定义使用 EIP-7495 中定义的 StableContainer[N]
SSZ 类型和 Optional[T]
。
名称 | 值 | 描述 |
---|---|---|
MAX_TOPICS_PER_LOG |
4 |
LOG0 到 LOG4 操作码允许每个日志 0-4 个主题 |
MAX_LOG_DATA_SIZE |
uint64(2**24) (= 16,777,216) |
日志的最大 data 字节长度 |
MAX_LOGS_PER_RECEIPT |
uint64(2**21) (= 2,097,152) |
logs 中的最大条目数 |
MAX_RECEIPT_FIELDS |
uint64(2**5) (= 32) |
Receipt 未来可能增长到的最大字段数 |
class Log(Container):
address: ExecutionAddress
topics: List[Bytes32, MAX_TOPICS_PER_LOG]
data: ByteList[MAX_LOG_DATA_SIZE]
class StableReceipt(StableContainer[MAX_RECEIPT_FIELDS]):
from_: Optional[ExecutionAddress]
gas_used: Optional[GasAmount]
contract_address: Optional[ExecutionAddress]
logs: Optional[List[Log, MAX_LOGS_PER_RECEIPT]]
# EIP-658
status: Optional[boolean]
# EIP-7702
authorities: Optional[List[ExecutionAddress, MAX_AUTHORIZATION_LIST_SIZE]]
class Receipt(Profile[StableReceipt]):
from_: ExecutionAddress
gas_used: GasAmount
contract_address: Optional[ExecutionAddress]
logs: List[Log, MAX_LOGS_PER_RECEIPT]
# EIP-658
status: boolean
# EIP-7702
authorities: Optional[List[ExecutionAddress, MAX_AUTHORIZATION_LIST_SIZE]]
Receipt
构造
回执的构造方式如下。
字段 | 描述 |
---|---|
from |
交易发送者的地址 |
gas_used |
此单个交易使用的 gas 量。 替换 cumulative_gas_used |
contract_address |
对于部署合约的交易,新的合约地址 |
logs |
交易执行期间发出的日志 |
status |
EIP-658 交易状态代码 |
authorities |
对于具有授权列表的交易,EIP-7702 authority 地址的列表。 不成功的授权用全零地址表示 |
SSZ 回执中不存在 logs_bloom
和中间状态 root
(Homestead 方案)。
执行区块头部的变更
执行区块头部的 receipts-root
从 MPT 转换为 SSZ。
receipts = List[Receipt, MAX_TRANSACTIONS_PER_PAYLOAD](
receipt_0, receipt_1, receipt_2, ...)
block_header.receipts_root = receipts.hash_tree_root()
JSON-RPC API
JSON-RPC API 上下文中的交易回执对象已扩展为包括:
authorities
:Array of DATA|null
- 0 到MAX_AUTHORIZATION_LIST_SIZE
个DATA
条目,每个条目包含 20 字节,对应于回执的authorities
字段
logsBloom
字段不再为新回执返回。 它继续为符合早期方案的历史回执返回。
from
、gasUsed
和 contractAddress
已经通过 JSON-RPC 提供,并且保持不变。
共识 ExecutionPayload
变更
构建共识 ExecutionPayload
时,receipts_root
现在基于 Receipt
类型,从而将 receipts_root
的类型从 MPT Hash32
更改为 SSZ Root
。
class ExecutionPayload(Container):
...
receipts_root: Root
...
class ExecutionPayloadHeader(Container):
...
receipts_root: Root
...
payload_header.receipts_root = payload.receipts_root
网络
当通过 Ethereum Wire Protocol 交换 SSZ 回执时,使用以下 EIP-2718 兼容信封:
Receipt
:SSZ_TX_TYPE || snappyFramed(ssz(Receipt))
对象使用 SSZ 进行编码,并使用 Snappy 帧格式进行压缩,这与 共识网络规范 中定义的共识对象的编码匹配。 作为编码的一部分,会发出未压缩的对象长度; 建议对每个对象强制执行的限制是 MAX_CHUNK_SIZE
字节。
理由
在执行区块中切换到单一、统一且向前兼容的回执格式降低了客户端应用程序和智能合约的实现复杂性。 现在可以验证回执数据的各个块,从而简化桥的实现。
轻客户端现在可以有效地验证回执的 from
、gas_used
和 authorities
,这以前需要获取相应的交易数据和其他回执。 在回填/提供历史回执数据时,执行层实现不再需要使用昂贵的 ecrecover
机制来计算签名者地址。
删除 logs_bloom
减少了每个回执 259 字节的存储成本。
向后兼容性
依赖于区块头中已替换的 MPT receipts_root
的应用程序需要迁移到 SSZ receipts_root
。
使用已验证的 cumulativeGasUsed
值的应用程序必须从先前的回执中计算该值。
依赖于 logsBloom
的应用程序将不得不转换为协议外的机制来过滤日志,或者退回到处理完整的回执集。 由于 logsBloom
机制对于轻客户端来说效率极低,因此其删除不太可能产生重大影响。
安全注意事项
无
版权
通过 CC0 放弃版权和相关权利。
Citation
Please cite this document as:
Etan Kissling (@etan-status), Gajinder Singh (@g11tech), Vitalik Buterin (@vbuterin), "EIP-6466: SSZ 回执 [DRAFT]," Ethereum Improvement Proposals, no. 6466, February 2023. [Online serial]. Available: https://eips.ethereum.org/EIPS/eip-6466.