Skip to content

feat(lint): add mapping-deletion detector#15202

Merged
mattsse merged 7 commits into
foundry-rs:masterfrom
0xMars42:feat/lint-mapping-deletion
Jun 27, 2026
Merged

feat(lint): add mapping-deletion detector#15202
mattsse merged 7 commits into
foundry-rs:masterfrom
0xMars42:feat/lint-mapping-deletion

Conversation

@0xMars42

Copy link
Copy Markdown
Contributor

Motivation

Adds the mapping-deletion detector from the forge lint parity checklist in #14381.

delete on a value whose type contains a mapping zeroes the non-mapping members but cannot enumerate the mapping's keys, so its entries are silently left in storage. The value looks reset while stale balances or flags remain reachable, which is a common accounting and access-control bug. solc does not warn on it.

Solution

A LateLintPass (med, mapping-deletion) that flags delete <expr> when the operand's type reaches a mapping, directly or through a nested struct or array. It walks the semantic type (Mapping short-circuits; Array/DynArray/Slice recurse into the element; Struct recurses into the fields) with a seen guard against recursive struct definitions.

This catches delete s, delete nested, delete arr, delete m[id], and delete arr[i], while leaving plain structs, scalar members, and single mapping-entry deletes (delete plainMap[k]) untouched.

Test

crates/lint/testdata/MappingDeletion.sol covers the five triggering shapes (direct struct, nested struct, array of structs, mapping value, array element) and three non-triggering ones (plain struct, scalar member, plain mapping entry), with the blessed .stderr. cargo test -p forge --test ui passes.

Addresses foundry-rs#14381.

delete on a value whose type contains a mapping zeroes the non-mapping
members but cannot clear the mapping entries, leaving stale storage. Flags
delete on a struct or array that reaches a mapping directly or through a
nested struct or array.

@mablr mablr left a comment

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

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

sgtm, just a smol wording nit

Comment thread crates/lint/src/sol/med/mapping_deletion.rs Outdated
figtracer
figtracer previously approved these changes Jun 18, 2026

@mablr mablr left a comment

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

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

LGTM.

Don't forget to add lint to the Medium Severity list in crates/lint/README.md.

mattsse
mattsse previously approved these changes Jun 20, 2026

@mattsse mattsse left a comment

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

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

LGTM

@0xMars42

Copy link
Copy Markdown
Contributor Author

Added to the Medium severity list in the README.

Comment thread crates/lint/src/sol/med/mapping_deletion.rs
0xMars42 and others added 2 commits June 22, 2026 18:22
Add a self-referential struct (Tree with a Tree[] children field and a
balances mapping) plus delete root, so the recursion guard in
ty_contains_mapping stays covered.
mablr
mablr previously approved these changes Jun 22, 2026

@mablr mablr left a comment

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

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

Conflict resolved, LGTM. Thanks @0xMars42 !

@mablr mablr enabled auto-merge (squash) June 22, 2026 16:47

@stevencartavia stevencartavia left a comment

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

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

it has another conflict :c

@mattsse mattsse disabled auto-merge June 27, 2026 06:05
@mattsse mattsse merged commit c5e44b5 into foundry-rs:master Jun 27, 2026
16 of 19 checks passed
@github-project-automation github-project-automation Bot moved this to Done in Foundry Jun 27, 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.

5 participants