erigontech / erigontech/erigon

execution: classify rules-engine failures at source

Open
#23,225 1 comment 0 reactions 1 assignee Claimed by @yperbasis View on GitHub
tech debt reduction
Dominant language
Go
Stars
3.6k
Forks
1.5k
Avg merge
1d 16h
Merged PRs (30d)
455

Description

## Problem

The executor must distinguish an invalid-block verdict from an operational failure, but the rules-engine producers still return an unclassified `error`.

`rules.Engine.Initialize` and `rules.Engine.Finalize` currently mix both classes:

- Shipped engines return some consensus violations as plain errors. Examples include a Merge requests-root mismatch, AuRa block-initialization validation, and the unexpected-withdrawals or unexpected-requests sentinels.
- The same methods can return state, syscall, chain-reader, or epoch-database failures that are operational.

Serial execution and legacy parallel execution force every `Initialize` or `Finalize` error into `rules.ErrInvalidBlock`. Classifying only errors that already wrap `rules.ErrInvalidBlock` would instead make existing consensus violations operational and make serial and parallel execution disagree. PR #23212 therefore keeps the legacy blanket classification until the producers expose enough information.

PR #23212 separately handles transaction state-read failures by retaining the source reader error and classifying it as operational even when execution cannot publish a complete read set. This issue tracks the remaining rules-engine boundary.

## Goal

Classify rules-engine failures at their source so downstream code does not infer their meaning from an error tree.

## Required work

- Define an explicit source-level distinction between block-validation failures and operational failures for `Initialize` and `Finalize`.
- Inventory every rules engine and tag all content-dependent validation errors, including errors returned through system calls.
- Preserve operational identity for state, database, chain-reader, and infrastructure failures.
- Migrate serial and parallel consumers together, then remove their blanket `Initialize`/`Finalize` wrapping.
- Keep the Engine API result consistent: invalid payloads must produce `INVALID`; operational failures must remain retryable errors.

## Acceptance criteria

- Plain consensus-validation failures from shipped engines are invalid-block verdicts under both serial and parallel execution.
- Injected `Initialize` and `Finalize` state or I/O failures are operational under both executors.
- Tests cover at least one real validation and one operational path for each affected producer boundary.
- The producer inventory confirms that no concrete rules engine still relies on consumer-side guessing.

Contributor guide

Open the contributing guide

Assessment

This issue has not been assessed yet.

Get new issues in your inbox

A short digest of beginner-friendly GitHub issues.