Skip to content

fix(specs): raise block_distance_for_finalized_data for probabilistic-finality chains - #2316

Open
yagop wants to merge 1 commit into
lavanet:mainfrom
yagop:fix/spec-finalized-block-distance
Open

fix(specs): raise block_distance_for_finalized_data for probabilistic-finality chains#2316
yagop wants to merge 1 commit into
lavanet:mainfrom
yagop:fix/spec-finalized-block-distance

Conversation

@yagop

@yagop yagop commented Jul 10, 2026

Copy link
Copy Markdown

Problem

Several specs set block_distance_for_finalized_data below the real reorg depth of the chain. IsFinalizedBlock then treats reorgable blocks as finalized, so:

  • Consumers/providers cache orphaned-block data as immutable — integrators relying on "finalized" responses risk double-crediting transactions and data loss.
  • During a routine reorg, two honest providers sign conflicting hashes for a "finalized" block, which the conflict module treats as fraud evidence (slashable).

Changes

Spec Old New Rationale
DOGE, DOGET 1 40 PoW; exchanges require ~40–60 confirmations
LTC, LTCT 1 13 PoW; the April 2026 MWEB incident caused a 13-block reorg
BCH, BCHT 1 15 Minority-hashrate PoW; exchanges use 15
TRX, TRXT 4 20 Blocks are solid after 19/27 SR confirmations; matches testnet-2
POLYGON, POLYGONA 1 10 Head reorgable until a milestone; Heimdall v2 finality is ~2–5s, 10 adds margin
FVM, FVMT 1 5 EC reorgs tipsets by a few epochs; F3 finalizes within ~2
BSC, BSCT 0 3 Spec uses eth_blockNumber (head); BEP-126 finality needs ~2–3 blocks

testnet-2 bch/bsc updated to match (its tron already used 20). Solana left at 0: its GET_BLOCKNUM uses getLatestBlockhash with finalized commitment.

Tradeoff: finalized-data lag grows by distance × average_block_time per chain.

Validated with go test ./x/spec/keeper/ -run TestSpecs.

Fixes #2317

…-finality chains

Values below real reorg depth let orphaned blocks be treated as
finalized: replies are cached as immutable and honest providers
signing conflicting hashes look fraudulent to the conflict module.
For integrators this risks double-credited transactions and data loss.

DOGE 1->40, LTC 1->13, BCH 1->15, TRX 4->20, POLYGON 1->10,
FVM 1->5, BSC 0->3 (testnet-2 bch/bsc aligned; tron already 20).
@qodo-code-review

Copy link
Copy Markdown

PR Summary by Qodo

Raise finalized-block distance for probabilistic-finality chain specs

🐞 Bug fix ⚙️ Configuration changes 🕐 10-20 Minutes

Grey Divider

AI Description

• Increase finalized-data block distance for PoW/probabilistic-finality chains to avoid reorged
 blocks being treated as final.
• Reduce risk of caching orphaned data and triggering false conflict/fraud evidence during routine
 reorgs.
• Align mainnet-1 and testnet-2 spec thresholds for BCH and BSC (TRON updated on mainnet-1).
Diagram

graph TD
  A["Chain spec JSON"] --> B["Spec module"] --> C{"IsFinalizedBlock"} --> D["Finalized responses"] --> E["Cache layer"] --> F["Integrators"]
  C --> G["Conflict module"]
  subgraph Legend
    direction LR
    _cfg["Config"] ~~~ _mod["Module"] ~~~ _dec{"Decision"}
  end
Loading
High-Level Assessment

The following are alternative approaches to this PR:

1. Use chain-native finalized markers where available
  • ➕ Eliminates guesswork and reduces unnecessary finalized-data lag
  • ➕ Adapts automatically across forks/upgrades (e.g., PoS epochs/commitments)
  • ➖ Not all chains expose a strong finalized concept in their RPC
  • ➖ May require per-chain RPC parsing and additional call paths (more maintenance/test surface)
2. Make finalized-distance governance-tunable per deployment/environment
  • ➕ Allows faster response to reorg incidents without code/PR changes
  • ➕ Can differ between mainnet/testnet or between provider risk profiles
  • ➖ Still manual and error-prone without strong guidance/validation
  • ➖ Adds operational overhead and potential config drift
3. Add validation/guardrails (min distances) in spec tooling/tests
  • ➕ Prevents obviously unsafe defaults (e.g., 0/1 on PoW chains) from being merged again
  • ➕ Creates a documented rationale as code (per-chain constraints)
  • ➖ Requires defining and maintaining policy thresholds
  • ➖ May block legitimate edge cases unless escape hatches exist

Recommendation: Proceed with the PR’s approach (raising distances) as the lowest-risk, immediately effective fix for incorrect finalization semantics. Consider a follow-up to add guardrails/tests that fail when probabilistic-finality chains are configured below a safe minimum, and selectively adopt chain-native finalized markers where the RPC provides them.

Files changed (9) +18 / -18

Bug fix (7) +14 / -14
bch.jsonRaise BCH finalized-data distance to 15 blocks +2/-2

