深度丨 Vitalik 提出的EIP-2938将给以太坊带来哪些改变?

来源:网络 时间:2020-11-29 01:31
导读:十组数据告诉你,以太坊你不知道的事 用数据讲述以太坊。 有两种类型的账户。外部自有账户(EOA)和合约账户(CA)。EOAs 由私钥控制,而 CA 由其中包罗的智能合约代码控制。 EOAs


十组数据告诉你,以太坊你不知道的事

用数据讲述以太坊。

有两种类型的账户。外部自有账户(EOA)和合约账户(CA)。EOAs 由私钥控制,而 CA 由其中包罗的智能合约代码控制。EOAs 一直比 CA 更有特权,由于只有 EOAs 可以通过支付 gas 最先买卖执行。账户抽象 (AA) 是一个提案,它允许合约像 EOA 一样成为一个 " 顶层 " 账户,其可以支付用度并最先买卖执行。

账户抽象的念头是显著改善用户在钱包、 DApps 和 DeFi 等种种场景下与举行交互时的用户体验。账户抽象在中提供了一个基础层的功效,来决议什么时候可以支付 gas,以及对谁支付 gas 等问题。

Status Messenger 应用集成了一个以隐私为中央的信息系统,以及一个钱包和一个 Web3 DApp 浏览器。Status wallet 现在是一个 EOA 钱包,它限制了我们提供只有智能合约钱包才气提供的厚实的用户体验,如多重署名平安、社交恢复、利率限制、允许 / 拒绝地址列表和无 gas 的元买卖。现在智能合约钱包的用户体验到了 gas 费颠簸的影响,而且第三方中继器无法有用解决这个问题。而账户抽象旨在解决这个问题。

在本文中,我们提出了智能合约钱包靠山下对账户抽象的需求。然后,我们通过形貌协议转变和对节点的影响深入探讨账户抽象的要害方面。最后,我们讨论了一些扩展的提议,并通过合理化与接口的 Status 项目的设计路线图来竣事,这些项目可能都市受到账户抽象的影响。

历史 & 念头

账户抽象最初是在 2017 年以 EIP-86 的形式提出的,目的是实现 「买卖泉源和署名的摘要 」,但这一想法的起源可以追溯到更早的 2016 年。那时有人建议:「与其有一个协议内机制,将 ECDSA 和默认的 nonce 方案作为唯一的 「尺度 」方式来保证账户的平安,不如接纳开端措施,确立一个模子,从长远来看,所有的账户都是合约,而且合约可以支付 gas,用户可以自由界说自己的平安模子。」

最初的建议被认为是具有挑战性的,由于需要改变许多协议而且需要保证平安性。最近,Vitalik Buterin 等人提出了 EIP-2938 的草案,该草案概述了一个更容易实现的方式:通过将协议 / 共识的转变最小化 , 并通过节点 mempool 规则强制执行所需的平安保证。由 Sam Wilson 和 Ansgar Dietrichs(另外两位 EIP 作者) 撰写的 Vitalik 的 Engineering Group Meetup presentation 和 ETH Online presentation(以及相关文章 1 和 2) 为这个主题提供了更详细的先容。本文重点先容了所有这些泉源的要害内容。

念头

账户抽象背后的念头原理异常简朴,但却是根本性的:今天的买卖具有可编程的效果(通过挪用智能合约实现),但它们只具有牢固的有用性,即只有当它们具有有用的 ECDSA 署名与有用的 nonce,而且具有足够的账户余额时,买卖才是有用的。账户抽象 通过引入一种新的账户抽象买卖类型,将买卖从牢固有用性升级为可编程有用性。这种账户抽象买卖类型总是来自一个特殊的地址而且协议不需要对其举行署名、Nonce 或余额检查。这种账户抽象买卖的有用性由目的智能合约决议,目的智能合约可以执行自己的有用性规则,之后它可以决议为这类买卖付款。

那么,为什么这个很有用呢?我们以钱包为例来强调账户抽象的利益。

