#28266·go-ethereum

平行中节点获取(用于单个三相)

作者: aaronbuchwald创建于 2023年10月6日更新于 2026年9月12日
标签type:feature

理由

目前,当去ethereum构建/执行一个块时,它处理EVM中的交易(同时使用O(1)快照来进行DB读取需要),然后需要将所有状态变化应用到三重奏并计算出一个新的状态根.

通常情况下,状态打乱比实际的EVM处理时间要昂贵得多(不过,对于使用过多RAM的新路径方案来说,这已接近于不再使用https://twitter.com/peter szilagyi/status/1708013385558671662。

在 EVM 中执行交易时, StateDB 使用前置逻辑来尝试将 tree 的缓存与所有中间节点预加热,当需要执行所声明的b并计算出一个新的 state root 时,这些中间节点需要被打乱. 如果中间节点还没有在内存中,那么这会导致大量DB读取,这可以占用大量用于状态洗涤的时间.

对于大型存储尝试来说,状态取取取的性能可能要低得多,因为三重执行并不安全,无法同时使用(https://GitHub.com/ethreum/go-ethreum/blob/v1.13.1/trie/trie.go#L37)。 虽然每个存储三重奏都得到了自己的预取出出行(https://GitHub.com/ethereum/go-ethereum/blob/master/core/state/trie prefetcher.go#L153),但如果大部分工作量来自单个存储三重奏,那么预取出行可能效率极低.

理想的情况是,我们可以将 DB 读取的平行化,以便在执行指定b 之前将所有中间节点都缓存到内存中.

执行

我玩过两种不同的方式,我很乐意完成其中两种。 我想首先提出这个问题,以便获得反馈,了解这一改变对Guh团队是否有意义,如果是的话,哪个执行更可取。

困难的部分是找到一种方法,围绕三重操作不能安全地同时使用这一事实开展工作,并且从外部调用者调用支持并行操作将是一种非常非三角重写。

最好能彻底解决这个问题。

□ 并行使用独立尝试获取

每个单个的trie并不会安全地同时使用,但我们可以创建多个相同的trie实例,以平行地取出所有请求的密钥,从磁盘中将所有必要的中间trie节点拉入trie数据库的缓存.

虽然所标出b所持有的三分点的例子可能并没有全部被扩展出节点,但它会将所有中间节点取入三分点数据库的缓存中,这样,当三分点执行时,每个三分点的节点已经存在内存了.

我对每个州内“更新Trie”的内容进行了粗略的落实:https://GitHub.com/ethereum/go-ethereum/compare/master.aronbuchwald:go-ethereum:平行的-fach-update-trie。 把这个移到预发器代码上也许更合理 但这是 . . . . . . .

内容来源: ethereum/go-ethereum