Raise BCH finalized-data distance to 15 blocks

• Updates BCH spec instances to treat blocks as finalized only after 15 confirmations instead of 1. This reduces the risk of caching and serving orphaned data as immutable during PoW reorgs.

specs/mainnet-1/specs/bch.json

bsc.jsonRaise BSC finalized-data distance to 3 blocks +2/-2

Raise BSC finalized-data distance to 3 blocks

• Updates BSC spec instances to require a 3-block distance from head before considering data finalized (was 0). This better matches practical BSC finality and reduces head-reorg exposure.

specs/mainnet-1/specs/bsc.json

doge.jsonRaise DOGE finalized-data distance to 40 blocks +2/-2

Raise DOGE finalized-data distance to 40 blocks

• Updates DOGE spec instances to require 40 confirmations for finalized data (was 1). This aligns finalization semantics with real PoW reorg depth expectations and common operational standards.

specs/mainnet-1/specs/doge.json

filecoin.jsonRaise Filecoin finalized-data distance to 5 epochs +2/-2

Raise Filecoin finalized-data distance to 5 epochs

• Updates Filecoin spec instances to treat data as finalized after 5 epochs instead of 1. This provides margin against short tipset reorgs while remaining close to expected fast finality behavior.

specs/mainnet-1/specs/filecoin.json

litecoin.jsonRaise LTC finalized-data distance to 13 blocks +2/-2

Raise LTC finalized-data distance to 13 blocks

• Updates Litecoin spec instances to require 13 confirmations for finalized data (was 1). This addresses observed deeper reorg behavior and reduces the chance of treating reorgable blocks as final.

specs/mainnet-1/specs/litecoin.json

polygon.jsonRaise Polygon finalized-data distance to 10 blocks +2/-2

Raise Polygon finalized-data distance to 10 blocks

• Updates Polygon spec instances to treat blocks as finalized only after 10 blocks instead of 1. This reduces exposure to short head reorgs before milestone-style anchoring/finality mechanisms.

specs/mainnet-1/specs/polygon.json

tron.jsonRaise TRON finalized-data distance to 20 blocks +2/-2

Raise TRON finalized-data distance to 20 blocks

• Updates TRON spec instances to require a 20-block distance for finalized data (was 4). This increases safety against short-lived reorgs and aligns finalized semantics with stronger confirmation confidence.

specs/mainnet-1/specs/tron.json

Other (2) +4 / -4
bch.jsonAlign testnet-2 BCH finalized-data distance to 15 blocks +2/-2

Align testnet-2 BCH finalized-data distance to 15 blocks

• Updates BCH spec instances on testnet-2 to match the 15-block finalized-data distance used on mainnet-1. Keeps finalized semantics consistent across environments for integrators and testing.

specs/testnet-2/specs/bch.json

bsc.jsonAlign testnet-2 BSC finalized-data distance to 3 blocks +2/-2

Align testnet-2 BSC finalized-data distance to 3 blocks

• Updates BSC spec instances on testnet-2 to match the 3-block finalized-data distance used on mainnet-1. Reduces head-reorg sensitivity in testnet behavior to better mirror production semantics.

specs/testnet-2/specs/bsc.json

@qodo-code-review

Copy link
Copy Markdown

Code Review by Qodo

🐞 Bugs (1) 📘 Rule violations (1) 📜 Skill insights (0)

Grey Divider


Remediation recommended