智能合约钱包:现在大多数钱包都是 EOA 钱包,它由种子短语天生的私钥珍爱。(BIP-39 种子短语是一个由 12-24 个单词组成的有序列表,这些单词是从 2048 个单词中随机选择的。这提供了获得二进制种子所需的熵,该种子使用 PBKDF2 函数天生。然后,二进制种子被用来天生 BIP-32 钱包的非对称密钥对。) 用户应该把种子短语写在平安的地方,由于以后在另一个钱包上恢复密钥时可能需要它。然而,这种钱包很容易受到私钥被盗或种子短语丢失的影响,从而导致用户的资金损失。

智能合约钱包是通过智能合约在链上实现的。这种钱包通过实现多署名平安、社交或基于时间的恢复、买卖或金额的速率限制、允许 / 拒绝地址列表、无 gas 买卖和批量买卖等功效,提供可编程的功效缓解风险以及用户友好体验。

虽然智能合约钱包露出在易受攻击的智能合约的平安风险之下,但钱包提供商执行的平安测试和审查可以减轻这种风险。EOA 钱包的风险完全在于钱包用户,他们被委托卖力种子短语的平安,而在智能合约中没有任何可保障平安的程序。

智能合约钱包的例子有 Argent、Authereum、Dapper、Dharma、Gnosis Safe、Monolith 和 MYKEY。如下图所示,这类钱包的采用率似乎在增添。

Argent 通过他们的 Guardians 观点实现了无密钥社交恢复功效,其中 Guardians 是用户信托的人或装备,可以辅助找回用户的钱包。Argent 还旨在实现类似银行的平安性(通过逐日买卖限额、账户锁定和可信联系人等功效)以及类似 Venmo 的可用性(通过使用 ENS 名称而非地址和支持元买卖)相结合。

Gnosis Safe 是一个多署名的智能合约钱包,专注于团队治理资金,需要团队成员的最低数目(m-of-n)批准买卖才气发生。它还可以通过元买卖实现无 gas 署名。

所有这些先进的钱包功效都需要使用完善的智能合约。钱包用户要么需要与 EOA 举行交互,要么依赖钱包提供商通过提供商的中继器或第三方中继器网络(如 Gas Station Network)来支持元买卖。前者依赖于在 KYC 后的中央化买卖所购置 ETH,而后者旨在通过将用户的肩负转移到中继器上,以削减这种上链用户体验摩擦,其成本由钱包提供商链上 / 链下和 / 或用户链下抵偿。

然而,基于中继器的架构有三个主要瑕玷:(1) 它们可能会被认为是中央化的中介机构,有可能会对买卖举行审查 (2) 由于中继者的买卖需要分外的 21000 基础 gas fee,而且它们的营业需要在 gas fee 之外获得利润,因此在手艺 / 经济上效率低下 (3) 使用中继者专用协议迫使应用依赖非基底层的基础设施,其用户群较小,可用性保证不确定。

账户抽象将使智能合约钱包能够接受用户的无 gas 买卖,并在不依赖中继层网络的情形下为其支付 gas 费。因此,这种下层能力将极大地改善这类钱包的入驻用户体验,而不会牺牲的去中央化保障。

Tornado Cash:一个相关的念头应用是混币器,如 tornado.cash,其中 Tornado 通过使用智能合约打破地址之间的链上联系来改善买卖隐私,该合约接受 ETH 存款,随后可由差别的地址提取。用户在存款时需要提供隐秘的哈希值,之后在提现时提供 zkSnark 证实,以显示对隐秘的领会,而不泄露隐秘或之前的存款自己。这样就把提现和存款脱钩了。

但提现存在一个问题 , 要从新天生的地址中执行提现买卖,用户需要在里面有一些 ETH 来支付 gas。这个 ETH 的泉源(一样平常是买卖所)会损坏 Tornado 的隐私。首选的替换方案是再次使用中继器网络,然则它有前面概述的瑕玷。

账户抽象将解决这个问题,允许 Tornado 合约接受用户的提现账户抽象买卖,然后验证 zkSnark 并扣除一些 gas 费(从之前的存款金额中扣除),然后将剩余的存款金额转到提现地址。

账户抽象

