1
0
mirror of https://github.com/golang/go synced 2024-11-18 20:04:52 -07:00

[dev.link] cmd/link: use new dodata on darwin/amd64

This probably breaks darwin/arm64. Will fix.

Change-Id: I8be168985124f971e9d8ab5bc95c303336dd705b
Reviewed-on: https://go-review.googlesource.com/c/go/+/230019
Reviewed-by: Than McIntosh <thanm@google.com>
This commit is contained in:
Cherry Zhang 2020-04-24 14:57:20 -04:00
parent c7a11099c9
commit b2fde1098a
4 changed files with 96 additions and 68 deletions

View File

@ -1355,8 +1355,7 @@ func (ctxt *Link) dodata2(symGroupType []sym.SymKind) {
//
// On darwin, we need the symbol table numbers for dynreloc.
if ctxt.HeadType == objabi.Hdarwin {
panic("not yet implemented for darwin")
// machosymorder(ctxt)
machosymorder(ctxt)
}
state.dynreloc2(ctxt)

View File

@ -45,7 +45,8 @@ func (ctxt *Link) dodata() {
//
// On darwin, we need the symbol table numbers for dynreloc.
if ctxt.HeadType == objabi.Hdarwin {
machosymorder(ctxt)
panic("not supported")
//machosymorder(ctxt)
}
state.dynreloc(ctxt)

View File

@ -8,6 +8,7 @@ import (
"bytes"
"cmd/internal/objabi"
"cmd/internal/sys"
"cmd/link/internal/loader"
"cmd/link/internal/sym"
"debug/macho"
"encoding/binary"
@ -216,7 +217,7 @@ const (
var nkind [NumSymKind]int
var sortsym []*sym.Symbol
var sortsym []loader.Sym
var nsortsym int
@ -743,106 +744,125 @@ func Asmbmacho(ctxt *Link) {
}
}
func symkind(s *sym.Symbol) int {
if s.Type == sym.SDYNIMPORT {
func symkind(ldr *loader.Loader, s loader.Sym) int {
if ldr.SymType(s) == sym.SDYNIMPORT {
return SymKindUndef
}
if s.Attr.CgoExport() {
if ldr.AttrCgoExport(s) {
return SymKindExtdef
}
return SymKindLocal
}
func addsym(ctxt *Link, s *sym.Symbol, name string, type_ SymbolType, addr int64, gotype *sym.Symbol) {
if s == nil {
return
func collectmachosyms(ctxt *Link) {
ldr := ctxt.loader
addsym := func(s loader.Sym) {
sortsym = append(sortsym, s)
nkind[symkind(ldr, s)]++
}
switch type_ {
default:
return
case DataSym, BSSSym, TextSym:
break
// Add special runtime.text and runtime.etext symbols.
// We've already included this symbol in Textp on darwin if ctxt.DynlinkingGo().
// See data.go:/textaddress
if !ctxt.DynlinkingGo() {
s := ldr.Lookup("runtime.text", 0)
if ldr.SymType(s) == sym.STEXT {
addsym(s)
}
s = ldr.Lookup("runtime.etext", 0)
if ldr.SymType(s) == sym.STEXT {
addsym(s)
}
}
if sortsym != nil {
sortsym[nsortsym] = s
nkind[symkind(s)]++
// Add text symbols.
for _, s := range ctxt.Textp2 {
addsym(s)
}
nsortsym++
}
type machoscmp []*sym.Symbol
func (x machoscmp) Len() int {
return len(x)
}
func (x machoscmp) Swap(i, j int) {
x[i], x[j] = x[j], x[i]
}
func (x machoscmp) Less(i, j int) bool {
s1 := x[i]
s2 := x[j]
k1 := symkind(s1)
k2 := symkind(s2)
if k1 != k2 {
return k1 < k2
shouldBeInSymbolTable := func(s loader.Sym) bool {
if ldr.AttrNotInSymbolTable(s) {
return false
}
name := ldr.RawSymName(s) // TODO: try not to read the name
if name == "" || name[0] == '.' {
return false
}
return true
}
return s1.Extname() < s2.Extname()
}
// Add data symbols and external references.
for s := loader.Sym(1); s < loader.Sym(ldr.NSym()); s++ {
if !ldr.AttrReachable(s) {
continue
}
t := ldr.SymType(s)
if t >= sym.SELFRXSECT && t < sym.SXREF { // data sections handled in dodata
if t == sym.STLSBSS {
// TLSBSS is not used on darwin. See data.go:allocateDataSections
continue
}
if !shouldBeInSymbolTable(s) {
continue
}
addsym(s)
}
switch t {
case sym.SDYNIMPORT, sym.SHOSTOBJ, sym.SUNDEFEXT, sym.SCONST:
addsym(s)
}
func machogenasmsym(ctxt *Link) {
genasmsym(ctxt, addsym)
for _, s := range ctxt.Syms.Allsym {
// Some 64-bit functions have a "$INODE64" or "$INODE64$UNIX2003" suffix.
if s.Type == sym.SDYNIMPORT && s.Dynimplib() == "/usr/lib/libSystem.B.dylib" {
if t == sym.SDYNIMPORT && ldr.SymDynimplib(s) == "/usr/lib/libSystem.B.dylib" {
// But only on macOS.
if machoPlatform == PLATFORM_MACOS {
switch n := s.Extname(); n {
switch n := ldr.SymExtname(s); n {
case "fdopendir":
switch objabi.GOARCH {
case "amd64":
s.SetExtname(n + "$INODE64")
ldr.SetSymExtname(s, n+"$INODE64")
case "386":
s.SetExtname(n + "$INODE64$UNIX2003")
ldr.SetSymExtname(s, n+"$INODE64$UNIX2003")
}
case "readdir_r", "getfsstat":
switch objabi.GOARCH {
case "amd64", "386":
s.SetExtname(n + "$INODE64")
ldr.SetSymExtname(s, n+"$INODE64")
}
}
}
}
if s.Type == sym.SDYNIMPORT || s.Type == sym.SHOSTOBJ || s.Type == sym.SUNDEFEXT {
if s.Attr.Reachable() {
addsym(ctxt, s, "", DataSym, 0, nil)
}
}
}
nsortsym = len(sortsym)
}
func machosymorder(ctxt *Link) {
ldr := ctxt.loader
// On Mac OS X Mountain Lion, we must sort exported symbols
// So we sort them here and pre-allocate dynid for them
// See https://golang.org/issue/4029
for i := range dynexp {
dynexp[i].Attr |= sym.AttrReachable
for _, s := range ctxt.dynexp2 {
if !ldr.AttrReachable(s) {
panic("dynexp symbol is not reachable")
}
}
machogenasmsym(ctxt)
sortsym = make([]*sym.Symbol, nsortsym)
nsortsym = 0
machogenasmsym(ctxt)
sort.Sort(machoscmp(sortsym[:nsortsym]))
for i := 0; i < nsortsym; i++ {
sortsym[i].Dynid = int32(i)
collectmachosyms(ctxt)
sort.Slice(sortsym[:nsortsym], func(i, j int) bool {
s1 := sortsym[i]
s2 := sortsym[j]
k1 := symkind(ldr, s1)
k2 := symkind(ldr, s2)
if k1 != k2 {
return k1 < k2
}
return ldr.SymExtname(s1) < ldr.SymExtname(s2) // Note: unnamed symbols are not added in collectmachosyms
})
for i, s := range sortsym {
ldr.SetSymDynid(s, int32(i))
}
}
@ -877,7 +897,7 @@ func machosymtab(ctxt *Link) {
symstr := ctxt.Syms.Lookup(".machosymstr", 0)
for i := 0; i < nsortsym; i++ {
s := sortsym[i]
s := ctxt.loader.Syms[sortsym[i]]
symtab.AddUint32(ctxt.Arch, uint32(symstr.Size))
export := machoShouldExport(ctxt, s)

View File

@ -202,8 +202,16 @@ func Main(arch *sys.Arch, theArch Arch) {
if *flagnewDoData {
// New dodata() is currently only implemented for selected targets.
if !(ctxt.IsElf() &&
(ctxt.IsAMD64() || ctxt.Is386())) {
switch {
case ctxt.IsElf():
if !(ctxt.IsAMD64() || ctxt.Is386()) {
*flagnewDoData = false
}
case ctxt.IsDarwin():
if !ctxt.IsAMD64() {
*flagnewDoData = false
}
default:
*flagnewDoData = false
}
}