1. block_distance_for_finalized_data docs missing 📘 Rule violation ⚙ Maintainability
Description
This PR changes spec finalization behavior by increasing block_distance_for_finalized_data, but no
corresponding specs/*_test.md GIVEN–WHEN–THEN test documentation update is included. This can
leave spec behavior changes undocumented and harder to verify/audit.
Code

specs/mainnet-1/specs/bch.json[15]

+                "block_distance_for_finalized_data": 15,
Evidence
PR Compliance ID 5 requires updating specs/*_test.md GIVEN–WHEN–THEN narratives when specs change.
The modified spec files show updated block_distance_for_finalized_data values (e.g., BCH and BSC),
indicating a behavior change that should be reflected in the specs test documentation.

AGENTS.md: Specs Test Documentation Must Be Updated with GIVEN–WHEN–THEN Narratives When Changing Specs
specs/mainnet-1/specs/bch.json[12-18]
specs/mainnet-1/specs/bsc.json[13-18]

Agent prompt
The issue below was found during a code review. Follow the provided context and guidance below and implement a solution

## Issue description
Spec behavior changed (`block_distance_for_finalized_data` increased for probabilistic-finality chains), but the required specs test documentation (`specs/*_test.md`) was not updated with GIVEN–WHEN–THEN narratives.

## Issue Context
These spec values affect what the system treats as “finalized” data. The compliance checklist requires keeping specs test documentation aligned whenever specs change.

## Fix Focus Areas
- specs/mainnet-1/specs/bch.json[12-18]
- specs/mainnet-1/specs/bsc.json[13-18]
- specs/mainnet-1/specs/doge.json[13-18]
- specs/mainnet-1/specs/filecoin.json[10-16]
- specs/mainnet-1/specs/litecoin.json[13-18]
- specs/mainnet-1/specs/polygon.json[13-18]
- specs/mainnet-1/specs/tron.json[9-15]
- specs/testnet-2/specs/bch.json[12-18]
- specs/testnet-2/specs/bsc.json[13-18]
- specs/finalized_data_test.md[1-200]

ⓘ Copy this prompt and use it to remediate the issue with your preferred AI generation tools


2. Stale testnet genesis values 🐞 Bug ≡ Correctness
Description
specs/testnet-2/specs/bsc.json raises block_distance_for_finalized_data to 3 for BSC/BSCT, but
specs/testnet-2/genesis_json/genesis.json still embeds 0 for those same spec indexes. Any
environment bootstrapped from the checked-in testnet-2 genesis will keep the old “head is finalized”
behavior, undermining this PR’s intended safety change for testnet-2.
Code

specs/testnet-2/specs/bsc.json[R15-16]

+                "block_distance_for_finalized_data": 3,
                "blocks_in_finalization_proof": 1,
Evidence
The updated testnet-2 spec proposal sets block_distance_for_finalized_data to 3 for both BSC and
BSCT, but the checked-in testnet-2 genesis JSON still contains `block_distance_for_finalized_data:
0 for index: "BSC" and index: "BSCT"`, leaving the repository inconsistent.

specs/testnet-2/specs/bsc.json[7-18]
specs/testnet-2/specs/bsc.json[51-63]
specs/testnet-2/genesis_json/genesis.json[273067-273087]
specs/testnet-2/genesis_json/genesis.json[274592-274612]

Agent prompt
The issue below was found during a code review. Follow the provided context and guidance below and implement a solution

## Issue description
The testnet-2 spec proposal JSON updates BSC/BSCT `block_distance_for_finalized_data` to 3, but the committed testnet-2 genesis artifact still has `block_distance_for_finalized_data: 0` for `index: "BSC"` and `index: "BSCT"`. This leaves the repo with two contradictory sources of truth.

## Issue Context
Even if specs are normally delivered via governance, the repo also carries a prebuilt `specs/testnet-2/genesis_json/genesis.json` artifact. If operators/tools use that genesis file to bootstrap a testnet-2 node, they will not get the updated finalization distance.

## Fix Focus Areas
- specs/testnet-2/genesis_json/genesis.json[273067-273087]
- specs/testnet-2/genesis_json/genesis.json[274592-274612]
- specs/testnet-2/specs/bsc.json[7-18]
- specs/testnet-2/specs/bsc.json[51-63]

## What to change
- Update/regenerate `specs/testnet-2/genesis_json/genesis.json` so that for `index: "BSC"` and `index: "BSCT"`, `block_distance_for_finalized_data` is `3` (matching the updated spec proposal JSON).
- If genesis artifacts are meant to be generated outside PRs, consider removing/updating the committed genesis artifact or documenting that it is not guaranteed to track `specs/testnet-2/specs/*.json`.

ⓘ Copy this prompt and use it to remediate the issue with your preferred AI generation tools


Grey Divider

Qodo Logo

Comment thread specs/mainnet-1/specs/bch.json
Comment thread specs/testnet-2/specs/bsc.json
@yagop

yagop commented Jul 10, 2026

Copy link
Copy Markdown
Author

Note for maintainers: AGENTS.md says specs/ is a git subtree synced from lavanet/lava-config — if that repo is the canonical home of these JSONs, this change should be mirrored there so it survives the next git subtree pull.

Related field worth considering as a follow-up: blocks_in_finalization_proof is 1 for BSC/DOGE/LTC/BCH. On a 450ms chain like BSC, a 1-block signed-hash window means two providers polled moments apart rarely sign an overlapping block, so cross-provider conflict detection has little to compare. Raising BSC to 3 (matching TRON/Polygon/Filecoin) would strengthen the fraud detection this PR's distances feed into.

yagop added a commit to yagop/lava-specs that referenced this pull request Jul 26, 2026
…ty chains

Values below real reorg depth let orphaned blocks be treated as
finalized: cached as immutable and honest providers signing
conflicting hashes look fraudulent to the conflict module.
Risks double-credited transactions and data loss for integrators.

DOGE 1->40, LTC 1->13, BCH 1->15, POLYGON 1->10, FVM 1->5, BSC 0->3.
Mirrors lavanet/lava#2316 (TRON already at 20 here).
nimrod-teich pushed a commit to Magma-Devs/lava-specs that referenced this pull request Aug 6, 2026
…ty chains

Values below real reorg depth let orphaned blocks be treated as
finalized: cached as immutable and honest providers signing
conflicting hashes look fraudulent to the conflict module.
Risks double-credited transactions and data loss for integrators.

DOGE 1->40, LTC 1->13, BCH 1->15, POLYGON 1->10, FVM 1->5, BSC 0->3.
Mirrors lavanet/lava#2316 (TRON already at 20 here).
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Projects

None yet

Development

Successfully merging this pull request may close these issues.

block_distance_for_finalized_data is set below real reorg depth on several chains

1 participant