文章探讨了以太坊中引入延迟执行(Delayed Execution)后可能出现的“免费DA(数据可用性)”问题,并分析了几种应对该问题的设计方案,包括乐观证明、预先验证和预收费等。文章还讨论了这些方案在用户体验、构建者复杂性、分叉选择复杂性、静态验证以及与FOCIL(强制包含列表)的兼容性等方面的权衡。
今天,免费 DA (Data Availability,数据可用性) 不是一个问题。每个交易发送者必须支付交易执行期间消耗的所有资源。放置在链上的数据,包括 calldata 中的数据或 EIP-2930 访问列表中列出的条目,都会产生 gas 成本,因此不可能在不支付费用的情况下发布数据。
以太坊目前通过要求验证者在证明该区块之前,完全执行和验证区块中的每个交易来保证每个区块的有效性。如果一个交易没有足够的余额来支付执行时所需的 gas,那么包含它的整个区块将变为无效。
然而,延迟执行 (EIP-7886) 的引入修改了这个过程。在延迟执行下:
例如,假设有两个账户 A 和 B,每个账户都提交交易(分别为 a 和 b)。交易 'a' 在区块中排在 'b' 之前。如果交易 'a' 耗尽了账户 B 的余额,那么交易 'b' 尽管最初看起来有资金,但在执行时变得无法支付,从而使区块无效。
查看包含初始设计的帖子here。
延迟执行的引入开启了几个设计的可能性。
不同的变体各有优点和缺点,下面我们主要关注以下几类:
乐观证明是指验证者在没有完全确定其有效性的情况下对区块进行投票的做法。经过最低限度的检查后,在 N Slot的证明者对在该Slot中提议的头区块进行投票。如果该区块在执行后被证明无效,则由 N{+}1 Slot中的下一个提议者将其从链中重组出去。
这种方法解决了延迟执行下的免费 DA,因为它确保了没有为他们写入的数据付费的交易不会被包含在链上。
棘手的部分在于分叉选择规则:N Slot的证明者合法地投出他们的选票,这些证明不仅代表对区块本身的支持,也代表对其整个祖先链的支持。因此,我们可能需要保留对无效头区块的证明,并允许来自这些区块的某些artifact保留在 Store
中。
有关乐观证明的更多详细信息,请参见 Francesco 的this post。
通过预先交易验证,我们在静态验证和执行之间引入了一个新步骤。
在静态验证区块及其交易之后,我们对所有交易执行以下有状态的检查并直接向发送者收费:
预先收取全部 gas 费用 (即,tx.gas * gas_price
)
block_gas_limit > block_gas_used
。With `block_gas_used = sum(tx.gas for tx in block.transactions)`.
其中 block_gas_used = sum(tx.gas for tx in block.transactions)
。
由于严格的预付款验证,在同一区块中资助一个帐户并立即从中进行交易的模式可能会变得不可能。这可以通过引入区块 coinbase 的基本费用赞助来解决。
这意味着交易不仅经过静态验证,还针对当前状态进行检查 - 确保 nonce 匹配并且有足够的资金可用。费用会立即被预留。
与今天不同的是,交易在执行期间不再相互干扰。因此:
这种方法有助于缓解免费 DA 问题,因为区块可以更早地被拒绝 - 在 执行开始之前。一旦预先验证完成并且费用被预留,验证者就可以自信地证明区块,因为他们知道其交易将按顺序成功执行。
这种设计在 FOCIL 兼容性方面存在权衡。
FOCIL 需要完全执行以验证 IL 合规性。仅仅访问区块及其交易是不够的 - 你无法仅从这些信息中确定是否遵守了 IL。相反,FOCIL 要求检查任何未包含在区块中但位于 IL 上的交易是否可以在给定的最终执行后状态下被包含。
在将包含执行前检查的 FOCIL 纳入考量时,一个重要的点是 “如何处理 gas_left
退款?”:
gas_left
退款与今天相比,允许发送者取回他们的 gas_left
并不会改变任何东西 - 交易的总成本仍然相同。
真正的问题出现在 FOCIL 中。一个交易可能看起来消耗了整个区块 gas 限制,但实际上并没有。例如,一个简单的 21,000 gas 的 ETH 转账可以提交一个等于完整区块限制 (例如 3600 万 gas) 的 gas 限制。在 FOCIL 下,区块构建者可以包含这个 “表面上很大的” 交易并忽略 IL。
问题在于,证明者 - 在执行区块之前 - 无法知道区块是否真的已满。如果区块被认为是满的,FOCIL 允许跳过 IL 上的交易。但是因为我们直到执行后才知道包含的交易实际会使用多少 gas,所以我们无法确定排除的 IL 交易是否可以放入区块中。
有两种可能的解决方案来解决这个问题。第一个是消除 gas 退款。第二个选择是使 FOCIL 无条件 - 也就是说,无论区块是否显得已满,都要强制执行包含列表。这完全消除了 gas 使用量的歧义,确保包含列表条目不能以区块空间不足为借口跳过。
gas_left
退款我们可以简单地限制退款,而不是像 2.1 中那样将所有 gas_left 退还给发送者。例如,将 gas_left 退款限制为交易实际使用的 gas 的 50% 将使审查攻击 (在攻击中指定高 gas 限制但仅消耗少量 gas) 在经济上不可行。在一个 3600 万 gas 的区块中,选择跳过 IL 的审查构建者需要一个至少使用 2400 万 gas 的交易才能获得 50% 的最高退款,即 1200 万 gas。
这种方法的缺点是它使区块打包效率降低。与跟踪累积 gas 使用量的当前模型相比,我们最终可能会遇到每个交易都包含更大缓冲区的情况,从而有效地限制了吞吐量。为了缓解这个问题,可以使用较低的上限 - 例如,将退款限制为 gas_used
的 10%,这将显着减少缓冲区开销。
gas_left
退款消除 gas_left
退款将使伪造大量 gas 使用量在 经济上不可行,因为用户必须完全支付他们声明的 gas 限制,而不管实际消耗量如何。
这解决了对 FOCIL 的攻击,在这种攻击中,构建者包含看似很大的交易 - 声明高 gas 限制 - 但最终执行起来非常便宜,从而有效地伪造一个完整的区块以绕过包含列表。
显然,此选项是对 UX 的相当激进的更改。
gas_left
退款和乐观的 gas_used
解决 FOCIL 不兼容性的另一种方法是将预先验证与乐观证明结合起来。在这种方法中,我们引入了一个新的标头字段 block_gas_used
,构建者必须设置该字段。执行后,我们验证 block_gas_used
是否与实际使用的 gas 匹配。如果不匹配,则该区块被认为是无效的,必须重新组织出去。
这将有利于 FOCIL,因为验证者可以根据声明的 gas 使用量可靠地检查 IL 中是否可以将交易添加到区块中。
但是,与乐观证明相关的 分叉选择复杂性 仍然适用。具有不正确的 block_gas_used
的区块不会成为规范,但我们可能仍然希望允许对此类区块的证明影响分叉选择。
在执行前向实体预先收费,并在之后发放退款是解决免费 DA 的有效方法。每当数据被写入链上而没有人为此付费时,协议可以简单地从预先收费方扣留退款。这确保了即使在没有人明确为数据付费的情况下,协议始终得到补偿。
延迟执行的初始版本 预先向 COINBASE
帐户收取所有交易的包含成本。包含成本包括 calldata、blob 和 EIP-2930 访问列表的 gas。Coinbase 承担成本,并且在执行期间变为无效的交易将被跳过,其数据占用空间已经得到支付。
tx.gas
而导致的区块打包效率低。相反,我们可以使用实际使用的 gas。与 FOCIL 的不兼容源于无法在执行前强制执行 IL。即使静态验证了一个区块,也没有预先向 coinbase 收取包含成本,并且允许跳过交易,但如果一个区块没有包含位于 IL 上的交易,即使区块中会有空间,那么该区块仍然会在 FOCIL 下变为无效。
gas_claimed
为了解决 FOCIL 不兼容性,一种潜在的解决方案是转向预先验证交易,由 coinbase 承担区块中所有交易的全部 gas_used * base_fee
。一个新的标头字段 gas_claimed
将允许区块构建者声明区块消耗了多少 gas。这使验证检查能够确定是否应该将来自 IL 的交易放入区块中。
在这种模型下,构建者预先支付所有声明的 gas 的基本费用。在执行期间,对于已执行的交易,会将全部交易费用 - 包括优先级费用 - 退还给构建者。如果 gas_claimed 值准确反映了实际的 gas 使用量,则构建者只需获得报销,再加上他们收到的优先级费用。但是,如果声明的 gas 超过了实际使用的 gas - 例如,为了避免包含 IL 交易 - 构建者最终会为此付费。
与 EL 上的通用请求类似,我们可以在执行payload中引入一个名为 proposer_penalty
的新字段,该字段表示来自所有跳过交易的总 gas 费用。当在 CL 上处理 payload 时,将从提议者处扣除此 proposer_penalty
。请求需要被推迟一个区块,以便我们处理来自Slot n 在Slot n{+}1 中的惩罚。
这种方法的优点是它消除了对 EL 上资金帐户的需求。相反,它利用了 CL 上现有的 stake。
但是,缺点是它增加了提议者的财务风险。在最坏的情况下,他们不仅会错过奖励 - 他们实际上可能会赔钱。对于 MEV-Boost 用户而言,这意味着签署一个可能花费他们成本的区块,依赖于中继提前进行适当的验证。
包含成本通常非常低 (假设非常高的 100 gwei 基本费用,则约为 0.55 ETH)。因此,平均而言,惩罚也应该很低。最坏的情况就是
gas_limit * base_fee
。让提议者用 stake 来支付也可以用作让 coinbase 承担成本的后备方案。
与乐观证明相关的想法如下:
这种方法的关键好处是证明者仍然可以尽早证明区块。但是,与乐观证明不同,即使其 payload 无效,该区块仍将保持规范。这避免了处理对后来被重组的区块的诚实验证的复杂性。相反,证明者将证明一个其执行 payload 仅变为 no-op 的区块。
从提议者的角度来看,为了利用此机制进行免费 DA,你至少需要获得作为 MEV-Boost 支付的报酬,或者对于本地构建者而言,区块的优先级费用作为补偿。因此,从利用该机制进行 “免费 DA” 中无法获得可持续的利润 - 这根本不是免费的。恢复状态意味着恢复所有交易及其优先级费用。这也意味着恢复构建者对提议者的付款,因此提议者极不可能参与此类策略。
BeaconBlock
仍然像以前一样 “有效”。gas_used
使用 Payload 空操作在这种设计中,发送者仍然在执行之前预先支付其交易的 gas 限制,并在执行后取回 gas_left
。为了强制执行 gas 限制,构建者必须将区块使用的 gas 量写入标头。如果事实证明 gas_used
与区块中指定的 gas 不同,则 EL payload 变为 no-op。变为 no-op 意味着恢复到区块之前的状态。
使用 Ethereum execution-specs 查看 Francesco 的实现。
BeaconBlock
,gas_left
退款,因此 UX 保持不变,^ 跟踪对无效区块的证明
^^ 静态验证要求 inclusion_gas <= claimed_gas_used,因此包含成本在预先支付,我们可以跳过超过 gas 限制的 tx
方法 | 发送者 UX | 构建者复杂度 | 分叉选择复杂度 | 静态验证 | FOCIL 兼容性 | 需要 sum(tx.gas) < block_gas_limit |
---|---|---|---|---|---|---|
(1) | ![]() |
![]() |
![]() |
![]() |
![]() |
![]() |
(2) 没有 gas_left 退款 | ![]() |
![]() |
![]() |
![]() |
![]() |
![]() |
(2) 带有 gas_left 退款 | ![]() |
![]() |
![]() |
![]() |
![]() |
![]() |
(2) 带有 gas_left 退款 + (1) (乐观的 gas_used) | ![]() |
![]() |
![]() |
![]() |
![]() |
![]() |
(2) 带有 gas_left 退款 + (3) 针对声明的 gas_used | ![]() |
![]() |
![]() |
![]() |
![]() |
![]() |
(3) 针对包含成本 | ![]() |
![]() |
![]() |
![]() |
![]() |
![]() |
(4) | ![]() |
![]() |
![]() |
![]() |
![]() |
![]() |
(2) 带有 gas_left 退款 + (4) 针对 gas_used | ![]() |
![]() |
![]() |
![]() |
![]() |
![]() |
- 原文链接: ethresear.ch/t/delayed-e...
- 登链社区 AI 助手,为大家转译优秀英文文章,如有翻译不通的地方,还请包涵~
如果觉得我的文章对您有用,请随意打赏。你的支持将鼓励我继续创作!