EIP-2938 号文件提出的账户抽象,允许合约成为支付用度和最先执行买卖的最高级账户。这是通过引入协议转变实现的,新的账户抽象买卖类型需要两个新的操作码:NONCE 和 PAYGAS,对 mempool 的规则举行改变以及支持高级用法的扩展。账户类型仍然有两种类型(EOA 和合约账户),所有拟议的转变都与当前的买卖、智能合约和协议向后兼容。

账户抽象的应用分为两个方面思量:1)单租户应用,如智能合约钱包,为每个用户建立一个新的合约 2)多租户应用,如 tornado.cash 或 Uniswap,多个用户与统一套智能合约交互。

账户抽象对多租户应用的支持需要更多的研究,建议作为未来的事情。以是我们将在本文中重点讨论单租户账户抽象的支持。

协议转变

引入了一种新的买卖类型,以及两个支持 NONCE 和 PAYGAS 的操作码。这些是唯一的协议转变。

账户抽象买卖:引入了一种新的账户抽象买卖类型 AA_TX_TYPE。它的有用类型被解释为 RLP([nonce, target, data]),而不是现有的买卖类型。后者的有用类型是 RLP([nonce, gas_price, gas_limit, to, value, data, v, r, s])。

账户抽象买卖中省略的 gas_price 和 gas_limit 在执行过程中由目的账户抽象合约指定。账户抽象买卖中省略的 ECDSA 署名 v、r、s 由特定合约对数据举行验证检查取代。to 地址由目的合约地址取代。之以是省略该值,是由于所有账户抽象买卖的始发地址是一个特殊的 ENTRY_POINT 地址 (0xFFFF...FFF),而不是与之相关联的 EOA 值。

若是检查失败,则买卖被认为是无效的,否则,tx.target.nonce 将被递增,买卖继续举行。

账户抽象买卖的基本 gas 成本建议为 15000,而不是现在的 21000 (以反映缺乏内在 ECDSA 署名所节约的成本)。此外,账户抽象买卖没有内在 gas 限额。在最先执行时,gas 限值只需设定为该组的剩余 gas。

NONCE 操作码:NONCE 操作码 (0x48) 将被挪用者的 NONCE(即账户抽象目的左券) 压入 EVM 客栈。因此,Nonce 露出给 EVM,以允许对所有买卖字段(包罗 nonce)举行署名验证,作为账户抽象合约中验证的一部分。

PAYGAS 操作码:PAYGAS 操作码 (0x49) 从客栈中取出两个参数 : (顶部)version_number, (顶部第二个)memory_start. version_number 允许未来的实现改变 opcode 的语义。现在,该操作码的语义如下。

检查 version_number == 0 (否则抛出异常)

提取 gas_price = bytes_to_int(vm.memory[memory_start: memory_start + 32])

提取 gas_limit = bytes_to_int(vm.memory[memory_start + 32: memory_start + 64])

检查 contract.balance >= gas_price * gas_limit (否则抛出异常)

检查 globals.transaction_fee_paid == False (否则抛出异常)

检查 AA 执行框架 == 顶层框架,即若是当前 EVM 执行退出或还原,则整个事务的 EVM 执行终止(否则抛出异常)。

设置 contract.balance -= gas_price * gas_limit(限制)。

设置 globals.transaction_fee_paid = True

设置 globals.gas_price = gas_price 和 globals.gas_limit = gas_limit。

设置当前执行上下文的剩余 gas=gas_limit-已经消耗的 gas。

在账户抽象买卖执行竣事时,(globals.gas_limit - remaining_gas)*globals.gas_price 转移给矿工,账户抽象合约退还 remaining_gas * globals.gas_price。

PAYGAS 作为 EVM 执行检查点。在此点之后的任何还原都只会还原到这里,然后合约不接受退款,globals.gas_limit * globals.gas_price 转移到矿机。

新的买卖类型和两个新的操作码构成了协议 / 共识层面的转变,它们的语义是对照容易明白。

Mempool 规则

「Mempool 」指的是 节点内部的一组内存数据结构,它在挖矿前存储候选买卖。Geth 称其为 「买卖池 」;Parity 称其为 「 买卖行列 」。无论名称若何,它都是一个坐在内存中守候被纳入区块的买卖池。把它看成是一个 「 守候区 」,守候买卖被接受到一个区块中。

