{"record":{"id":"d2f128efe9e44425","repo":"golang/go","slug":"multiple-toplevel-scopes","errorCode":null,"errorMessage":"multiple toplevel scopes","messagePattern":"multiple toplevel scopes","errorType":"exception","errorClass":null,"httpStatus":null,"severity":"error","filePath":"src/cmd/internal/dwarf/dwarf.go","lineNumber":1192,"sourceCode":"\tscopes := make([]Scope, len(s.Scopes), len(s.Scopes))\n\tpvars := inlinedVarTable(&s.InlCalls)\n\tfor k, s := range s.Scopes {\n\t\tvar pruned Scope = Scope{Parent: s.Parent, Ranges: s.Ranges}\n\t\tfor i := 0; i < len(s.Vars); i++ {\n\t\t\t_, found := pvars[s.Vars[i]]\n\t\t\tif !found {\n\t\t\t\tpruned.Vars = append(pruned.Vars, s.Vars[i])\n\t\t\t}\n\t\t}\n\t\tslices.SortFunc(pruned.Vars, byChildIndexCmp)\n\t\tscopes[k] = pruned\n\t}\n\n\ts.dictIndexToOffset = putparamtypes(ctxt, s, scopes, fnabbrev)\n\n\tvar encbuf [20]byte\n\tif putscope(ctxt, s, scopes, 0, fnabbrev, encbuf[:0]) < int32(len(scopes)) {\n\t\treturn errors.New(\"multiple toplevel scopes\")\n\t}\n\treturn nil\n}\n\n// Emit DWARF attributes and child DIEs for an 'abstract' subprogram.\n// The abstract subprogram DIE for a function contains its\n// location-independent attributes (name, type, etc). Other instances\n// of the function (any inlined copy of it, or the single out-of-line\n// 'concrete' instance) will contain a pointer back to this abstract\n// DIE (as a space-saving measure, so that name/type etc doesn't have\n// to be repeated for each inlined copy).\nfunc PutAbstractFunc(ctxt Context, s *FnState) error {\n\tif logDwarf {\n\t\tctxt.Logf(\"PutAbstractFunc(%v)\\n\", s.Absfn)\n\t}\n\n\tabbrev := DW_ABRV_FUNCTION_ABSTRACT\n\tUleb128put(ctxt, s.Absfn, int64(abbrev))","sourceCodeStart":1174,"sourceCodeEnd":1210,"githubUrl":"https://github.com/golang/go/blob/b6b368adc57c96c3151d224d172029f233ead2c3/src/cmd/internal/dwarf/dwarf.go#L1174-L1210","documentation":"Thrown by putPrunedScopes in cmd/internal/dwarf when emitting DWARF variable scopes for a function. putscope starts at scope index 0 (the toplevel function scope) and is expected to consume scopes recursively, returning the index of the next unprocessed scope. If it returns less than len(scopes), there is more than one top-level scope for a single function — a structural invariant violation in the compiler's scope data, since each function must have exactly one outermost lexical scope.","triggerScenarios":"This is essentially an internal compiler assertion surfaced during DWARF generation. It fires when the compiler's scope tree for a function has multiple roots (more than one scope with Parent == -1 or no enclosing scope). It can be triggered by unusual control-flow + generics/inlining combinations that confuse scope assignment. Almost never user-facing unless the user's code happens to hit a compiler bug.","commonSituations":"Hitting a Go compiler bug in DWARF scope generation — most often seen with heavy use of generics instantiation, inlined closures, or very recent/unstable Go versions. Building with -ldflags=-w or similar may avoid it but masks the underlying bug. Reproducible across builds of the same source with the same toolchain.","solutions":["File a bug at https://go.dev/issue with a minimal reproducer; this is almost always a compiler/DWARF bug rather than user error.","As a workaround, build with -gcflags=-l (disable inlining) or -ldflags=-w (strip DWARF) to bypass the failing path.","Try a different Go version — newer tip often has the fix; older stable may avoid the regression.","Reduce the offending function (often a heavily-generic one) to isolate the trigger for the bug report."],"exampleFix":"# before\n$ go build ./...\n# -> multiple toplevel scopes\n\n# after (workaround while bug is open)\n$ go build -ldflags=-w ./...\n# or\n$ go build -gcflags=-l ./...","handlingStrategy":"fallback","validationCode":"// No caller-side prevention: this is a compiler-internal assertion.\n// Detect the toolchain version to avoid known-bad releases.\nfunc toolchainHasDwarfScopeBug() bool {\n    // example predicate; substitute the range from the upstream issue\n    v := runtime.Version()\n    return strings.Contains(v, \"devel\") && strings.Contains(v, \"2024-01\")\n}","typeGuard":null,"tryCatchPattern":"// If the error surfaces during release builds, fall back to stripping DWARF.\nout, err := build()\nif err != nil && strings.Contains(err.Error(), \"multiple toplevel scopes\") {\n    return buildWithFlags(\"-ldflags\", \"-w\")\n}","preventionTips":["Pin the toolchain in go.mod and avoid tip/devel for production builds.","Keep a minimal reproducer ready to attach to the upstream Go issue.","Apply -ldflags=-w as a temporary workaround while the bug is fixed upstream."],"tags":["go-toolchain","dwarf","compiler-internal","debug-info","bug"],"backgroundTag":null,"analyzedSha":"b6b368adc57c96c3151d224d172029f233ead2c3","analyzedAt":"2026-08-12T00:22:02.250Z","schemaVersion":2},"datasetVersion":"2026-08-13T04:17:16.726Z"}