Skip to content

fix(anvil): sync state snapshots with reset and revert#14317

Closed
solanaXpeter wants to merge 2 commits intofoundry-rs:masterfrom
solanaXpeter:fix-anvil-sync-state-snapshots
Closed

fix(anvil): sync state snapshots with reset and revert#14317
solanaXpeter wants to merge 2 commits intofoundry-rs:masterfrom
solanaXpeter:fix-anvil-sync-state-snapshots

Conversation

@solanaXpeter
Copy link
Copy Markdown
Contributor

Motivation

State snapshot metadata can diverge from backend state. anvil_reset clears chain and DB state without clearing active_state_snapshots, and revert_state_snapshot removed metadata before the DB revert succeeded. That can leave anvil_metadata reporting stale snapshots and make evm_revert depend on a partially applied rollback path.

Solution

Clear active_state_snapshots in both reset paths, and only remove a snapshot entry after the DB revert succeeds. When the backing snapshot block or DB snapshot is already gone, drop the stale metadata entry and return false without mutating chain state. Added regression tests for failed revert, in-memory reset, and fork reset paths.

PR Checklist

  • Added Tests
  • Added Documentation
  • Breaking changes

Comment on lines +2256 to +2261
let Some(block) = self.block_by_hash(hash).await? else {
self.active_state_snapshots.lock().remove(&id);
return Ok(false);
};

let reset_time = block.header.timestamp();
self.time.reset(reset_time);
if !self.db.write().await.revert_state(id, RevertStateSnapshotAction::RevertRemove) {
Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Would we rather need to revert_state any case ? (even if self.block_by_hash(hash).await? is None)

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@mablr Good point, I agree this branch still needs handling. I think we should drop the DB snapshot and return false when block_by_hash(hash) is None, since calling revert_state there would leave things half-reverted. Do you think that makes sense?

Copy link
Copy Markdown
Collaborator

@figtracer figtracer left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

i think we don't need this now tbf, pending another review

Copy link
Copy Markdown
Collaborator

@mablr mablr left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yes I think it's not necessary to apply these changes, as Anvil's internals are going to be completely refactored soon.

Thanks for the effort @solanaXpeter 👍

@mablr mablr closed this Apr 20, 2026
@github-project-automation github-project-automation Bot moved this to Done in Foundry Apr 20, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

Status: Done

Development

Successfully merging this pull request may close these issues.

3 participants