现在,通过牢固的买卖有用性规则,矿工和其他节点只需要最小的起劲就可以验证其 mempool 中的买卖,从而制止 DoS 攻击。例如,若是一个矿工拥有有用的 ECDSA 署名、有用的 nonce,而且有足够的账户余额,就可以确定某笔买卖将真正支付用度。该矿工的 mempool 中的其他买卖只有在来自统一地址,而且,增添 nonce 或充实削减账户余额的情形下,才可能使这个待处置的买卖无效。这些条件在计算上是最小的,以使矿工和节点对其 mempools 有足够的信心,划分举行区块守候或重播。

账户抽象买卖以其可编程的有用性引入了更多的复杂性。账户抽象买卖不支付任何前期 gas,并依赖其目的账户抽象合约来支付 gas (通过 PAYGAS)。从观点上讲,账户抽象买卖处置分为两个阶段:较短的验证阶段(PAYGAS 之前)和较长的执行阶段(PAYGAS 之后)。若是验证阶段失败(或抛出异常),买卖无效(就像今天无效署名的非账户抽象买卖一样),不会被包罗在一个区块中,矿工也得不到任何用度。

因此,矿工和节点需要一个可展望的机制来制止一个待处置的账户 抽象 买卖的有用性对 mempool 中其他待处置买卖的依赖性。否则,一个买卖的执行可能会使 mempool 中的许多 / 所有账户抽象买卖无效,导致 DoS 攻击。为了制止这种情形,有两个建议的规则要在 mempools 中的账户抽象买卖上执行(由矿工和节点执行,但不是在协议自己)。

Opcode Restriction

为了防止账户抽象买卖的有用性取决于账户抽象合约自己以外的任何因素,以下操作码在核查阶段 (即在 PAYGAS 之前) 被视为无效:PAYGAS 之前):环境操作码(BLOCKHASH、COINBASE、TIMESTAMP、NUMBER、DIFFICULTY、GASLIMIT)、BALANCE (任何账户,包罗目的自己)、对目的以外的任何事物的外部挪用 / 建立或预编译(CALL, CALLCODE、STATICCALL、CREATE、CREATE2)和读取代码的外部状态接见(EXTCODESIZE、EXTCODEHASH、EXTCODECOPY、DELEGATECALL),除非地址是目的。

节点要放弃 mempool 中以账户抽象合约为目的的账户抽象事务,打破这个操作码限制规则。这确保了只要账户抽象合约状态不发生转变,mempool 中的有用账户抽象事务将保持有用。

字节码前缀限制

若是非账户抽象事务可以影响账户抽象合约的状态,那么就会影响 mempool 中账户抽象事务的有用性。为了防止这种情形的发生,账户抽象事务应该只允许针对那些在其字节码开头有 AA_PREFIX 的合约,其中 AA_PREFIX 实现了对 msg.sender 是账户抽象事务的特殊 ENTRY_POINT 地址的检查。这有用地防止了非账户抽象买卖与账户抽象合约的交互。

节点要把账户抽象事务丢给在其字节码入口点没有这个 AA_PREFIX 的账户抽象合约。

对账户抽象合约实行的这两个限制配合确保了:(1) 账户抽象买卖的有用性逻辑所能接见的唯一状态是账户抽象合约内部的状态,(2) 这个状态只能被其他针对这个特定账户抽象合约的账户抽象买卖修改。

因此,只有在另一宗针对统一份账户抽象合约的守候买卖中,未完成的账户抽象买卖才会失效。然而,鉴于这些不是协议 / 共识的改变,矿工可以自由地在区块中包罗打破这些规则的买卖。

扩展

上述协议调换和 mempool 规则允许基本的账户抽象合约充实而平安地实现单租户应用,如智能合约钱包。其他需要放宽上述规则或需要实现多租户应用的高级用法,则需要账户抽象以扩展的形式提供更多的支持,好比。

SET_INDESTRUCTIBLE opcode,禁用 SELFESTRUCT,允许账户抽象合约在验证阶段平安地挪用 DELEGATECALL 的库。

