mirror of
https://github.com/golang/go.git
synced 2026-01-29 07:02:05 +03:00
cmd/link: generate DWARF for moduledata
Fixes #76731 Change-Id: I5c686c91af8543b57880a89d30393912ef1958ad Reviewed-on: https://go-review.googlesource.com/c/go/+/727760 Auto-Submit: Ian Lance Taylor <iant@golang.org> Reviewed-by: Alessandro Arzilli <alessandro.arzilli@gmail.com> Reviewed-by: Florian Lehner <lehner.florian86@gmail.com> Reviewed-by: David Chase <drchase@google.com> Reviewed-by: Dmitri Shuralyov <dmitshur@google.com> LUCI-TryBot-Result: Go LUCI <golang-scoped@luci-project-accounts.iam.gserviceaccount.com>
This commit is contained in:
committed by
Gopher Robot
parent
44a39c9dac
commit
b5f6816cea
@@ -156,10 +156,102 @@ func testDWARF(t *testing.T, buildmode string, expectDWARF bool, env ...string)
|
||||
if !strings.HasSuffix(line.File.Name, wantFile) || line.Line != wantLine {
|
||||
t.Errorf("%#x is %s:%d, want %s:%d", addr, line.File.Name, line.Line, filepath.Join("...", wantFile), wantLine)
|
||||
}
|
||||
|
||||
if buildmode != "c-archive" {
|
||||
testModuledata(t, d)
|
||||
}
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
// testModuledata makes sure that runtime.firstmoduledata exists
|
||||
// and has a type. Issue #76731.
|
||||
func testModuledata(t *testing.T, d *dwarf.Data) {
|
||||
const symName = "runtime.firstmoduledata"
|
||||
|
||||
r := d.Reader()
|
||||
for {
|
||||
e, err := r.Next()
|
||||
if err != nil {
|
||||
t.Error(err)
|
||||
return
|
||||
}
|
||||
if e == nil {
|
||||
t.Errorf("did not find DWARF entry for %s", symName)
|
||||
return
|
||||
}
|
||||
|
||||
switch e.Tag {
|
||||
case dwarf.TagVariable:
|
||||
// carry on after switch
|
||||
case dwarf.TagCompileUnit, dwarf.TagSubprogram:
|
||||
continue
|
||||
default:
|
||||
r.SkipChildren()
|
||||
continue
|
||||
}
|
||||
|
||||
nameIdx, typeIdx := -1, -1
|
||||
for i := range e.Field {
|
||||
f := &e.Field[i]
|
||||
switch f.Attr {
|
||||
case dwarf.AttrName:
|
||||
nameIdx = i
|
||||
case dwarf.AttrType:
|
||||
typeIdx = i
|
||||
}
|
||||
}
|
||||
if nameIdx == -1 {
|
||||
// unnamed variable?
|
||||
r.SkipChildren()
|
||||
continue
|
||||
}
|
||||
nameStr, ok := e.Field[nameIdx].Val.(string)
|
||||
if !ok {
|
||||
// variable name is not a string?
|
||||
r.SkipChildren()
|
||||
continue
|
||||
}
|
||||
if nameStr != symName {
|
||||
r.SkipChildren()
|
||||
continue
|
||||
}
|
||||
|
||||
if typeIdx == -1 {
|
||||
t.Errorf("%s has no DWARF type", symName)
|
||||
return
|
||||
}
|
||||
off, ok := e.Field[typeIdx].Val.(dwarf.Offset)
|
||||
if !ok {
|
||||
t.Errorf("unexpected Go type %T for DWARF type for %s; expected %T", e.Field[typeIdx].Val, symName, dwarf.Offset(0))
|
||||
return
|
||||
}
|
||||
|
||||
typeInfo, err := d.Type(off)
|
||||
if err != nil {
|
||||
t.Error(err)
|
||||
return
|
||||
}
|
||||
|
||||
typeName := typeInfo.Common().Name
|
||||
if want := "runtime.moduledata"; typeName != want {
|
||||
t.Errorf("type of %s is %s, expected %s", symName, typeName, want)
|
||||
}
|
||||
for {
|
||||
typedef, ok := typeInfo.(*dwarf.TypedefType)
|
||||
if !ok {
|
||||
break
|
||||
}
|
||||
typeInfo = typedef.Type
|
||||
}
|
||||
if _, ok := typeInfo.(*dwarf.StructType); !ok {
|
||||
t.Errorf("type of %s is %T, expected %T", symName, typeInfo, dwarf.StructType{})
|
||||
}
|
||||
|
||||
return
|
||||
}
|
||||
}
|
||||
|
||||
func TestDWARF(t *testing.T) {
|
||||
testDWARF(t, "", true)
|
||||
if !testing.Short() {
|
||||
|
||||
@@ -2036,7 +2036,7 @@ func dwarfGenerateDebugInfo(ctxt *Link) {
|
||||
t := d.ldr.SymType(idx)
|
||||
switch {
|
||||
case t.IsRODATA(), t.IsDATA(), t.IsNOPTRDATA(),
|
||||
t == sym.STYPE, t == sym.SBSS, t == sym.SNOPTRBSS, t == sym.STLSBSS:
|
||||
t == sym.STYPE, t == sym.SBSS, t == sym.SNOPTRBSS, t == sym.STLSBSS, t == sym.SMODULEDATA:
|
||||
// ok
|
||||
default:
|
||||
continue
|
||||
|
||||
Reference in New Issue
Block a user