[sergo] Sergo Report: 34th-Linter lenstringsplit Audit + ctxbackground Scope-Boundary - 2026-06-24 #41165
Closed
Replies: 1 comment
-
|
This discussion has been marked as outdated by Sergo - Serena Go Expert. A newer discussion is available at Discussion #41378. |
Beta Was this translation helpful? Give feedback.
0 replies
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Uh oh!
There was an error while loading. Please reload this page.
-
Executive Summary
Run R46 detected a registry delta (33 → 34 analyzers) and audited the new 34th linter
lenstringsplit, plus a second never-deep-audited linterctxbackground. Both yielded distinct, single-file precision bugs with confirming test gaps. Filed 2 issues; cached reconciliation surfaced no new syntactic holdout (the 5 known ones remain open and unfixed).lenstringsplit)doc.goheader#41163,#41164)sg45a1→ #40947Tool & Registry Updates
grep -c Analyzer cmd/linters/main.go= 34. The new linter was identified via the doc-omitted-minus-known detector:doc.goomits 5 registered linters; four (hardcodedfilepath,sprintferrdot,sprintferrorsnew,wgdonenotdeferred) are known prior additions, leavinglenstringsplitas the genuinely new, never-referenced one.Strategy (50/50 Split)
New exploration (50%) — fresh audits of unaudited linters. Target the 34th linter
lenstringsplitand the never-deep-auditedctxbackground. Success criterion: a demonstrable correctness/precision bug backed by a concrete input and a test-coverage gap.Cached reuse (50%) —
syntactic_stdlib_matchreconcile + landing recheck. Re-grep allident.Name ==/!= "pkg"sites and recheck prior landings. Success criterion: confirm holdout status (open ≠ fixed) without filing duplicates.Findings
#41163 — lenstringsplit: empty raw-string separator escapes the non-empty guard (FP + wrong autofix)
hasProvablyNonEmptySeparator(pkg/linters/lenstringsplit/lenstringsplit.go:104-116) has a*ast.BasicLitfast-path that compares the raw source token textlit.Value != "\"\""instead of the decoded value. An empty raw string separator`` haslit.Valueof two backticks, which is `!= """"`, so it is treated as "provably non-empty".len(strings.Split(s, ``))is flagged (the exact empty-separator case the linter intends to exclude) and the suggested rewritestrings.Count(s, ``)+1is not semantically equivalent (Split("")→ runes, len = N;Count("")+1= N+2).`` to""and reject it — but it is unreachable.testdatacountRunesexercises only the double-quoted""form.constant.StringVal(handles all string-constant forms uniformly).#41164 — ctxbackground: enclosing-scope walk only inspects *ast.FuncDecl, skipping FuncLit (FN for closures with own ctx)
The linter resolves the enclosing function's ctx parameter with
cur.Enclosing((*ast.FuncDecl)(nil))(pkg/linters/ctxbackground/ctxbackground.go:43), which steps over any intervening*ast.FuncLit.context.Background()inside a closure that receives its ownctx context.Contextis missed — the walk jumps to the outerFuncDecl, finds no ctx, andbreaks. The nearest function scope is exactly the linter's target.go func(){ context.Background() }()inside a ctx-receiving function, the call is flagged and rewritten to the outer captured ctx — often semantically wrong for goroutines that intentionally outlive the request.testdatahas no closure/FuncLit cases.Enclosing(FuncDecl, FuncLit)and resolve the nearest function scope via*ast.FuncType.wgdonenotdeferred).Cached Reconciliation (no new issue)
Holdout & landing status
ident.Nameholdouts STILL open + unfixed in code: Linter precision: migrate the 3 remaining CI-enforced linters that match stdlib packages by identifier name to astutil.IsPkgSele [Content truncated due to length] #40243 (osexitinlibrary:59,fprintlnsprintf:144,errstringmatch:100), Linter precision: two newest linters (fileclosenotdeferred, contextcancelnotdeferred) match stdlib packages by identifier name — [Content truncated due to length] #40435 (contextcancelnotdeferred:138,fileclosenotdeferred:172). Open ≠ fixed — confirmed via re-grep.tolowerequalfoldnow fully type-resolved (IsPkgSelectorat :259/:274 +collectCaseConvAliases) → tolowerequalfold precision: strings.ToLower/ToUpper matched by identifier name "strings" — shadowing FP + alias-import FN in a C [Content truncated due to length] #40580 landed in code (issue still open, team rarely auto-closes).Generated Tasks
#41163— Remove the BasicLit text-compare fast-path inlenstringsplit; rely on decoded constant value. Effort: small.#41164— Makectxbackgroundconsider FuncLit scope boundaries (Enclosing(FuncDecl, FuncLit)+*ast.FuncTypehelper). Effort: small–medium.Metrics & Historical Context
scope_boundary_funclitpattern now confirmed twice (wgdonenotdeferred wgdonenotdeferred precision: non-deferred wg.Done() inside a goroutine launched in a loop escapes detection (FuncLit scope bound [Content truncated due to length] #40947 stack-walk-no-break; ctxbackgroundEnclosing(FuncDecl)-only) — a recurring, high-yield probe class.Recommendations & Next-Run Focus (R47)
#41163,#41164, tolowerequalfold precision: strings.ToLower/ToUpper matched by identifier name "strings" — shadowing FP + alias-import FN in a C [Content truncated due to length] #40580 (may close).grep -c Analyzer+ doc-omitted-minus-known detector.scope_boundary_funclit: any linter resolving enclosing-function context that filters only*ast.FuncDeclor walks past FuncLit.sortslice,execcommandwithoutcontext,hardcodedfilepath,manualmutexunlock,panicinlibrarycode.ctxbackgroundhas test-skip but nonolint— evaluate vs the Threshold linters: excessivefuncparams lints test files (every sibling FuncDecl linter skips them); largefunc & excessivefuncpar [Content truncated due to length] #40734 theme.References: §28076275497
Beta Was this translation helpful? Give feedback.
All reactions