IS_STATIC opcode,若是当前上下文是静态的,则返回 true,允许非账户抽象事务挪用者笼罩之前的字节码前缀限制,平安地从账户抽象合约中读出值。

RESERVE_GAS opcode,当从一个非账户抽象事务挪用时,它确立了一个账户抽象合约消耗的 gas 下限,该下限是追求写入合约状态的。这样做的作用是迫使攻击者不消耗最低数目的 gas,以抑制试图使 mempool 中任何账户抽象事务无效的行为。

另有其他的如多个待处置的买卖、验证的缓存效果、验证的动态 gas 限制和赞助买卖,这些都是支持多租户应用和 zk 证实所需要的,如 Tornado Cash。关于它们的详细内容不在本文的讨论范围内。

下一步事情

账户 抽象 EIP-2938 现在处于草案模式,正在 研究论坛中举行讨论。EIP 的下一步是被思量纳入即将到来的硬分叉之一。EIP 作者的目的显然是 Berlin 之后的硬分叉(Berlin 暂定于 2021 年头的某个时间),其时间表现在还不是很明确。以是对于 EIP-2938 来说,现在还为时过早。

此外,也不清楚是否有必要在基础第 1 层(L1)加入 EIP-2938。鉴于第 2 层(L2)解决方案的相对灵活性(如我们之前的文章所述),账户抽象可以在特定的 L2 上实现,而不需要升级整个 L1。然而,纵然一些 L2 实现了自己的账户抽象版本,在 L1 上统一支持账户抽象也有利益。因此,账户 抽象 在那里实现,若何实现,另有待考察。

「账户抽象不太主要是由于不管 L1 是否支持,都可以在 L2 上实现。」--- Vitalik 在他关于以汇总为中央的路线图的文章中谈到了在基础层将继续起作用的事情)。

Status:Status 钱包现在是一个 EOA 钱包,它的区别在于捆绑了一个以隐私为中央的短信系统,并实现了谈天中的支付或 Keycard 的增强平安性等集成。正在思量智能合约钱包的功效,如多签和社交恢复,账户抽象 EIP-2938 的支持将有助于消除对集中式和低效的基于 relayer 的架构的依赖,如前所述。

Status 也在评估 L2 解决方案,既要支持其钱包中的多链,又要为种种用例提供所需的扩展,如我们在前面的文章中所述。例如,Keycard 正在探索一个支付网络,其信用卡级别的可扩展性和近乎即时的终局性的设计要求是现在网络无法知足的。此外,另有许多其他的设计,如推荐设计、Tribute-to-Talk 和 ENS 名称,所有这些设计都将受益于 L2 扩展性,以实现可行的部署和合理的用户体验。若是一个可行的 L2 解决方案实现了账户 抽象 ,那么确立在该 L2 基础上的项目将能够行使账户 抽象 的优势,而不必依赖 L1。

总结

协议的一个基本方面是,只有外部自有账户 (EOAs) 可以支付 gas 费并最先执行买卖。合约账户(CA)不能这样做。账户 抽象 (AA)是一个提案,旨在改变这种区别,允许专门构建的 CA 以编程方式检查新型账户抽象买卖的有用性,决议代为支付 gas 费 ,从而有用地启动其执行,而不需要 EOA。

账户抽象对于显著改善钱包、混币器、DApps 和 DeFi 等种种场景下的用户体验具有意义,而无需依赖中央化和低效的基于 relayer 的架构。基本的单租户场景,如智能合约钱包,通过引入一种新的买卖类型、两种新的操作码和两种 mempool 规则,账户抽象可以平安地支持。高级多租户应用,如 Tornado Cash,需要对这些协议转变和节点规则举行扩展。

在这篇文章中,我们提到了智能合约钱包靠山下对账户抽象的需求。我们通过形貌协议转变和对节点的影响来强调账户抽象的要害方面。我们触及了一些针对高级用途的拟议扩展,最后,我们在当前的路线图和 Status 的优先事项中对账户抽象举行了定位。

在 Web3 中削减摩擦和改善用户体验是这个生态系统中所有项目的首要任务。以某种形式,账户抽象可能一定会在未来的起劲中施展主要作用。