EIP-7862 지연 상태 루트 (Delayed State Root)

Hegota 포함 제외 (DFI) · 확장성·데이터 · 원문 상태 Draft · 2024-12-23 작성

블록 헤더에 그 블록 자신의 상태 루트 대신 직전 블록의 사후 상태 루트를 담아, 상태 루트 계산을 블록 검증에서 분리하는 제안입니다.

왜 필요한가

이더리움 블록 헤더에는 그 블록의 모든 거래를 실행한 뒤의 장부 요약값인 상태 루트(state root)가 들어갑니다. 이 값을 계산하는 일이 블록 생산의 큰 병목입니다. 블록을 만드는 빌더는 어떤 거래 조합이 가장 수익이 좋은지 겨루는 MEV 경매 동안 조합을 바꿀 때마다 상태 루트를 다시 계산해야 해서 한 슬롯에 수천 번을 계산하게 됩니다. ePBS(EIP-7732)가 도입되면 빌더의 시간 여유는 더 빠듯해집니다. 블록이 건드린 저장 공간 목록인 블록 접근 목록(Block-Level Access Lists, EIP-7928)은 상태 읽기·쓰기를 병렬화해 주지만 상태 루트는 실행이 끝나야 알 수 있어서 같은 슬롯 안에서는 도움이 되지 않습니다. 이 제안은 상태 루트를 한 블록 늦게 헤더에 담아, 검증자가 상태 루트 계산을 기다리지 않고 블록 유효성을 증명할 수 있게 합니다.

무엇이 바뀌나

지금

EIP-7862 이후

누구에게 영향이 있나

심층 설명

헤더: 필드 추가 없이 의미만 변경

Header의 state_root 필드 의미가 바뀝니다. 블록 n의 state_root는 블록 n-1의 사후 상태(post-state), 곧 블록 n의 사전 상태(pre-state)를 가리킵니다. 새 필드는 추가되지 않습니다. 명세의 Header 클래스에는 parent_hash, state_root, transactions_root, receipt_root 등 기존 필드와 함께 block_access_list_hash가 포함되어 있어 BAL(EIP-7928)을 전제로 합니다.

last_computed_state_root와 헤더 검증

BlockChain 객체에 last_computed_state_root 필드가 추가되어 마지막으로 계산한 상태 루트를 추적합니다. validate_header는 header.number가 1 미만이면 InvalidBlock을 올리고 header.state_root가 chain.last_computed_state_root와 다르면 InvalidBlock을 올립니다. 나머지 헤더 검증은 그대로입니다. 즉 블록의 상태 루트 검증이 '이 블록을 실행한 결과와 맞는가'에서 '직전 블록 실행 후 계산해 둔 값과 맞는가'로 바뀝니다.

상태 전이: 루트 계산을 실행 뒤로

state_transition은 먼저 validate_header를 수행한 뒤 apply_body로 거래와 출금을 실행합니다. 실행 결과 검증에서 state_root는 제외됩니다. 헤더 검증에서 이미 확인했기 때문입니다. block_gas_used와 header.gas_used 불일치 등 다른 검증은 유지됩니다. 실행이 끝나면 state_root(block_env.state)를 계산해 chain.last_computed_state_root에 저장하고 이 값이 다음 블록의 헤더 검증에 쓰입니다. 블록 목록은 최근 255개까지만 유지합니다.

포크 활성화와 하위 호환성

활성화 블록 F에서 apply_fork는 last_computed_state_root를 현재 상태 루트, 곧 블록 F-1의 사후 상태 루트로 초기화합니다. 블록 F는 블록 F-1의 사후 상태 루트를 담아야 하며(MUST), F+1부터는 각 블록이 부모 블록의 사후 상태 루트를 담습니다. 이 변경은 하드포크가 필요하고 구현하지 않은 클라이언트는 지연 상태 루트가 담긴 블록을 거부합니다.

ePBS 호환성과 BAL 시너지

EIP-7732(ePBS)에서 ExecutionPayloadEnvelope는 process_execution_payload 끝에 검증되는 합의 계층(CL) state_root를 담는데, 이 제안은 실행 계층(EL) 헤더의 state_root 의미만 바꾸므로 CL 쪽 검증에는 영향이 없습니다. BAL(EIP-7928)과의 시너지가 핵심입니다. 클라이언트는 블록 n을 BAL과 함께 받고 BAL로 블록 n의 상태 루트 계산을 병렬화한 뒤, 그 루트를 블록 n+1에 포함합니다. 이 제안이 없으면 상태 루트는 실행이 끝나야 알 수 있어 같은 슬롯 안에서는 BAL이 루트 계산에 도움이 되지 않습니다. 또한 빌더는 BAL의 상태 변경분을 슬롯의 사전 상태에 적용해, 직전 블록을 완전히 실행하지 않고도 블록 구성을 시작할 수 있습니다.

라이트 클라이언트 영향

블록 n에 대한 상태 증명은 블록 n+1이 나올 때까지 기다려야 합니다. 대부분의 라이트 클라이언트 프로토콜은 이미 증명 생성에 여러 블록의 지연을 허용하므로 영향은 제한적입니다. 보안 모델은 바뀌지 않고 타이밍만 한 슬롯 늦어집니다.

보안 고려: 리오그와 사전 상태 보존

체인 재구성(reorg)이 일어나면 클라이언트는 새 정규 체인의 각 블록에 대해 last_computed_state_root를 다시 계산해야 합니다(MUST). 루트가 지연된다는 특성 자체가 리오그 로직을 바꾸지는 않습니다. 또 클라이언트는 현재 블록의 상태 루트가 다음 블록에 포함될 때까지 사전 상태(부모 블록의 사후 상태)를 보존해야 하는데(MUST), 이는 리오그 대응을 위해 이미 표준적으로 하고 있는 관행입니다.

진행 상태: 헤고타 후보에서 제외

07.02 ACDE #240에서 EIP-7862가 헤고타(Hegota) 후보로 접수되었으나(PFI), 09.10 ACDE #245에서 제외되었습니다(DFI). BAL 이후 병렬 계산이 가능해 스테이트 루트가 큰 병목은 아니라는 반론이 우세했고 바이너리 트라이 작업과 함께 향후 포크에서 재검토할 수 있다는 결정이었습니다. 원문 상태도 Draft라 명세 내용은 앞으로 바뀔 수 있습니다.

EIP 원문 · ← EIPs