Skip to content

lint: enable the remaining modernize analyzers #22199

Description

@yperbasis

Follow-up to #22197, which enabled the modernize linter with the analyzers that had an existing backlog disabled via settings.modernize.disable in .golangci.yml.

Context: #22163 was the fourth manual strings.Splitstrings.SplitSeq pass (after #17910, #17997, #19175), and without mechanical enforcement the class churns — e.g. the same line in execution/rlp/internal/rlpstruct/rlpstruct.go was converted in #17910, reverted by the geth-sync commit (#18933), and re-converted in #19175. Lint enforcement stops that cycle; this issue tracks extending it to the rest of the modernize suite.

Goal

Clear each disabled analyzer's backlog and remove it from the disable list — one analyzer (or a few small ones) per PR to keep review manageable. Done when settings.modernize.disable is empty.

Workflow per analyzer

  1. Remove the analyzer from settings.modernize.disable in .golangci.yml.
  2. go tool golangci-lint run --enable-only modernize --fix applies gopls's suggested fixes; review every hunk (see caveats below), especially under cl/ (consensus-critical — see cl/CLAUDE.md).
  3. make lint (repeat until clean — it is non-deterministic) and make erigon integration.

Checklist

Finding counts as of #22197; regenerate with go tool golangci-lint run --enable-only modernize --max-issues-per-linter 0 --max-same-issues 0 after temporarily emptying the disable list.

  • rangeint — 1002 findings
  • any — 190
  • waitgroupgo — 82
  • slicesbackward — 51
  • minmax — 21
  • forvar — 12
  • atomictypes — 12
  • mapsloop — 11
  • stringscut — 6
  • reflecttypefor — 6
  • testingcontext — 5
  • slicescontains — 3
  • omitzero — 3
  • stditerators — 2
  • slicessort — 2
  • stringscutprefix — 1
  • stringsbuilder — 1

Count is not difficulty: any (190) and forvar (12) are pure textual modernizations the autofix handles safely, while omitzero (3) needs per-site semantic review.

Not purely mechanical — review with extra care

  • omitzero: switching struct tags from omitempty to omitzero changes the JSON wire format for zero-valued struct fields; check API compatibility per site.
  • testingcontext: t.Context() is canceled when the test ends, unlike context.Background(); verify nothing in the test or its cleanup relies on the context outliving the test body.
  • minmax: the min/max builtins have defined NaN and signed-zero semantics for floats that can differ from the original comparison chain.
  • rangeint: for i := range n evaluates n once and disallows loop-variable mutation affecting iteration; not equivalent if the body modifies i or the bound.

Notes

  • Files behind build tags (e.g. //go:build leak) are invisible to the linter, so their backlogs must be found manually with git grep and won't be enforced (see the leak-test site fixed in golangci: enable modernize linter #22197).
  • Four more analyzers (appendclipped, bloop, fmtappendf, slicesdelete) are excluded from the suite upstream by gopls (not nil-preserving, benchmark-skewing, or clarity concerns) and are not available through the golangci-lint modernize linter — out of scope here.

Metadata

Metadata

Assignees

Type

No type

Fields

No fields configured for issues without a type.

Projects

No projects

Relationships

None yet

Development

No branches or pull requests

Issue actions