1
0
mirror of https://github.com/golang/go synced 2024-11-23 10:10:02 -07:00

cmd/link: set .dynsym info field

.dynsym section info field is the index of first non-local symbol, mean
the number of local symbols.

The go linker have never ever set it before, so just set it.

Fixes #33358

Change-Id: Ifde2deb7c15471b04d565861f5d81daffb0c0d3d
Reviewed-on: https://go-review.googlesource.com/c/go/+/187979
Run-TryBot: Cuong Manh Le <cuong.manhle.vn@gmail.com>
TryBot-Result: Gobot Gobot <gobot@golang.org>
Reviewed-by: Ian Lance Taylor <iant@golang.org>
This commit is contained in:
LE Manh Cuong 2019-07-31 11:45:32 +07:00 committed by Ian Lance Taylor
parent c96d794f66
commit 12dbd20a50
2 changed files with 90 additions and 2 deletions

View File

@ -1942,8 +1942,17 @@ func Asmbelf(ctxt *Link, symo int64) {
sh.addralign = uint64(ctxt.Arch.RegSize)
sh.link = uint32(elfshname(".dynstr").shnum)
// sh->info = index of first non-local symbol (number of local symbols)
shsym(sh, ctxt.Syms.Lookup(".dynsym", 0))
// sh.info is the index of first non-local symbol (number of local symbols)
s := ctxt.Syms.Lookup(".dynsym", 0)
i := uint32(0)
for sub := s; sub != nil; sub = sub.Sub {
i++
if !sub.Attr.Local() {
sh.info = i
break
}
}
shsym(sh, s)
sh = elfshname(".dynstr")
sh.type_ = SHT_STRTAB

View File

@ -0,0 +1,79 @@
// +build cgo
// Copyright 2019 The Go Authors. All rights reserved.
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.
package ld
import (
"debug/elf"
"internal/testenv"
"io/ioutil"
"os"
"os/exec"
"path/filepath"
"testing"
)
func TestDynSymShInfo(t *testing.T) {
t.Parallel()
testenv.MustHaveGoBuild(t)
dir, err := ioutil.TempDir("", "go-build-issue33358")
if err != nil {
t.Fatal(err)
}
defer os.RemoveAll(dir)
const prog = `
package main
import "net"
func main() {
net.Dial("", "")
}
`
src := filepath.Join(dir, "issue33358.go")
if err := ioutil.WriteFile(src, []byte(prog), 0666); err != nil {
t.Fatal(err)
}
binFile := filepath.Join(dir, "issue33358")
cmd := exec.Command(testenv.GoToolPath(t), "build", "-o", binFile, src)
if out, err := cmd.CombinedOutput(); err != nil {
t.Fatalf("%v: %v:\n%s", cmd.Args, err, out)
}
fi, err := os.Open(binFile)
if err != nil {
t.Fatalf("failed to open built file: %v", err)
}
elfFile, err := elf.NewFile(fi)
if err != nil {
t.Skip("The system may not support ELF, skipped.")
}
section := elfFile.Section(".dynsym")
if section == nil {
t.Fatal("no dynsym")
}
symbols, err := elfFile.DynamicSymbols()
if err != nil {
t.Fatalf("failed to get dynamic symbols: %v", err)
}
var numLocalSymbols uint32
for i, s := range symbols {
if elf.ST_BIND(s.Info) != elf.STB_LOCAL {
numLocalSymbols = uint32(i + 1)
break
}
}
if section.Info != numLocalSymbols {
t.Fatalf("Unexpected sh info, want greater than 0, got: %d", section.Info)
}
}