mirror of
https://github.com/golang/go.git
synced 2025-12-08 06:10:04 +00:00
cmd/internal/objabi: extract shared functionality from obj
Now only cmd/asm and cmd/compile depend on cmd/internal/obj. Changing the assembler backends no longer requires reinstalling cmd/link or cmd/addr2line. There's also now one canonical definition of the object file format in cmd/internal/objabi/doc.go, with a warning to update all three implementations. objabi is still something of a grab bag of unrelated code (e.g., flag and environment variable handling probably belong in a separate "tool" package), but this is still progress. Fixes #15165. Fixes #20026. Change-Id: Ic4b92fac7d0d35438e0d20c9579aad4085c5534c Reviewed-on: https://go-review.googlesource.com/40972 Run-TryBot: Matthew Dempsky <mdempsky@google.com> TryBot-Result: Gobot Gobot <gobot@golang.org> Reviewed-by: Josh Bleecher Snyder <josharian@gmail.com>
This commit is contained in:
parent
f71f32e5e1
commit
1e3570ac86
118 changed files with 2419 additions and 2407 deletions
|
|
@ -13,6 +13,7 @@ import (
|
||||||
"cmd/asm/internal/flags"
|
"cmd/asm/internal/flags"
|
||||||
"cmd/asm/internal/lex"
|
"cmd/asm/internal/lex"
|
||||||
"cmd/internal/obj"
|
"cmd/internal/obj"
|
||||||
|
"cmd/internal/objabi"
|
||||||
"cmd/internal/sys"
|
"cmd/internal/sys"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
|
@ -151,7 +152,7 @@ func (p *Parser) asmText(word string, operands [][]lex.Token) {
|
||||||
frameSize = -frameSize
|
frameSize = -frameSize
|
||||||
}
|
}
|
||||||
op = op[1:]
|
op = op[1:]
|
||||||
argSize := int64(obj.ArgsSizeUnknown)
|
argSize := int64(objabi.ArgsSizeUnknown)
|
||||||
if len(op) > 0 {
|
if len(op) > 0 {
|
||||||
// There is an argument size. It must be a minus sign followed by a non-negative integer literal.
|
// There is an argument size. It must be a minus sign followed by a non-negative integer literal.
|
||||||
if len(op) != 2 || op[0].ScanToken != '-' || op[1].ScanToken != scanner.Int {
|
if len(op) != 2 || op[0].ScanToken != '-' || op[1].ScanToken != scanner.Int {
|
||||||
|
|
|
||||||
|
|
@ -10,13 +10,14 @@ import (
|
||||||
"cmd/asm/internal/arch"
|
"cmd/asm/internal/arch"
|
||||||
"cmd/asm/internal/lex"
|
"cmd/asm/internal/lex"
|
||||||
"cmd/internal/obj"
|
"cmd/internal/obj"
|
||||||
|
"cmd/internal/objabi"
|
||||||
)
|
)
|
||||||
|
|
||||||
// A simple in-out test: Do we print what we parse?
|
// A simple in-out test: Do we print what we parse?
|
||||||
|
|
||||||
func setArch(goarch string) (*arch.Arch, *obj.Link) {
|
func setArch(goarch string) (*arch.Arch, *obj.Link) {
|
||||||
obj.GOOS = "linux" // obj can handle this OS for all architectures.
|
objabi.GOOS = "linux" // obj can handle this OS for all architectures.
|
||||||
obj.GOARCH = goarch
|
objabi.GOARCH = goarch
|
||||||
architecture := arch.Set(goarch)
|
architecture := arch.Set(goarch)
|
||||||
if architecture == nil {
|
if architecture == nil {
|
||||||
panic("asm: unrecognized architecture " + goarch)
|
panic("asm: unrecognized architecture " + goarch)
|
||||||
|
|
|
||||||
|
|
@ -12,7 +12,7 @@ import (
|
||||||
"unicode"
|
"unicode"
|
||||||
|
|
||||||
"cmd/asm/internal/flags"
|
"cmd/asm/internal/flags"
|
||||||
"cmd/internal/obj"
|
"cmd/internal/objabi"
|
||||||
"cmd/internal/src"
|
"cmd/internal/src"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
|
@ -43,7 +43,7 @@ func NewTokenizer(name string, r io.Reader, file *os.File) *Tokenizer {
|
||||||
s.IsIdentRune = isIdentRune
|
s.IsIdentRune = isIdentRune
|
||||||
return &Tokenizer{
|
return &Tokenizer{
|
||||||
s: &s,
|
s: &s,
|
||||||
base: src.NewFileBase(name, obj.AbsFile(obj.WorkingDir(), name, *flags.TrimPath)),
|
base: src.NewFileBase(name, objabi.AbsFile(objabi.WorkingDir(), name, *flags.TrimPath)),
|
||||||
line: 1,
|
line: 1,
|
||||||
file: file,
|
file: file,
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -18,13 +18,14 @@ import (
|
||||||
|
|
||||||
"cmd/internal/bio"
|
"cmd/internal/bio"
|
||||||
"cmd/internal/obj"
|
"cmd/internal/obj"
|
||||||
|
"cmd/internal/objabi"
|
||||||
)
|
)
|
||||||
|
|
||||||
func main() {
|
func main() {
|
||||||
log.SetFlags(0)
|
log.SetFlags(0)
|
||||||
log.SetPrefix("asm: ")
|
log.SetPrefix("asm: ")
|
||||||
|
|
||||||
GOARCH := obj.GOARCH
|
GOARCH := objabi.GOARCH
|
||||||
|
|
||||||
architecture := arch.Set(GOARCH)
|
architecture := arch.Set(GOARCH)
|
||||||
if architecture == nil {
|
if architecture == nil {
|
||||||
|
|
@ -52,7 +53,7 @@ func main() {
|
||||||
defer bio.MustClose(out)
|
defer bio.MustClose(out)
|
||||||
buf := bufio.NewWriter(bio.MustWriter(out))
|
buf := bufio.NewWriter(bio.MustWriter(out))
|
||||||
|
|
||||||
fmt.Fprintf(buf, "go object %s %s %s\n", obj.GOOS, obj.GOARCH, obj.Version)
|
fmt.Fprintf(buf, "go object %s %s %s\n", objabi.GOOS, objabi.GOARCH, objabi.Version)
|
||||||
fmt.Fprintf(buf, "!\n")
|
fmt.Fprintf(buf, "!\n")
|
||||||
|
|
||||||
var ok, diag bool
|
var ok, diag bool
|
||||||
|
|
|
||||||
|
|
@ -6,15 +6,15 @@ package amd64
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"cmd/compile/internal/gc"
|
"cmd/compile/internal/gc"
|
||||||
"cmd/internal/obj"
|
|
||||||
"cmd/internal/obj/x86"
|
"cmd/internal/obj/x86"
|
||||||
|
"cmd/internal/objabi"
|
||||||
)
|
)
|
||||||
|
|
||||||
var leaptr = x86.ALEAQ
|
var leaptr = x86.ALEAQ
|
||||||
|
|
||||||
func Init(arch *gc.Arch) {
|
func Init(arch *gc.Arch) {
|
||||||
arch.LinkArch = &x86.Linkamd64
|
arch.LinkArch = &x86.Linkamd64
|
||||||
if obj.GOARCH == "amd64p32" {
|
if objabi.GOARCH == "amd64p32" {
|
||||||
arch.LinkArch = &x86.Linkamd64p32
|
arch.LinkArch = &x86.Linkamd64p32
|
||||||
leaptr = x86.ALEAL
|
leaptr = x86.ALEAL
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -8,10 +8,11 @@ import (
|
||||||
"cmd/compile/internal/gc"
|
"cmd/compile/internal/gc"
|
||||||
"cmd/internal/obj"
|
"cmd/internal/obj"
|
||||||
"cmd/internal/obj/x86"
|
"cmd/internal/obj/x86"
|
||||||
|
"cmd/internal/objabi"
|
||||||
)
|
)
|
||||||
|
|
||||||
// no floating point in note handlers on Plan 9
|
// no floating point in note handlers on Plan 9
|
||||||
var isPlan9 = obj.GOOS == "plan9"
|
var isPlan9 = objabi.GOOS == "plan9"
|
||||||
|
|
||||||
func defframe(pp *gc.Progs, fn *gc.Node, sz int64) {
|
func defframe(pp *gc.Progs, fn *gc.Node, sz int64) {
|
||||||
// fill in argument size, stack size
|
// fill in argument size, stack size
|
||||||
|
|
|
||||||
|
|
@ -8,6 +8,7 @@ import (
|
||||||
"cmd/compile/internal/gc"
|
"cmd/compile/internal/gc"
|
||||||
"cmd/internal/obj"
|
"cmd/internal/obj"
|
||||||
"cmd/internal/obj/arm64"
|
"cmd/internal/obj/arm64"
|
||||||
|
"cmd/internal/objabi"
|
||||||
)
|
)
|
||||||
|
|
||||||
func defframe(pp *gc.Progs, fn *gc.Node, sz int64) {
|
func defframe(pp *gc.Progs, fn *gc.Node, sz int64) {
|
||||||
|
|
@ -65,7 +66,7 @@ func defframe(pp *gc.Progs, fn *gc.Node, sz int64) {
|
||||||
zerorange(pp, p, int64(frame), lo, hi)
|
zerorange(pp, p, int64(frame), lo, hi)
|
||||||
}
|
}
|
||||||
|
|
||||||
var darwin = obj.GOOS == "darwin"
|
var darwin = objabi.GOOS == "darwin"
|
||||||
|
|
||||||
func zerorange(pp *gc.Progs, p *obj.Prog, frame int64, lo int64, hi int64) *obj.Prog {
|
func zerorange(pp *gc.Progs, p *obj.Prog, frame int64, lo int64, hi int64) *obj.Prog {
|
||||||
cnt := hi - lo
|
cnt := hi - lo
|
||||||
|
|
|
||||||
|
|
@ -33,6 +33,7 @@ package gc
|
||||||
import (
|
import (
|
||||||
"cmd/compile/internal/types"
|
"cmd/compile/internal/types"
|
||||||
"cmd/internal/obj"
|
"cmd/internal/obj"
|
||||||
|
"cmd/internal/objabi"
|
||||||
"cmd/internal/src"
|
"cmd/internal/src"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
|
@ -158,13 +159,13 @@ func (pp *Progs) settext(fn *Node) {
|
||||||
ptxt.From.Sym = fn.Func.lsym
|
ptxt.From.Sym = fn.Func.lsym
|
||||||
|
|
||||||
p := pp.Prog(obj.AFUNCDATA)
|
p := pp.Prog(obj.AFUNCDATA)
|
||||||
Addrconst(&p.From, obj.FUNCDATA_ArgsPointerMaps)
|
Addrconst(&p.From, objabi.FUNCDATA_ArgsPointerMaps)
|
||||||
p.To.Type = obj.TYPE_MEM
|
p.To.Type = obj.TYPE_MEM
|
||||||
p.To.Name = obj.NAME_EXTERN
|
p.To.Name = obj.NAME_EXTERN
|
||||||
p.To.Sym = &fn.Func.lsym.Func.GCArgs
|
p.To.Sym = &fn.Func.lsym.Func.GCArgs
|
||||||
|
|
||||||
p = pp.Prog(obj.AFUNCDATA)
|
p = pp.Prog(obj.AFUNCDATA)
|
||||||
Addrconst(&p.From, obj.FUNCDATA_LocalsPointerMaps)
|
Addrconst(&p.From, objabi.FUNCDATA_LocalsPointerMaps)
|
||||||
p.To.Type = obj.TYPE_MEM
|
p.To.Type = obj.TYPE_MEM
|
||||||
p.To.Name = obj.NAME_EXTERN
|
p.To.Name = obj.NAME_EXTERN
|
||||||
p.To.Sym = &fn.Func.lsym.Func.GCLocals
|
p.To.Sym = &fn.Func.lsym.Func.GCLocals
|
||||||
|
|
|
||||||
|
|
@ -6,7 +6,7 @@ package gc
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"cmd/compile/internal/syntax"
|
"cmd/compile/internal/syntax"
|
||||||
"cmd/internal/obj"
|
"cmd/internal/objabi"
|
||||||
"cmd/internal/src"
|
"cmd/internal/src"
|
||||||
"fmt"
|
"fmt"
|
||||||
"strings"
|
"strings"
|
||||||
|
|
@ -64,7 +64,7 @@ const (
|
||||||
func pragmaValue(verb string) syntax.Pragma {
|
func pragmaValue(verb string) syntax.Pragma {
|
||||||
switch verb {
|
switch verb {
|
||||||
case "go:nointerface":
|
case "go:nointerface":
|
||||||
if obj.Fieldtrack_enabled != 0 {
|
if objabi.Fieldtrack_enabled != 0 {
|
||||||
return Nointerface
|
return Nointerface
|
||||||
}
|
}
|
||||||
case "go:noescape":
|
case "go:noescape":
|
||||||
|
|
|
||||||
|
|
@ -12,6 +12,7 @@ import (
|
||||||
"cmd/compile/internal/ssa"
|
"cmd/compile/internal/ssa"
|
||||||
"cmd/compile/internal/types"
|
"cmd/compile/internal/types"
|
||||||
"cmd/internal/obj"
|
"cmd/internal/obj"
|
||||||
|
"cmd/internal/objabi"
|
||||||
"cmd/internal/src"
|
"cmd/internal/src"
|
||||||
"cmd/internal/sys"
|
"cmd/internal/sys"
|
||||||
"flag"
|
"flag"
|
||||||
|
|
@ -68,7 +69,7 @@ var debugtab = []struct {
|
||||||
|
|
||||||
func usage() {
|
func usage() {
|
||||||
fmt.Printf("usage: compile [options] file.go...\n")
|
fmt.Printf("usage: compile [options] file.go...\n")
|
||||||
obj.Flagprint(1)
|
objabi.Flagprint(1)
|
||||||
Exit(2)
|
Exit(2)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -85,7 +86,7 @@ func hidePanic() {
|
||||||
}
|
}
|
||||||
|
|
||||||
func doversion() {
|
func doversion() {
|
||||||
p := obj.Expstring()
|
p := objabi.Expstring()
|
||||||
if p == "X:none" {
|
if p == "X:none" {
|
||||||
p = ""
|
p = ""
|
||||||
}
|
}
|
||||||
|
|
@ -93,7 +94,7 @@ func doversion() {
|
||||||
if p != "" {
|
if p != "" {
|
||||||
sep = " "
|
sep = " "
|
||||||
}
|
}
|
||||||
fmt.Printf("compile version %s%s%s\n", obj.Version, sep, p)
|
fmt.Printf("compile version %s%s%s\n", objabi.Version, sep, p)
|
||||||
os.Exit(0)
|
os.Exit(0)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -162,49 +163,49 @@ func Main(archInit func(*Arch)) {
|
||||||
mappkg.Name = "go.map"
|
mappkg.Name = "go.map"
|
||||||
mappkg.Prefix = "go.map"
|
mappkg.Prefix = "go.map"
|
||||||
|
|
||||||
Nacl = obj.GOOS == "nacl"
|
Nacl = objabi.GOOS == "nacl"
|
||||||
|
|
||||||
flag.BoolVar(&compiling_runtime, "+", false, "compiling runtime")
|
flag.BoolVar(&compiling_runtime, "+", false, "compiling runtime")
|
||||||
obj.Flagcount("%", "debug non-static initializers", &Debug['%'])
|
objabi.Flagcount("%", "debug non-static initializers", &Debug['%'])
|
||||||
obj.Flagcount("B", "disable bounds checking", &Debug['B'])
|
objabi.Flagcount("B", "disable bounds checking", &Debug['B'])
|
||||||
obj.Flagcount("C", "disable printing of columns in error messages", &Debug['C']) // TODO(gri) remove eventually
|
objabi.Flagcount("C", "disable printing of columns in error messages", &Debug['C']) // TODO(gri) remove eventually
|
||||||
flag.StringVar(&localimport, "D", "", "set relative `path` for local imports")
|
flag.StringVar(&localimport, "D", "", "set relative `path` for local imports")
|
||||||
obj.Flagcount("E", "debug symbol export", &Debug['E'])
|
objabi.Flagcount("E", "debug symbol export", &Debug['E'])
|
||||||
obj.Flagfn1("I", "add `directory` to import search path", addidir)
|
objabi.Flagfn1("I", "add `directory` to import search path", addidir)
|
||||||
obj.Flagcount("K", "debug missing line numbers", &Debug['K'])
|
objabi.Flagcount("K", "debug missing line numbers", &Debug['K'])
|
||||||
obj.Flagcount("N", "disable optimizations", &Debug['N'])
|
objabi.Flagcount("N", "disable optimizations", &Debug['N'])
|
||||||
flag.BoolVar(&Debug_asm, "S", false, "print assembly listing")
|
flag.BoolVar(&Debug_asm, "S", false, "print assembly listing")
|
||||||
obj.Flagfn0("V", "print compiler version", doversion)
|
objabi.Flagfn0("V", "print compiler version", doversion)
|
||||||
obj.Flagcount("W", "debug parse tree after type checking", &Debug['W'])
|
objabi.Flagcount("W", "debug parse tree after type checking", &Debug['W'])
|
||||||
flag.StringVar(&asmhdr, "asmhdr", "", "write assembly header to `file`")
|
flag.StringVar(&asmhdr, "asmhdr", "", "write assembly header to `file`")
|
||||||
flag.StringVar(&buildid, "buildid", "", "record `id` as the build id in the export metadata")
|
flag.StringVar(&buildid, "buildid", "", "record `id` as the build id in the export metadata")
|
||||||
flag.BoolVar(&pure_go, "complete", false, "compiling complete package (no C or assembly)")
|
flag.BoolVar(&pure_go, "complete", false, "compiling complete package (no C or assembly)")
|
||||||
flag.StringVar(&debugstr, "d", "", "print debug information about items in `list`")
|
flag.StringVar(&debugstr, "d", "", "print debug information about items in `list`")
|
||||||
flag.BoolVar(&flagDWARF, "dwarf", true, "generate DWARF symbols")
|
flag.BoolVar(&flagDWARF, "dwarf", true, "generate DWARF symbols")
|
||||||
obj.Flagcount("e", "no limit on number of errors reported", &Debug['e'])
|
objabi.Flagcount("e", "no limit on number of errors reported", &Debug['e'])
|
||||||
obj.Flagcount("f", "debug stack frames", &Debug['f'])
|
objabi.Flagcount("f", "debug stack frames", &Debug['f'])
|
||||||
obj.Flagcount("h", "halt on error", &Debug['h'])
|
objabi.Flagcount("h", "halt on error", &Debug['h'])
|
||||||
obj.Flagcount("i", "debug line number stack", &Debug['i'])
|
objabi.Flagcount("i", "debug line number stack", &Debug['i'])
|
||||||
obj.Flagfn1("importmap", "add `definition` of the form source=actual to import map", addImportMap)
|
objabi.Flagfn1("importmap", "add `definition` of the form source=actual to import map", addImportMap)
|
||||||
flag.StringVar(&flag_installsuffix, "installsuffix", "", "set pkg directory `suffix`")
|
flag.StringVar(&flag_installsuffix, "installsuffix", "", "set pkg directory `suffix`")
|
||||||
obj.Flagcount("j", "debug runtime-initialized variables", &Debug['j'])
|
objabi.Flagcount("j", "debug runtime-initialized variables", &Debug['j'])
|
||||||
obj.Flagcount("l", "disable inlining", &Debug['l'])
|
objabi.Flagcount("l", "disable inlining", &Debug['l'])
|
||||||
flag.StringVar(&linkobj, "linkobj", "", "write linker-specific object to `file`")
|
flag.StringVar(&linkobj, "linkobj", "", "write linker-specific object to `file`")
|
||||||
obj.Flagcount("live", "debug liveness analysis", &debuglive)
|
objabi.Flagcount("live", "debug liveness analysis", &debuglive)
|
||||||
obj.Flagcount("m", "print optimization decisions", &Debug['m'])
|
objabi.Flagcount("m", "print optimization decisions", &Debug['m'])
|
||||||
flag.BoolVar(&flag_msan, "msan", false, "build code compatible with C/C++ memory sanitizer")
|
flag.BoolVar(&flag_msan, "msan", false, "build code compatible with C/C++ memory sanitizer")
|
||||||
flag.BoolVar(&dolinkobj, "dolinkobj", true, "generate linker-specific objects; if false, some invalid code may compile")
|
flag.BoolVar(&dolinkobj, "dolinkobj", true, "generate linker-specific objects; if false, some invalid code may compile")
|
||||||
flag.BoolVar(&nolocalimports, "nolocalimports", false, "reject local (relative) imports")
|
flag.BoolVar(&nolocalimports, "nolocalimports", false, "reject local (relative) imports")
|
||||||
flag.StringVar(&outfile, "o", "", "write output to `file`")
|
flag.StringVar(&outfile, "o", "", "write output to `file`")
|
||||||
flag.StringVar(&myimportpath, "p", "", "set expected package import `path`")
|
flag.StringVar(&myimportpath, "p", "", "set expected package import `path`")
|
||||||
flag.BoolVar(&writearchive, "pack", false, "write package file instead of object file")
|
flag.BoolVar(&writearchive, "pack", false, "write package file instead of object file")
|
||||||
obj.Flagcount("r", "debug generated wrappers", &Debug['r'])
|
objabi.Flagcount("r", "debug generated wrappers", &Debug['r'])
|
||||||
flag.BoolVar(&flag_race, "race", false, "enable race detector")
|
flag.BoolVar(&flag_race, "race", false, "enable race detector")
|
||||||
obj.Flagcount("s", "warn about composite literals that can be simplified", &Debug['s'])
|
objabi.Flagcount("s", "warn about composite literals that can be simplified", &Debug['s'])
|
||||||
flag.StringVar(&pathPrefix, "trimpath", "", "remove `prefix` from recorded source file paths")
|
flag.StringVar(&pathPrefix, "trimpath", "", "remove `prefix` from recorded source file paths")
|
||||||
flag.BoolVar(&safemode, "u", false, "reject unsafe code")
|
flag.BoolVar(&safemode, "u", false, "reject unsafe code")
|
||||||
flag.BoolVar(&Debug_vlog, "v", false, "increase debug verbosity")
|
flag.BoolVar(&Debug_vlog, "v", false, "increase debug verbosity")
|
||||||
obj.Flagcount("w", "debug type checking", &Debug['w'])
|
objabi.Flagcount("w", "debug type checking", &Debug['w'])
|
||||||
flag.BoolVar(&use_writebarrier, "wb", true, "enable write barrier")
|
flag.BoolVar(&use_writebarrier, "wb", true, "enable write barrier")
|
||||||
var flag_shared bool
|
var flag_shared bool
|
||||||
var flag_dynlink bool
|
var flag_dynlink bool
|
||||||
|
|
@ -219,7 +220,7 @@ func Main(archInit func(*Arch)) {
|
||||||
flag.StringVar(&blockprofile, "blockprofile", "", "write block profile to `file`")
|
flag.StringVar(&blockprofile, "blockprofile", "", "write block profile to `file`")
|
||||||
flag.StringVar(&mutexprofile, "mutexprofile", "", "write mutex profile to `file`")
|
flag.StringVar(&mutexprofile, "mutexprofile", "", "write mutex profile to `file`")
|
||||||
flag.StringVar(&benchfile, "bench", "", "append benchmark times to `file`")
|
flag.StringVar(&benchfile, "bench", "", "append benchmark times to `file`")
|
||||||
obj.Flagparse(usage)
|
objabi.Flagparse(usage)
|
||||||
|
|
||||||
Ctxt.Flag_shared = flag_dynlink || flag_shared
|
Ctxt.Flag_shared = flag_dynlink || flag_shared
|
||||||
Ctxt.Flag_dynlink = flag_dynlink
|
Ctxt.Flag_dynlink = flag_dynlink
|
||||||
|
|
@ -600,7 +601,7 @@ func writebench(filename string) error {
|
||||||
}
|
}
|
||||||
|
|
||||||
var buf bytes.Buffer
|
var buf bytes.Buffer
|
||||||
fmt.Fprintln(&buf, "commit:", obj.Version)
|
fmt.Fprintln(&buf, "commit:", objabi.Version)
|
||||||
fmt.Fprintln(&buf, "goos:", runtime.GOOS)
|
fmt.Fprintln(&buf, "goos:", runtime.GOOS)
|
||||||
fmt.Fprintln(&buf, "goarch:", runtime.GOARCH)
|
fmt.Fprintln(&buf, "goarch:", runtime.GOARCH)
|
||||||
timings.Write(&buf, "BenchmarkCompile:"+myimportpath+":")
|
timings.Write(&buf, "BenchmarkCompile:"+myimportpath+":")
|
||||||
|
|
@ -723,7 +724,7 @@ func findpkg(name string) (file string, ok bool) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if obj.GOROOT != "" {
|
if objabi.GOROOT != "" {
|
||||||
suffix := ""
|
suffix := ""
|
||||||
suffixsep := ""
|
suffixsep := ""
|
||||||
if flag_installsuffix != "" {
|
if flag_installsuffix != "" {
|
||||||
|
|
@ -737,11 +738,11 @@ func findpkg(name string) (file string, ok bool) {
|
||||||
suffix = "msan"
|
suffix = "msan"
|
||||||
}
|
}
|
||||||
|
|
||||||
file = fmt.Sprintf("%s/pkg/%s_%s%s%s/%s.a", obj.GOROOT, obj.GOOS, obj.GOARCH, suffixsep, suffix, name)
|
file = fmt.Sprintf("%s/pkg/%s_%s%s%s/%s.a", objabi.GOROOT, objabi.GOOS, objabi.GOARCH, suffixsep, suffix, name)
|
||||||
if _, err := os.Stat(file); err == nil {
|
if _, err := os.Stat(file); err == nil {
|
||||||
return file, true
|
return file, true
|
||||||
}
|
}
|
||||||
file = fmt.Sprintf("%s/pkg/%s_%s%s%s/%s.o", obj.GOROOT, obj.GOOS, obj.GOARCH, suffixsep, suffix, name)
|
file = fmt.Sprintf("%s/pkg/%s_%s%s%s/%s.o", objabi.GOROOT, objabi.GOOS, objabi.GOARCH, suffixsep, suffix, name)
|
||||||
if _, err := os.Stat(file); err == nil {
|
if _, err := os.Stat(file); err == nil {
|
||||||
return file, true
|
return file, true
|
||||||
}
|
}
|
||||||
|
|
@ -887,7 +888,7 @@ func importfile(f *Val) *types.Pkg {
|
||||||
errorexit()
|
errorexit()
|
||||||
}
|
}
|
||||||
|
|
||||||
q := fmt.Sprintf("%s %s %s %s", obj.GOOS, obj.GOARCH, obj.Version, obj.Expstring())
|
q := fmt.Sprintf("%s %s %s %s", objabi.GOOS, objabi.GOARCH, objabi.Version, objabi.Expstring())
|
||||||
if p[10:] != q {
|
if p[10:] != q {
|
||||||
yyerror("import %s: object is [%s] expected [%s]", file, p[10:], q)
|
yyerror("import %s: object is [%s] expected [%s]", file, p[10:], q)
|
||||||
errorexit()
|
errorexit()
|
||||||
|
|
|
||||||
|
|
@ -13,7 +13,7 @@ import (
|
||||||
|
|
||||||
"cmd/compile/internal/syntax"
|
"cmd/compile/internal/syntax"
|
||||||
"cmd/compile/internal/types"
|
"cmd/compile/internal/types"
|
||||||
"cmd/internal/obj"
|
"cmd/internal/objabi"
|
||||||
"cmd/internal/src"
|
"cmd/internal/src"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
|
@ -66,7 +66,7 @@ func yyerrorpos(pos src.Pos, format string, args ...interface{}) {
|
||||||
var pathPrefix string
|
var pathPrefix string
|
||||||
|
|
||||||
func absFilename(name string) string {
|
func absFilename(name string) string {
|
||||||
return obj.AbsFile(Ctxt.Pathname, name, pathPrefix)
|
return objabi.AbsFile(Ctxt.Pathname, name, pathPrefix)
|
||||||
}
|
}
|
||||||
|
|
||||||
// noder transforms package syntax's AST into a Node tree.
|
// noder transforms package syntax's AST into a Node tree.
|
||||||
|
|
|
||||||
|
|
@ -8,6 +8,7 @@ import (
|
||||||
"cmd/compile/internal/types"
|
"cmd/compile/internal/types"
|
||||||
"cmd/internal/bio"
|
"cmd/internal/bio"
|
||||||
"cmd/internal/obj"
|
"cmd/internal/obj"
|
||||||
|
"cmd/internal/objabi"
|
||||||
"crypto/sha256"
|
"crypto/sha256"
|
||||||
"fmt"
|
"fmt"
|
||||||
"io"
|
"io"
|
||||||
|
|
@ -73,7 +74,7 @@ func dumpobj1(outfile string, mode int) {
|
||||||
}
|
}
|
||||||
|
|
||||||
printheader := func() {
|
printheader := func() {
|
||||||
fmt.Fprintf(bout, "go object %s %s %s %s\n", obj.GOOS, obj.GOARCH, obj.Version, obj.Expstring())
|
fmt.Fprintf(bout, "go object %s %s %s %s\n", objabi.GOOS, objabi.GOARCH, objabi.Version, objabi.Expstring())
|
||||||
if buildid != "" {
|
if buildid != "" {
|
||||||
fmt.Fprintf(bout, "build id %q\n", buildid)
|
fmt.Fprintf(bout, "build id %q\n", buildid)
|
||||||
}
|
}
|
||||||
|
|
@ -277,7 +278,7 @@ func duintxx(s *types.Sym, off int, v uint64, wid int) int {
|
||||||
func duintxxLSym(s *obj.LSym, off int, v uint64, wid int) int {
|
func duintxxLSym(s *obj.LSym, off int, v uint64, wid int) int {
|
||||||
if s.Type == 0 {
|
if s.Type == 0 {
|
||||||
// TODO(josharian): Do this in obj.prepwrite instead.
|
// TODO(josharian): Do this in obj.prepwrite instead.
|
||||||
s.Type = obj.SDATA
|
s.Type = objabi.SDATA
|
||||||
}
|
}
|
||||||
if off&(wid-1) != 0 {
|
if off&(wid-1) != 0 {
|
||||||
Fatalf("duintxxLSym: misaligned: v=%d wid=%d off=%d", v, wid, off)
|
Fatalf("duintxxLSym: misaligned: v=%d wid=%d off=%d", v, wid, off)
|
||||||
|
|
|
||||||
|
|
@ -9,6 +9,7 @@ import (
|
||||||
"cmd/compile/internal/types"
|
"cmd/compile/internal/types"
|
||||||
"cmd/internal/dwarf"
|
"cmd/internal/dwarf"
|
||||||
"cmd/internal/obj"
|
"cmd/internal/obj"
|
||||||
|
"cmd/internal/objabi"
|
||||||
"cmd/internal/src"
|
"cmd/internal/src"
|
||||||
"cmd/internal/sys"
|
"cmd/internal/sys"
|
||||||
"fmt"
|
"fmt"
|
||||||
|
|
@ -250,7 +251,7 @@ func debuginfo(fnsym *obj.LSym, curfn interface{}) []*dwarf.Var {
|
||||||
if Ctxt.FixedFrameSize() == 0 {
|
if Ctxt.FixedFrameSize() == 0 {
|
||||||
offs -= int64(Widthptr)
|
offs -= int64(Widthptr)
|
||||||
}
|
}
|
||||||
if obj.Framepointer_enabled(obj.GOOS, obj.GOARCH) {
|
if objabi.Framepointer_enabled(objabi.GOOS, objabi.GOARCH) {
|
||||||
offs -= int64(Widthptr)
|
offs -= int64(Widthptr)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -297,7 +298,7 @@ func fieldtrack(fnsym *obj.LSym, tracked map[*types.Sym]struct{}) {
|
||||||
if fnsym == nil {
|
if fnsym == nil {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
if obj.Fieldtrack_enabled == 0 || len(tracked) == 0 {
|
if objabi.Fieldtrack_enabled == 0 || len(tracked) == 0 {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -309,7 +310,7 @@ func fieldtrack(fnsym *obj.LSym, tracked map[*types.Sym]struct{}) {
|
||||||
for _, sym := range trackSyms {
|
for _, sym := range trackSyms {
|
||||||
r := obj.Addrel(fnsym)
|
r := obj.Addrel(fnsym)
|
||||||
r.Sym = Linksym(sym)
|
r.Sym = Linksym(sym)
|
||||||
r.Type = obj.R_USEFIELD
|
r.Type = objabi.R_USEFIELD
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -8,6 +8,7 @@ import (
|
||||||
"cmd/compile/internal/types"
|
"cmd/compile/internal/types"
|
||||||
"cmd/internal/gcprog"
|
"cmd/internal/gcprog"
|
||||||
"cmd/internal/obj"
|
"cmd/internal/obj"
|
||||||
|
"cmd/internal/objabi"
|
||||||
"cmd/internal/src"
|
"cmd/internal/src"
|
||||||
"fmt"
|
"fmt"
|
||||||
"os"
|
"os"
|
||||||
|
|
@ -677,38 +678,38 @@ func dmethodptrOffLSym(s *obj.LSym, ot int, x *obj.LSym) int {
|
||||||
r.Off = int32(ot)
|
r.Off = int32(ot)
|
||||||
r.Siz = 4
|
r.Siz = 4
|
||||||
r.Sym = x
|
r.Sym = x
|
||||||
r.Type = obj.R_METHODOFF
|
r.Type = objabi.R_METHODOFF
|
||||||
return ot + 4
|
return ot + 4
|
||||||
}
|
}
|
||||||
|
|
||||||
var kinds = []int{
|
var kinds = []int{
|
||||||
TINT: obj.KindInt,
|
TINT: objabi.KindInt,
|
||||||
TUINT: obj.KindUint,
|
TUINT: objabi.KindUint,
|
||||||
TINT8: obj.KindInt8,
|
TINT8: objabi.KindInt8,
|
||||||
TUINT8: obj.KindUint8,
|
TUINT8: objabi.KindUint8,
|
||||||
TINT16: obj.KindInt16,
|
TINT16: objabi.KindInt16,
|
||||||
TUINT16: obj.KindUint16,
|
TUINT16: objabi.KindUint16,
|
||||||
TINT32: obj.KindInt32,
|
TINT32: objabi.KindInt32,
|
||||||
TUINT32: obj.KindUint32,
|
TUINT32: objabi.KindUint32,
|
||||||
TINT64: obj.KindInt64,
|
TINT64: objabi.KindInt64,
|
||||||
TUINT64: obj.KindUint64,
|
TUINT64: objabi.KindUint64,
|
||||||
TUINTPTR: obj.KindUintptr,
|
TUINTPTR: objabi.KindUintptr,
|
||||||
TFLOAT32: obj.KindFloat32,
|
TFLOAT32: objabi.KindFloat32,
|
||||||
TFLOAT64: obj.KindFloat64,
|
TFLOAT64: objabi.KindFloat64,
|
||||||
TBOOL: obj.KindBool,
|
TBOOL: objabi.KindBool,
|
||||||
TSTRING: obj.KindString,
|
TSTRING: objabi.KindString,
|
||||||
TPTR32: obj.KindPtr,
|
TPTR32: objabi.KindPtr,
|
||||||
TPTR64: obj.KindPtr,
|
TPTR64: objabi.KindPtr,
|
||||||
TSTRUCT: obj.KindStruct,
|
TSTRUCT: objabi.KindStruct,
|
||||||
TINTER: obj.KindInterface,
|
TINTER: objabi.KindInterface,
|
||||||
TCHAN: obj.KindChan,
|
TCHAN: objabi.KindChan,
|
||||||
TMAP: obj.KindMap,
|
TMAP: objabi.KindMap,
|
||||||
TARRAY: obj.KindArray,
|
TARRAY: objabi.KindArray,
|
||||||
TSLICE: obj.KindSlice,
|
TSLICE: objabi.KindSlice,
|
||||||
TFUNC: obj.KindFunc,
|
TFUNC: objabi.KindFunc,
|
||||||
TCOMPLEX64: obj.KindComplex64,
|
TCOMPLEX64: objabi.KindComplex64,
|
||||||
TCOMPLEX128: obj.KindComplex128,
|
TCOMPLEX128: objabi.KindComplex128,
|
||||||
TUNSAFEPTR: obj.KindUnsafePointer,
|
TUNSAFEPTR: objabi.KindUnsafePointer,
|
||||||
}
|
}
|
||||||
|
|
||||||
// typeptrdata returns the length in bytes of the prefix of t
|
// typeptrdata returns the length in bytes of the prefix of t
|
||||||
|
|
@ -867,13 +868,13 @@ func dcommontype(s *types.Sym, ot int, t *types.Type) int {
|
||||||
|
|
||||||
i = kinds[t.Etype]
|
i = kinds[t.Etype]
|
||||||
if !types.Haspointers(t) {
|
if !types.Haspointers(t) {
|
||||||
i |= obj.KindNoPointers
|
i |= objabi.KindNoPointers
|
||||||
}
|
}
|
||||||
if isdirectiface(t) {
|
if isdirectiface(t) {
|
||||||
i |= obj.KindDirectIface
|
i |= objabi.KindDirectIface
|
||||||
}
|
}
|
||||||
if useGCProg {
|
if useGCProg {
|
||||||
i |= obj.KindGCProg
|
i |= objabi.KindGCProg
|
||||||
}
|
}
|
||||||
ot = duint8(s, ot, uint8(i)) // kind
|
ot = duint8(s, ot, uint8(i)) // kind
|
||||||
if algsym == nil {
|
if algsym == nil {
|
||||||
|
|
|
||||||
|
|
@ -15,6 +15,7 @@ import (
|
||||||
"cmd/compile/internal/ssa"
|
"cmd/compile/internal/ssa"
|
||||||
"cmd/compile/internal/types"
|
"cmd/compile/internal/types"
|
||||||
"cmd/internal/obj"
|
"cmd/internal/obj"
|
||||||
|
"cmd/internal/objabi"
|
||||||
"cmd/internal/src"
|
"cmd/internal/src"
|
||||||
"cmd/internal/sys"
|
"cmd/internal/sys"
|
||||||
)
|
)
|
||||||
|
|
@ -4663,7 +4664,7 @@ func (s *SSAGenState) Call(v *ssa.Value) *obj.Prog {
|
||||||
Fatalf("missing stack map index for %v", v.LongString())
|
Fatalf("missing stack map index for %v", v.LongString())
|
||||||
}
|
}
|
||||||
p := s.Prog(obj.APCDATA)
|
p := s.Prog(obj.APCDATA)
|
||||||
Addrconst(&p.From, obj.PCDATA_StackMapIndex)
|
Addrconst(&p.From, objabi.PCDATA_StackMapIndex)
|
||||||
Addrconst(&p.To, int64(idx))
|
Addrconst(&p.To, int64(idx))
|
||||||
|
|
||||||
if sym, _ := v.Aux.(*obj.LSym); sym == Deferreturn {
|
if sym, _ := v.Aux.(*obj.LSym); sym == Deferreturn {
|
||||||
|
|
|
||||||
|
|
@ -7,7 +7,7 @@ package gc
|
||||||
import (
|
import (
|
||||||
"bytes"
|
"bytes"
|
||||||
"cmd/compile/internal/types"
|
"cmd/compile/internal/types"
|
||||||
"cmd/internal/obj"
|
"cmd/internal/objabi"
|
||||||
"cmd/internal/src"
|
"cmd/internal/src"
|
||||||
"crypto/md5"
|
"crypto/md5"
|
||||||
"encoding/binary"
|
"encoding/binary"
|
||||||
|
|
@ -168,7 +168,7 @@ func Fatalf(fmt_ string, args ...interface{}) {
|
||||||
fmt.Printf("\n")
|
fmt.Printf("\n")
|
||||||
|
|
||||||
// If this is a released compiler version, ask for a bug report.
|
// If this is a released compiler version, ask for a bug report.
|
||||||
if strings.HasPrefix(obj.Version, "release") {
|
if strings.HasPrefix(objabi.Version, "release") {
|
||||||
fmt.Printf("\n")
|
fmt.Printf("\n")
|
||||||
fmt.Printf("Please file a bug report including a short program that triggers the error.\n")
|
fmt.Printf("Please file a bug report including a short program that triggers the error.\n")
|
||||||
fmt.Printf("https://golang.org/issue/new\n")
|
fmt.Printf("https://golang.org/issue/new\n")
|
||||||
|
|
|
||||||
|
|
@ -6,7 +6,7 @@ package gc
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"cmd/compile/internal/types"
|
"cmd/compile/internal/types"
|
||||||
"cmd/internal/obj"
|
"cmd/internal/objabi"
|
||||||
"cmd/internal/src"
|
"cmd/internal/src"
|
||||||
"fmt"
|
"fmt"
|
||||||
"math"
|
"math"
|
||||||
|
|
@ -2463,7 +2463,7 @@ func lookdot(n *Node, t *types.Type, dostrcmp int) *types.Field {
|
||||||
}
|
}
|
||||||
n.Xoffset = f1.Offset
|
n.Xoffset = f1.Offset
|
||||||
n.Type = f1.Type
|
n.Type = f1.Type
|
||||||
if obj.Fieldtrack_enabled > 0 {
|
if objabi.Fieldtrack_enabled > 0 {
|
||||||
dotField[typeSymKey{t.Orig, s}] = f1
|
dotField[typeSymKey{t.Orig, s}] = f1
|
||||||
}
|
}
|
||||||
if t.IsInterface() {
|
if t.IsInterface() {
|
||||||
|
|
|
||||||
|
|
@ -6,7 +6,7 @@ package gc
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"cmd/compile/internal/types"
|
"cmd/compile/internal/types"
|
||||||
"cmd/internal/obj"
|
"cmd/internal/objabi"
|
||||||
"cmd/internal/sys"
|
"cmd/internal/sys"
|
||||||
"fmt"
|
"fmt"
|
||||||
"strings"
|
"strings"
|
||||||
|
|
@ -3477,7 +3477,7 @@ func usemethod(n *Node) {
|
||||||
}
|
}
|
||||||
|
|
||||||
func usefield(n *Node) {
|
func usefield(n *Node) {
|
||||||
if obj.Fieldtrack_enabled == 0 {
|
if objabi.Fieldtrack_enabled == 0 {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -7,13 +7,13 @@ package mips
|
||||||
import (
|
import (
|
||||||
"cmd/compile/internal/gc"
|
"cmd/compile/internal/gc"
|
||||||
"cmd/compile/internal/ssa"
|
"cmd/compile/internal/ssa"
|
||||||
"cmd/internal/obj"
|
|
||||||
"cmd/internal/obj/mips"
|
"cmd/internal/obj/mips"
|
||||||
|
"cmd/internal/objabi"
|
||||||
)
|
)
|
||||||
|
|
||||||
func Init(arch *gc.Arch) {
|
func Init(arch *gc.Arch) {
|
||||||
arch.LinkArch = &mips.Linkmips
|
arch.LinkArch = &mips.Linkmips
|
||||||
if obj.GOARCH == "mipsle" {
|
if objabi.GOARCH == "mipsle" {
|
||||||
arch.LinkArch = &mips.Linkmipsle
|
arch.LinkArch = &mips.Linkmipsle
|
||||||
}
|
}
|
||||||
arch.REGSP = mips.REGSP
|
arch.REGSP = mips.REGSP
|
||||||
|
|
|
||||||
|
|
@ -7,13 +7,13 @@ package mips64
|
||||||
import (
|
import (
|
||||||
"cmd/compile/internal/gc"
|
"cmd/compile/internal/gc"
|
||||||
"cmd/compile/internal/ssa"
|
"cmd/compile/internal/ssa"
|
||||||
"cmd/internal/obj"
|
|
||||||
"cmd/internal/obj/mips"
|
"cmd/internal/obj/mips"
|
||||||
|
"cmd/internal/objabi"
|
||||||
)
|
)
|
||||||
|
|
||||||
func Init(arch *gc.Arch) {
|
func Init(arch *gc.Arch) {
|
||||||
arch.LinkArch = &mips.Linkmips64
|
arch.LinkArch = &mips.Linkmips64
|
||||||
if obj.GOARCH == "mips64le" {
|
if objabi.GOARCH == "mips64le" {
|
||||||
arch.LinkArch = &mips.Linkmips64le
|
arch.LinkArch = &mips.Linkmips64le
|
||||||
}
|
}
|
||||||
arch.REGSP = mips.REGSP
|
arch.REGSP = mips.REGSP
|
||||||
|
|
|
||||||
|
|
@ -6,13 +6,13 @@ package ppc64
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"cmd/compile/internal/gc"
|
"cmd/compile/internal/gc"
|
||||||
"cmd/internal/obj"
|
|
||||||
"cmd/internal/obj/ppc64"
|
"cmd/internal/obj/ppc64"
|
||||||
|
"cmd/internal/objabi"
|
||||||
)
|
)
|
||||||
|
|
||||||
func Init(arch *gc.Arch) {
|
func Init(arch *gc.Arch) {
|
||||||
arch.LinkArch = &ppc64.Linkppc64
|
arch.LinkArch = &ppc64.Linkppc64
|
||||||
if obj.GOARCH == "ppc64le" {
|
if objabi.GOARCH == "ppc64le" {
|
||||||
arch.LinkArch = &ppc64.Linkppc64le
|
arch.LinkArch = &ppc64.Linkppc64le
|
||||||
}
|
}
|
||||||
arch.REGSP = ppc64.REGSP
|
arch.REGSP = ppc64.REGSP
|
||||||
|
|
|
||||||
|
|
@ -5,7 +5,7 @@
|
||||||
package ssa
|
package ssa
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"cmd/internal/obj"
|
"cmd/internal/objabi"
|
||||||
"cmd/internal/src"
|
"cmd/internal/src"
|
||||||
"fmt"
|
"fmt"
|
||||||
"log"
|
"log"
|
||||||
|
|
@ -352,7 +352,7 @@ var passes = [...]pass{
|
||||||
{name: "fuse", fn: fuse},
|
{name: "fuse", fn: fuse},
|
||||||
{name: "dse", fn: dse},
|
{name: "dse", fn: dse},
|
||||||
{name: "insert resched checks", fn: insertLoopReschedChecks,
|
{name: "insert resched checks", fn: insertLoopReschedChecks,
|
||||||
disabled: obj.Preemptibleloops_enabled == 0}, // insert resched checks in loops.
|
disabled: objabi.Preemptibleloops_enabled == 0}, // insert resched checks in loops.
|
||||||
{name: "tighten", fn: tighten}, // move values closer to their uses
|
{name: "tighten", fn: tighten}, // move values closer to their uses
|
||||||
{name: "lower", fn: lower, required: true},
|
{name: "lower", fn: lower, required: true},
|
||||||
{name: "lowered cse", fn: cse},
|
{name: "lowered cse", fn: cse},
|
||||||
|
|
|
||||||
|
|
@ -6,6 +6,7 @@ package ssa
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"cmd/internal/obj"
|
"cmd/internal/obj"
|
||||||
|
"cmd/internal/objabi"
|
||||||
"cmd/internal/src"
|
"cmd/internal/src"
|
||||||
"os"
|
"os"
|
||||||
"strconv"
|
"strconv"
|
||||||
|
|
@ -202,7 +203,7 @@ func NewConfig(arch string, types Types, ctxt *obj.Link, optimize bool) *Config
|
||||||
c.FPReg = framepointerRegARM64
|
c.FPReg = framepointerRegARM64
|
||||||
c.LinkReg = linkRegARM64
|
c.LinkReg = linkRegARM64
|
||||||
c.hasGReg = true
|
c.hasGReg = true
|
||||||
c.noDuffDevice = obj.GOOS == "darwin" // darwin linker cannot handle BR26 reloc with non-zero addend
|
c.noDuffDevice = objabi.GOOS == "darwin" // darwin linker cannot handle BR26 reloc with non-zero addend
|
||||||
case "ppc64":
|
case "ppc64":
|
||||||
c.BigEndian = true
|
c.BigEndian = true
|
||||||
fallthrough
|
fallthrough
|
||||||
|
|
@ -271,11 +272,11 @@ func NewConfig(arch string, types Types, ctxt *obj.Link, optimize bool) *Config
|
||||||
}
|
}
|
||||||
c.ctxt = ctxt
|
c.ctxt = ctxt
|
||||||
c.optimize = optimize
|
c.optimize = optimize
|
||||||
c.nacl = obj.GOOS == "nacl"
|
c.nacl = objabi.GOOS == "nacl"
|
||||||
|
|
||||||
// Don't use Duff's device on Plan 9 AMD64, because floating
|
// Don't use Duff's device on Plan 9 AMD64, because floating
|
||||||
// point operations are not allowed in note handler.
|
// point operations are not allowed in note handler.
|
||||||
if obj.GOOS == "plan9" && arch == "amd64" {
|
if objabi.GOOS == "plan9" && arch == "amd64" {
|
||||||
c.noDuffDevice = true
|
c.noDuffDevice = true
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -89,10 +89,10 @@
|
||||||
|
|
||||||
// count trailing zero for ARMv5 and ARMv6
|
// count trailing zero for ARMv5 and ARMv6
|
||||||
// 32 - CLZ(x&-x - 1)
|
// 32 - CLZ(x&-x - 1)
|
||||||
(Ctz32 <t> x) && obj.GOARM<=6 -> (RSBconst [32] (CLZ <t> (SUBconst <t> (AND <t> x (RSBconst <t> [0] x)) [1])))
|
(Ctz32 <t> x) && objabi.GOARM<=6 -> (RSBconst [32] (CLZ <t> (SUBconst <t> (AND <t> x (RSBconst <t> [0] x)) [1])))
|
||||||
|
|
||||||
// count trailing zero for ARMv7
|
// count trailing zero for ARMv7
|
||||||
(Ctz32 <t> x) && obj.GOARM==7 -> (CLZ <t> (RBIT <t> x))
|
(Ctz32 <t> x) && objabi.GOARM==7 -> (CLZ <t> (RBIT <t> x))
|
||||||
|
|
||||||
// bit length
|
// bit length
|
||||||
(BitLen32 <t> x) -> (RSBconst [32] (CLZ <t> x))
|
(BitLen32 <t> x) -> (RSBconst [32] (CLZ <t> x))
|
||||||
|
|
@ -106,13 +106,13 @@
|
||||||
// t5 = x right rotate 8 bits -- (d, a, b, c )
|
// t5 = x right rotate 8 bits -- (d, a, b, c )
|
||||||
// result = t4 ^ t5 -- (d, c, b, a )
|
// result = t4 ^ t5 -- (d, c, b, a )
|
||||||
// using shifted ops this can be done in 4 instructions.
|
// using shifted ops this can be done in 4 instructions.
|
||||||
(Bswap32 <t> x) && obj.GOARM==5 ->
|
(Bswap32 <t> x) && objabi.GOARM==5 ->
|
||||||
(XOR <t>
|
(XOR <t>
|
||||||
(SRLconst <t> (BICconst <t> (XOR <t> x (SRRconst <t> [16] x)) [0xff0000]) [8])
|
(SRLconst <t> (BICconst <t> (XOR <t> x (SRRconst <t> [16] x)) [0xff0000]) [8])
|
||||||
(SRRconst <t> x [8]))
|
(SRRconst <t> x [8]))
|
||||||
|
|
||||||
// byte swap for ARMv6 and above
|
// byte swap for ARMv6 and above
|
||||||
(Bswap32 x) && obj.GOARM>=6 -> (REV x)
|
(Bswap32 x) && objabi.GOARM>=6 -> (REV x)
|
||||||
|
|
||||||
// boolean ops -- booleans are represented with 0=false, 1=true
|
// boolean ops -- booleans are represented with 0=false, 1=true
|
||||||
(AndB x y) -> (AND x y)
|
(AndB x y) -> (AND x y)
|
||||||
|
|
|
||||||
|
|
@ -156,8 +156,11 @@ func genRules(arch arch) {
|
||||||
fmt.Fprintln(w, "package ssa")
|
fmt.Fprintln(w, "package ssa")
|
||||||
fmt.Fprintln(w, "import \"math\"")
|
fmt.Fprintln(w, "import \"math\"")
|
||||||
fmt.Fprintln(w, "import \"cmd/internal/obj\"")
|
fmt.Fprintln(w, "import \"cmd/internal/obj\"")
|
||||||
|
fmt.Fprintln(w, "import \"cmd/internal/objabi\"")
|
||||||
fmt.Fprintln(w, "var _ = math.MinInt8 // in case not otherwise used")
|
fmt.Fprintln(w, "var _ = math.MinInt8 // in case not otherwise used")
|
||||||
fmt.Fprintln(w, "var _ = obj.ANOP // in case not otherwise used")
|
fmt.Fprintln(w, "var _ = obj.ANOP // in case not otherwise used")
|
||||||
|
fmt.Fprintln(w, "var _ = objabi.GOROOT // in case not otherwise used")
|
||||||
|
fmt.Fprintln(w)
|
||||||
|
|
||||||
// Main rewrite routine is a switch on v.Op.
|
// Main rewrite routine is a switch on v.Op.
|
||||||
fmt.Fprintf(w, "func rewriteValue%s(v *Value) bool {\n", arch.name)
|
fmt.Fprintf(w, "func rewriteValue%s(v *Value) bool {\n", arch.name)
|
||||||
|
|
|
||||||
|
|
@ -114,7 +114,7 @@
|
||||||
package ssa
|
package ssa
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"cmd/internal/obj"
|
"cmd/internal/objabi"
|
||||||
"cmd/internal/src"
|
"cmd/internal/src"
|
||||||
"fmt"
|
"fmt"
|
||||||
"unsafe"
|
"unsafe"
|
||||||
|
|
@ -552,7 +552,7 @@ func (s *regAllocState) init(f *Func) {
|
||||||
// Leaf functions don't save/restore the link register.
|
// Leaf functions don't save/restore the link register.
|
||||||
s.allocatable &^= 1 << uint(s.f.Config.LinkReg)
|
s.allocatable &^= 1 << uint(s.f.Config.LinkReg)
|
||||||
}
|
}
|
||||||
if s.f.Config.arch == "arm" && obj.GOARM == 5 {
|
if s.f.Config.arch == "arm" && objabi.GOARM == 5 {
|
||||||
// On ARMv5 we insert softfloat calls at each FP instruction.
|
// On ARMv5 we insert softfloat calls at each FP instruction.
|
||||||
// This clobbers LR almost everywhere. Disable allocating LR
|
// This clobbers LR almost everywhere. Disable allocating LR
|
||||||
// on ARMv5.
|
// on ARMv5.
|
||||||
|
|
|
||||||
|
|
@ -5,9 +5,12 @@ package ssa
|
||||||
|
|
||||||
import "math"
|
import "math"
|
||||||
import "cmd/internal/obj"
|
import "cmd/internal/obj"
|
||||||
|
import "cmd/internal/objabi"
|
||||||
|
|
||||||
var _ = math.MinInt8 // in case not otherwise used
|
var _ = math.MinInt8 // in case not otherwise used
|
||||||
var _ = obj.ANOP // in case not otherwise used
|
var _ = obj.ANOP // in case not otherwise used
|
||||||
|
var _ = objabi.GOROOT // in case not otherwise used
|
||||||
|
|
||||||
func rewriteValue386(v *Value) bool {
|
func rewriteValue386(v *Value) bool {
|
||||||
switch v.Op {
|
switch v.Op {
|
||||||
case Op386ADCL:
|
case Op386ADCL:
|
||||||
|
|
|
||||||
|
|
@ -5,9 +5,12 @@ package ssa
|
||||||
|
|
||||||
import "math"
|
import "math"
|
||||||
import "cmd/internal/obj"
|
import "cmd/internal/obj"
|
||||||
|
import "cmd/internal/objabi"
|
||||||
|
|
||||||
var _ = math.MinInt8 // in case not otherwise used
|
var _ = math.MinInt8 // in case not otherwise used
|
||||||
var _ = obj.ANOP // in case not otherwise used
|
var _ = obj.ANOP // in case not otherwise used
|
||||||
|
var _ = objabi.GOROOT // in case not otherwise used
|
||||||
|
|
||||||
func rewriteValueAMD64(v *Value) bool {
|
func rewriteValueAMD64(v *Value) bool {
|
||||||
switch v.Op {
|
switch v.Op {
|
||||||
case OpAMD64ADDL:
|
case OpAMD64ADDL:
|
||||||
|
|
|
||||||
|
|
@ -5,9 +5,12 @@ package ssa
|
||||||
|
|
||||||
import "math"
|
import "math"
|
||||||
import "cmd/internal/obj"
|
import "cmd/internal/obj"
|
||||||
|
import "cmd/internal/objabi"
|
||||||
|
|
||||||
var _ = math.MinInt8 // in case not otherwise used
|
var _ = math.MinInt8 // in case not otherwise used
|
||||||
var _ = obj.ANOP // in case not otherwise used
|
var _ = obj.ANOP // in case not otherwise used
|
||||||
|
var _ = objabi.GOROOT // in case not otherwise used
|
||||||
|
|
||||||
func rewriteValueARM(v *Value) bool {
|
func rewriteValueARM(v *Value) bool {
|
||||||
switch v.Op {
|
switch v.Op {
|
||||||
case OpARMADC:
|
case OpARMADC:
|
||||||
|
|
@ -13196,12 +13199,12 @@ func rewriteValueARM_OpBswap32(v *Value) bool {
|
||||||
b := v.Block
|
b := v.Block
|
||||||
_ = b
|
_ = b
|
||||||
// match: (Bswap32 <t> x)
|
// match: (Bswap32 <t> x)
|
||||||
// cond: obj.GOARM==5
|
// cond: objabi.GOARM==5
|
||||||
// result: (XOR <t> (SRLconst <t> (BICconst <t> (XOR <t> x (SRRconst <t> [16] x)) [0xff0000]) [8]) (SRRconst <t> x [8]))
|
// result: (XOR <t> (SRLconst <t> (BICconst <t> (XOR <t> x (SRRconst <t> [16] x)) [0xff0000]) [8]) (SRRconst <t> x [8]))
|
||||||
for {
|
for {
|
||||||
t := v.Type
|
t := v.Type
|
||||||
x := v.Args[0]
|
x := v.Args[0]
|
||||||
if !(obj.GOARM == 5) {
|
if !(objabi.GOARM == 5) {
|
||||||
break
|
break
|
||||||
}
|
}
|
||||||
v.reset(OpARMXOR)
|
v.reset(OpARMXOR)
|
||||||
|
|
@ -13226,11 +13229,11 @@ func rewriteValueARM_OpBswap32(v *Value) bool {
|
||||||
return true
|
return true
|
||||||
}
|
}
|
||||||
// match: (Bswap32 x)
|
// match: (Bswap32 x)
|
||||||
// cond: obj.GOARM>=6
|
// cond: objabi.GOARM>=6
|
||||||
// result: (REV x)
|
// result: (REV x)
|
||||||
for {
|
for {
|
||||||
x := v.Args[0]
|
x := v.Args[0]
|
||||||
if !(obj.GOARM >= 6) {
|
if !(objabi.GOARM >= 6) {
|
||||||
break
|
break
|
||||||
}
|
}
|
||||||
v.reset(OpARMREV)
|
v.reset(OpARMREV)
|
||||||
|
|
@ -13382,12 +13385,12 @@ func rewriteValueARM_OpCtz32(v *Value) bool {
|
||||||
b := v.Block
|
b := v.Block
|
||||||
_ = b
|
_ = b
|
||||||
// match: (Ctz32 <t> x)
|
// match: (Ctz32 <t> x)
|
||||||
// cond: obj.GOARM<=6
|
// cond: objabi.GOARM<=6
|
||||||
// result: (RSBconst [32] (CLZ <t> (SUBconst <t> (AND <t> x (RSBconst <t> [0] x)) [1])))
|
// result: (RSBconst [32] (CLZ <t> (SUBconst <t> (AND <t> x (RSBconst <t> [0] x)) [1])))
|
||||||
for {
|
for {
|
||||||
t := v.Type
|
t := v.Type
|
||||||
x := v.Args[0]
|
x := v.Args[0]
|
||||||
if !(obj.GOARM <= 6) {
|
if !(objabi.GOARM <= 6) {
|
||||||
break
|
break
|
||||||
}
|
}
|
||||||
v.reset(OpARMRSBconst)
|
v.reset(OpARMRSBconst)
|
||||||
|
|
@ -13407,12 +13410,12 @@ func rewriteValueARM_OpCtz32(v *Value) bool {
|
||||||
return true
|
return true
|
||||||
}
|
}
|
||||||
// match: (Ctz32 <t> x)
|
// match: (Ctz32 <t> x)
|
||||||
// cond: obj.GOARM==7
|
// cond: objabi.GOARM==7
|
||||||
// result: (CLZ <t> (RBIT <t> x))
|
// result: (CLZ <t> (RBIT <t> x))
|
||||||
for {
|
for {
|
||||||
t := v.Type
|
t := v.Type
|
||||||
x := v.Args[0]
|
x := v.Args[0]
|
||||||
if !(obj.GOARM == 7) {
|
if !(objabi.GOARM == 7) {
|
||||||
break
|
break
|
||||||
}
|
}
|
||||||
v.reset(OpARMCLZ)
|
v.reset(OpARMCLZ)
|
||||||
|
|
|
||||||
|
|
@ -5,9 +5,12 @@ package ssa
|
||||||
|
|
||||||
import "math"
|
import "math"
|
||||||
import "cmd/internal/obj"
|
import "cmd/internal/obj"
|
||||||
|
import "cmd/internal/objabi"
|
||||||
|
|
||||||
var _ = math.MinInt8 // in case not otherwise used
|
var _ = math.MinInt8 // in case not otherwise used
|
||||||
var _ = obj.ANOP // in case not otherwise used
|
var _ = obj.ANOP // in case not otherwise used
|
||||||
|
var _ = objabi.GOROOT // in case not otherwise used
|
||||||
|
|
||||||
func rewriteValueARM64(v *Value) bool {
|
func rewriteValueARM64(v *Value) bool {
|
||||||
switch v.Op {
|
switch v.Op {
|
||||||
case OpARM64ADD:
|
case OpARM64ADD:
|
||||||
|
|
|
||||||
|
|
@ -5,9 +5,12 @@ package ssa
|
||||||
|
|
||||||
import "math"
|
import "math"
|
||||||
import "cmd/internal/obj"
|
import "cmd/internal/obj"
|
||||||
|
import "cmd/internal/objabi"
|
||||||
|
|
||||||
var _ = math.MinInt8 // in case not otherwise used
|
var _ = math.MinInt8 // in case not otherwise used
|
||||||
var _ = obj.ANOP // in case not otherwise used
|
var _ = obj.ANOP // in case not otherwise used
|
||||||
|
var _ = objabi.GOROOT // in case not otherwise used
|
||||||
|
|
||||||
func rewriteValueMIPS(v *Value) bool {
|
func rewriteValueMIPS(v *Value) bool {
|
||||||
switch v.Op {
|
switch v.Op {
|
||||||
case OpAdd16:
|
case OpAdd16:
|
||||||
|
|
|
||||||
|
|
@ -5,9 +5,12 @@ package ssa
|
||||||
|
|
||||||
import "math"
|
import "math"
|
||||||
import "cmd/internal/obj"
|
import "cmd/internal/obj"
|
||||||
|
import "cmd/internal/objabi"
|
||||||
|
|
||||||
var _ = math.MinInt8 // in case not otherwise used
|
var _ = math.MinInt8 // in case not otherwise used
|
||||||
var _ = obj.ANOP // in case not otherwise used
|
var _ = obj.ANOP // in case not otherwise used
|
||||||
|
var _ = objabi.GOROOT // in case not otherwise used
|
||||||
|
|
||||||
func rewriteValueMIPS64(v *Value) bool {
|
func rewriteValueMIPS64(v *Value) bool {
|
||||||
switch v.Op {
|
switch v.Op {
|
||||||
case OpAdd16:
|
case OpAdd16:
|
||||||
|
|
|
||||||
|
|
@ -5,9 +5,12 @@ package ssa
|
||||||
|
|
||||||
import "math"
|
import "math"
|
||||||
import "cmd/internal/obj"
|
import "cmd/internal/obj"
|
||||||
|
import "cmd/internal/objabi"
|
||||||
|
|
||||||
var _ = math.MinInt8 // in case not otherwise used
|
var _ = math.MinInt8 // in case not otherwise used
|
||||||
var _ = obj.ANOP // in case not otherwise used
|
var _ = obj.ANOP // in case not otherwise used
|
||||||
|
var _ = objabi.GOROOT // in case not otherwise used
|
||||||
|
|
||||||
func rewriteValuePPC64(v *Value) bool {
|
func rewriteValuePPC64(v *Value) bool {
|
||||||
switch v.Op {
|
switch v.Op {
|
||||||
case OpAdd16:
|
case OpAdd16:
|
||||||
|
|
|
||||||
|
|
@ -5,9 +5,12 @@ package ssa
|
||||||
|
|
||||||
import "math"
|
import "math"
|
||||||
import "cmd/internal/obj"
|
import "cmd/internal/obj"
|
||||||
|
import "cmd/internal/objabi"
|
||||||
|
|
||||||
var _ = math.MinInt8 // in case not otherwise used
|
var _ = math.MinInt8 // in case not otherwise used
|
||||||
var _ = obj.ANOP // in case not otherwise used
|
var _ = obj.ANOP // in case not otherwise used
|
||||||
|
var _ = objabi.GOROOT // in case not otherwise used
|
||||||
|
|
||||||
func rewriteValueS390X(v *Value) bool {
|
func rewriteValueS390X(v *Value) bool {
|
||||||
switch v.Op {
|
switch v.Op {
|
||||||
case OpAdd16:
|
case OpAdd16:
|
||||||
|
|
|
||||||
|
|
@ -5,9 +5,12 @@ package ssa
|
||||||
|
|
||||||
import "math"
|
import "math"
|
||||||
import "cmd/internal/obj"
|
import "cmd/internal/obj"
|
||||||
|
import "cmd/internal/objabi"
|
||||||
|
|
||||||
var _ = math.MinInt8 // in case not otherwise used
|
var _ = math.MinInt8 // in case not otherwise used
|
||||||
var _ = obj.ANOP // in case not otherwise used
|
var _ = obj.ANOP // in case not otherwise used
|
||||||
|
var _ = objabi.GOROOT // in case not otherwise used
|
||||||
|
|
||||||
func rewriteValuedec(v *Value) bool {
|
func rewriteValuedec(v *Value) bool {
|
||||||
switch v.Op {
|
switch v.Op {
|
||||||
case OpComplexImag:
|
case OpComplexImag:
|
||||||
|
|
|
||||||
|
|
@ -5,9 +5,12 @@ package ssa
|
||||||
|
|
||||||
import "math"
|
import "math"
|
||||||
import "cmd/internal/obj"
|
import "cmd/internal/obj"
|
||||||
|
import "cmd/internal/objabi"
|
||||||
|
|
||||||
var _ = math.MinInt8 // in case not otherwise used
|
var _ = math.MinInt8 // in case not otherwise used
|
||||||
var _ = obj.ANOP // in case not otherwise used
|
var _ = obj.ANOP // in case not otherwise used
|
||||||
|
var _ = objabi.GOROOT // in case not otherwise used
|
||||||
|
|
||||||
func rewriteValuedec64(v *Value) bool {
|
func rewriteValuedec64(v *Value) bool {
|
||||||
switch v.Op {
|
switch v.Op {
|
||||||
case OpAdd64:
|
case OpAdd64:
|
||||||
|
|
|
||||||
|
|
@ -5,9 +5,12 @@ package ssa
|
||||||
|
|
||||||
import "math"
|
import "math"
|
||||||
import "cmd/internal/obj"
|
import "cmd/internal/obj"
|
||||||
|
import "cmd/internal/objabi"
|
||||||
|
|
||||||
var _ = math.MinInt8 // in case not otherwise used
|
var _ = math.MinInt8 // in case not otherwise used
|
||||||
var _ = obj.ANOP // in case not otherwise used
|
var _ = obj.ANOP // in case not otherwise used
|
||||||
|
var _ = objabi.GOROOT // in case not otherwise used
|
||||||
|
|
||||||
func rewriteValuegeneric(v *Value) bool {
|
func rewriteValuegeneric(v *Value) bool {
|
||||||
switch v.Op {
|
switch v.Op {
|
||||||
case OpAdd16:
|
case OpAdd16:
|
||||||
|
|
|
||||||
|
|
@ -6,8 +6,8 @@ package x86
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"cmd/compile/internal/gc"
|
"cmd/compile/internal/gc"
|
||||||
"cmd/internal/obj"
|
|
||||||
"cmd/internal/obj/x86"
|
"cmd/internal/obj/x86"
|
||||||
|
"cmd/internal/objabi"
|
||||||
"fmt"
|
"fmt"
|
||||||
"os"
|
"os"
|
||||||
)
|
)
|
||||||
|
|
@ -15,7 +15,7 @@ import (
|
||||||
func Init(arch *gc.Arch) {
|
func Init(arch *gc.Arch) {
|
||||||
arch.LinkArch = &x86.Link386
|
arch.LinkArch = &x86.Link386
|
||||||
arch.REGSP = x86.REGSP
|
arch.REGSP = x86.REGSP
|
||||||
switch v := obj.GO386; v {
|
switch v := objabi.GO386; v {
|
||||||
case "387":
|
case "387":
|
||||||
arch.Use387 = true
|
arch.Use387 = true
|
||||||
arch.SSAGenValue = ssaGenValue387
|
arch.SSAGenValue = ssaGenValue387
|
||||||
|
|
|
||||||
|
|
@ -14,7 +14,7 @@ import (
|
||||||
"cmd/compile/internal/ppc64"
|
"cmd/compile/internal/ppc64"
|
||||||
"cmd/compile/internal/s390x"
|
"cmd/compile/internal/s390x"
|
||||||
"cmd/compile/internal/x86"
|
"cmd/compile/internal/x86"
|
||||||
"cmd/internal/obj"
|
"cmd/internal/objabi"
|
||||||
"fmt"
|
"fmt"
|
||||||
"log"
|
"log"
|
||||||
"os"
|
"os"
|
||||||
|
|
@ -40,9 +40,9 @@ func main() {
|
||||||
log.SetFlags(0)
|
log.SetFlags(0)
|
||||||
log.SetPrefix("compile: ")
|
log.SetPrefix("compile: ")
|
||||||
|
|
||||||
archInit, ok := archInits[obj.GOARCH]
|
archInit, ok := archInits[objabi.GOARCH]
|
||||||
if !ok {
|
if !ok {
|
||||||
fmt.Fprintf(os.Stderr, "compile: unknown architecture %q\n", obj.GOARCH)
|
fmt.Fprintf(os.Stderr, "compile: unknown architecture %q\n", objabi.GOARCH)
|
||||||
os.Exit(2)
|
os.Exit(2)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
6
src/cmd/dist/buildruntime.go
vendored
6
src/cmd/dist/buildruntime.go
vendored
|
|
@ -36,9 +36,9 @@ func mkzversion(dir, file string) {
|
||||||
writefile(out, file, writeSkipSame)
|
writefile(out, file, writeSkipSame)
|
||||||
}
|
}
|
||||||
|
|
||||||
// mkzbootstrap writes cmd/internal/obj/zbootstrap.go:
|
// mkzbootstrap writes cmd/internal/objabi/zbootstrap.go:
|
||||||
//
|
//
|
||||||
// package obj
|
// package objabi
|
||||||
//
|
//
|
||||||
// const defaultGOROOT = <goroot>
|
// const defaultGOROOT = <goroot>
|
||||||
// const defaultGO386 = <go386>
|
// const defaultGO386 = <go386>
|
||||||
|
|
@ -63,7 +63,7 @@ func mkzbootstrap(file string) {
|
||||||
out := fmt.Sprintf(
|
out := fmt.Sprintf(
|
||||||
"// auto generated by go tool dist\n"+
|
"// auto generated by go tool dist\n"+
|
||||||
"\n"+
|
"\n"+
|
||||||
"package obj\n"+
|
"package objabi\n"+
|
||||||
"\n"+
|
"\n"+
|
||||||
"import \"runtime\"\n"+
|
"import \"runtime\"\n"+
|
||||||
"\n"+
|
"\n"+
|
||||||
|
|
|
||||||
3
src/cmd/dist/buildtool.go
vendored
3
src/cmd/dist/buildtool.go
vendored
|
|
@ -51,6 +51,7 @@ var bootstrapDirs = []string{
|
||||||
"cmd/internal/bio",
|
"cmd/internal/bio",
|
||||||
"cmd/internal/gcprog",
|
"cmd/internal/gcprog",
|
||||||
"cmd/internal/dwarf",
|
"cmd/internal/dwarf",
|
||||||
|
"cmd/internal/objabi",
|
||||||
"cmd/internal/obj",
|
"cmd/internal/obj",
|
||||||
"cmd/internal/obj/arm",
|
"cmd/internal/obj/arm",
|
||||||
"cmd/internal/obj/arm64",
|
"cmd/internal/obj/arm64",
|
||||||
|
|
@ -96,7 +97,7 @@ func bootstrapBuildTools() {
|
||||||
}
|
}
|
||||||
xprintf("##### Building Go toolchain using %s.\n", goroot_bootstrap)
|
xprintf("##### Building Go toolchain using %s.\n", goroot_bootstrap)
|
||||||
|
|
||||||
mkzbootstrap(pathf("%s/src/cmd/internal/obj/zbootstrap.go", goroot))
|
mkzbootstrap(pathf("%s/src/cmd/internal/objabi/zbootstrap.go", goroot))
|
||||||
|
|
||||||
// Use $GOROOT/pkg/bootstrap as the bootstrap workspace root.
|
// Use $GOROOT/pkg/bootstrap as the bootstrap workspace root.
|
||||||
// We use a subdirectory of $GOROOT/pkg because that's the
|
// We use a subdirectory of $GOROOT/pkg because that's the
|
||||||
|
|
|
||||||
|
|
@ -12,7 +12,7 @@ package goobj
|
||||||
import (
|
import (
|
||||||
"bufio"
|
"bufio"
|
||||||
"bytes"
|
"bytes"
|
||||||
"cmd/internal/obj"
|
"cmd/internal/objabi"
|
||||||
"errors"
|
"errors"
|
||||||
"fmt"
|
"fmt"
|
||||||
"io"
|
"io"
|
||||||
|
|
@ -20,107 +20,10 @@ import (
|
||||||
"strings"
|
"strings"
|
||||||
)
|
)
|
||||||
|
|
||||||
// A SymKind describes the kind of memory represented by a symbol.
|
|
||||||
type SymKind int
|
|
||||||
|
|
||||||
// This list is taken from include/link.h.
|
|
||||||
|
|
||||||
// Defined SymKind values.
|
|
||||||
// TODO(rsc): Give idiomatic Go names.
|
|
||||||
// TODO(rsc): Reduce the number of symbol types in the object files.
|
|
||||||
const (
|
|
||||||
// readonly, executable
|
|
||||||
STEXT = SymKind(obj.STEXT)
|
|
||||||
SELFRXSECT = SymKind(obj.SELFRXSECT)
|
|
||||||
|
|
||||||
// readonly, non-executable
|
|
||||||
STYPE = SymKind(obj.STYPE)
|
|
||||||
SSTRING = SymKind(obj.SSTRING)
|
|
||||||
SGOSTRING = SymKind(obj.SGOSTRING)
|
|
||||||
SGOFUNC = SymKind(obj.SGOFUNC)
|
|
||||||
SRODATA = SymKind(obj.SRODATA)
|
|
||||||
SFUNCTAB = SymKind(obj.SFUNCTAB)
|
|
||||||
STYPELINK = SymKind(obj.STYPELINK)
|
|
||||||
SITABLINK = SymKind(obj.SITABLINK)
|
|
||||||
SSYMTAB = SymKind(obj.SSYMTAB) // TODO: move to unmapped section
|
|
||||||
SPCLNTAB = SymKind(obj.SPCLNTAB)
|
|
||||||
SELFROSECT = SymKind(obj.SELFROSECT)
|
|
||||||
|
|
||||||
// writable, non-executable
|
|
||||||
SMACHOPLT = SymKind(obj.SMACHOPLT)
|
|
||||||
SELFSECT = SymKind(obj.SELFSECT)
|
|
||||||
SMACHO = SymKind(obj.SMACHO) // Mach-O __nl_symbol_ptr
|
|
||||||
SMACHOGOT = SymKind(obj.SMACHOGOT)
|
|
||||||
SWINDOWS = SymKind(obj.SWINDOWS)
|
|
||||||
SELFGOT = SymKind(obj.SELFGOT)
|
|
||||||
SNOPTRDATA = SymKind(obj.SNOPTRDATA)
|
|
||||||
SINITARR = SymKind(obj.SINITARR)
|
|
||||||
SDATA = SymKind(obj.SDATA)
|
|
||||||
SBSS = SymKind(obj.SBSS)
|
|
||||||
SNOPTRBSS = SymKind(obj.SNOPTRBSS)
|
|
||||||
STLSBSS = SymKind(obj.STLSBSS)
|
|
||||||
|
|
||||||
// not mapped
|
|
||||||
SXREF = SymKind(obj.SXREF)
|
|
||||||
SMACHOSYMSTR = SymKind(obj.SMACHOSYMSTR)
|
|
||||||
SMACHOSYMTAB = SymKind(obj.SMACHOSYMTAB)
|
|
||||||
SMACHOINDIRECTPLT = SymKind(obj.SMACHOINDIRECTPLT)
|
|
||||||
SMACHOINDIRECTGOT = SymKind(obj.SMACHOINDIRECTGOT)
|
|
||||||
SFILE = SymKind(obj.SFILE)
|
|
||||||
SFILEPATH = SymKind(obj.SFILEPATH)
|
|
||||||
SCONST = SymKind(obj.SCONST)
|
|
||||||
SDYNIMPORT = SymKind(obj.SDYNIMPORT)
|
|
||||||
SHOSTOBJ = SymKind(obj.SHOSTOBJ)
|
|
||||||
)
|
|
||||||
|
|
||||||
var symKindStrings = []string{
|
|
||||||
SBSS: "SBSS",
|
|
||||||
SCONST: "SCONST",
|
|
||||||
SDATA: "SDATA",
|
|
||||||
SDYNIMPORT: "SDYNIMPORT",
|
|
||||||
SELFROSECT: "SELFROSECT",
|
|
||||||
SELFRXSECT: "SELFRXSECT",
|
|
||||||
SELFSECT: "SELFSECT",
|
|
||||||
SFILE: "SFILE",
|
|
||||||
SFILEPATH: "SFILEPATH",
|
|
||||||
SFUNCTAB: "SFUNCTAB",
|
|
||||||
SGOFUNC: "SGOFUNC",
|
|
||||||
SGOSTRING: "SGOSTRING",
|
|
||||||
SHOSTOBJ: "SHOSTOBJ",
|
|
||||||
SINITARR: "SINITARR",
|
|
||||||
SMACHO: "SMACHO",
|
|
||||||
SMACHOGOT: "SMACHOGOT",
|
|
||||||
SMACHOINDIRECTGOT: "SMACHOINDIRECTGOT",
|
|
||||||
SMACHOINDIRECTPLT: "SMACHOINDIRECTPLT",
|
|
||||||
SMACHOPLT: "SMACHOPLT",
|
|
||||||
SMACHOSYMSTR: "SMACHOSYMSTR",
|
|
||||||
SMACHOSYMTAB: "SMACHOSYMTAB",
|
|
||||||
SNOPTRBSS: "SNOPTRBSS",
|
|
||||||
SNOPTRDATA: "SNOPTRDATA",
|
|
||||||
SPCLNTAB: "SPCLNTAB",
|
|
||||||
SRODATA: "SRODATA",
|
|
||||||
SSTRING: "SSTRING",
|
|
||||||
SSYMTAB: "SSYMTAB",
|
|
||||||
STEXT: "STEXT",
|
|
||||||
STLSBSS: "STLSBSS",
|
|
||||||
STYPE: "STYPE",
|
|
||||||
STYPELINK: "STYPELINK",
|
|
||||||
SITABLINK: "SITABLINK",
|
|
||||||
SWINDOWS: "SWINDOWS",
|
|
||||||
SXREF: "SXREF",
|
|
||||||
}
|
|
||||||
|
|
||||||
func (k SymKind) String() string {
|
|
||||||
if k < 0 || int(k) >= len(symKindStrings) {
|
|
||||||
return fmt.Sprintf("SymKind(%d)", k)
|
|
||||||
}
|
|
||||||
return symKindStrings[k]
|
|
||||||
}
|
|
||||||
|
|
||||||
// A Sym is a named symbol in an object file.
|
// A Sym is a named symbol in an object file.
|
||||||
type Sym struct {
|
type Sym struct {
|
||||||
SymID // symbol identifier (name and version)
|
SymID // symbol identifier (name and version)
|
||||||
Kind SymKind // kind of symbol
|
Kind objabi.SymKind // kind of symbol
|
||||||
DupOK bool // are duplicate definitions okay?
|
DupOK bool // are duplicate definitions okay?
|
||||||
Size int // size of corresponding data
|
Size int // size of corresponding data
|
||||||
Type SymID // symbol for Go type information
|
Type SymID // symbol for Go type information
|
||||||
|
|
@ -172,7 +75,7 @@ type Reloc struct {
|
||||||
// The Type records the form of address expected in the bytes
|
// The Type records the form of address expected in the bytes
|
||||||
// described by the previous fields: absolute, PC-relative, and so on.
|
// described by the previous fields: absolute, PC-relative, and so on.
|
||||||
// TODO(rsc): The interpretation of Type is not exposed by this package.
|
// TODO(rsc): The interpretation of Type is not exposed by this package.
|
||||||
Type obj.RelocType
|
Type objabi.RelocType
|
||||||
}
|
}
|
||||||
|
|
||||||
// A Var describes a variable in a function stack frame: a declared
|
// A Var describes a variable in a function stack frame: a declared
|
||||||
|
|
@ -646,7 +549,7 @@ func (r *objReader) parseObject(prefix []byte) error {
|
||||||
typ := r.readInt()
|
typ := r.readInt()
|
||||||
s := &Sym{SymID: r.readSymID()}
|
s := &Sym{SymID: r.readSymID()}
|
||||||
r.p.Syms = append(r.p.Syms, s)
|
r.p.Syms = append(r.p.Syms, s)
|
||||||
s.Kind = SymKind(typ)
|
s.Kind = objabi.SymKind(typ)
|
||||||
flags := r.readInt()
|
flags := r.readInt()
|
||||||
s.DupOK = flags&1 != 0
|
s.DupOK = flags&1 != 0
|
||||||
s.Size = r.readInt()
|
s.Size = r.readInt()
|
||||||
|
|
@ -657,12 +560,12 @@ func (r *objReader) parseObject(prefix []byte) error {
|
||||||
rel := &s.Reloc[i]
|
rel := &s.Reloc[i]
|
||||||
rel.Offset = r.readInt()
|
rel.Offset = r.readInt()
|
||||||
rel.Size = r.readInt()
|
rel.Size = r.readInt()
|
||||||
rel.Type = obj.RelocType(r.readInt())
|
rel.Type = objabi.RelocType(r.readInt())
|
||||||
rel.Add = r.readInt()
|
rel.Add = r.readInt()
|
||||||
rel.Sym = r.readSymID()
|
rel.Sym = r.readSymID()
|
||||||
}
|
}
|
||||||
|
|
||||||
if s.Kind == STEXT {
|
if s.Kind == objabi.STEXT {
|
||||||
f := new(Func)
|
f := new(Func)
|
||||||
s.Func = f
|
s.Func = f
|
||||||
f.Args = r.readInt()
|
f.Args = r.readInt()
|
||||||
|
|
|
||||||
|
|
@ -32,6 +32,7 @@ package arm
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"cmd/internal/obj"
|
"cmd/internal/obj"
|
||||||
|
"cmd/internal/objabi"
|
||||||
"fmt"
|
"fmt"
|
||||||
"log"
|
"log"
|
||||||
"math"
|
"math"
|
||||||
|
|
@ -602,7 +603,7 @@ func span5(ctxt *obj.Link, cursym *obj.LSym, newprog obj.ProgAlloc) {
|
||||||
|
|
||||||
p.Pc = int64(pc)
|
p.Pc = int64(pc)
|
||||||
o = c.oplook(p)
|
o = c.oplook(p)
|
||||||
if ctxt.Headtype != obj.Hnacl {
|
if ctxt.Headtype != objabi.Hnacl {
|
||||||
m = int(o.size)
|
m = int(o.size)
|
||||||
} else {
|
} else {
|
||||||
m = c.asmoutnacl(pc, p, o, nil)
|
m = c.asmoutnacl(pc, p, o, nil)
|
||||||
|
|
@ -696,7 +697,7 @@ func span5(ctxt *obj.Link, cursym *obj.LSym, newprog obj.ProgAlloc) {
|
||||||
*/
|
*/
|
||||||
opc = int32(p.Pc)
|
opc = int32(p.Pc)
|
||||||
|
|
||||||
if ctxt.Headtype != obj.Hnacl {
|
if ctxt.Headtype != objabi.Hnacl {
|
||||||
m = int(o.size)
|
m = int(o.size)
|
||||||
} else {
|
} else {
|
||||||
m = c.asmoutnacl(pc, p, o, nil)
|
m = c.asmoutnacl(pc, p, o, nil)
|
||||||
|
|
@ -756,7 +757,7 @@ func span5(ctxt *obj.Link, cursym *obj.LSym, newprog obj.ProgAlloc) {
|
||||||
c.pc = p.Pc
|
c.pc = p.Pc
|
||||||
o = c.oplook(p)
|
o = c.oplook(p)
|
||||||
opc = int32(p.Pc)
|
opc = int32(p.Pc)
|
||||||
if ctxt.Headtype != obj.Hnacl {
|
if ctxt.Headtype != objabi.Hnacl {
|
||||||
c.asmout(p, o, out[:])
|
c.asmout(p, o, out[:])
|
||||||
m = int(o.size)
|
m = int(o.size)
|
||||||
} else {
|
} else {
|
||||||
|
|
@ -834,7 +835,7 @@ func (c *ctxt5) flushpool(p *obj.Prog, skip int, force int) bool {
|
||||||
} else if force == 0 && (p.Pc+int64(12+c.pool.size)-int64(c.pool.start) < 2048) { // 12 take into account the maximum nacl literal pool alignment padding size
|
} else if force == 0 && (p.Pc+int64(12+c.pool.size)-int64(c.pool.start) < 2048) { // 12 take into account the maximum nacl literal pool alignment padding size
|
||||||
return false
|
return false
|
||||||
}
|
}
|
||||||
if c.ctxt.Headtype == obj.Hnacl && c.pool.size%16 != 0 {
|
if c.ctxt.Headtype == objabi.Hnacl && c.pool.size%16 != 0 {
|
||||||
// if pool is not multiple of 16 bytes, add an alignment marker
|
// if pool is not multiple of 16 bytes, add an alignment marker
|
||||||
q := c.newprog()
|
q := c.newprog()
|
||||||
|
|
||||||
|
|
@ -902,7 +903,7 @@ func (c *ctxt5) addpool(p *obj.Prog, a *obj.Addr) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if c.ctxt.Headtype == obj.Hnacl && c.pool.size%16 == 0 {
|
if c.ctxt.Headtype == objabi.Hnacl && c.pool.size%16 == 0 {
|
||||||
// start a new data bundle
|
// start a new data bundle
|
||||||
q := c.newprog()
|
q := c.newprog()
|
||||||
q.As = ADATABUNDLE
|
q.As = ADATABUNDLE
|
||||||
|
|
@ -1019,7 +1020,7 @@ func (c *ctxt5) aclass(a *obj.Addr) int {
|
||||||
}
|
}
|
||||||
|
|
||||||
c.instoffset = 0 // s.b. unused but just in case
|
c.instoffset = 0 // s.b. unused but just in case
|
||||||
if a.Sym.Type == obj.STLSBSS {
|
if a.Sym.Type == objabi.STLSBSS {
|
||||||
if c.ctxt.Flag_shared {
|
if c.ctxt.Flag_shared {
|
||||||
return C_TLS_IE
|
return C_TLS_IE
|
||||||
} else {
|
} else {
|
||||||
|
|
@ -1584,7 +1585,7 @@ func (c *ctxt5) asmout(p *obj.Prog, o *Optab, out []uint32) {
|
||||||
rel.Sym = p.To.Sym
|
rel.Sym = p.To.Sym
|
||||||
v += int32(p.To.Offset)
|
v += int32(p.To.Offset)
|
||||||
rel.Add = int64(o1) | (int64(v)>>2)&0xffffff
|
rel.Add = int64(o1) | (int64(v)>>2)&0xffffff
|
||||||
rel.Type = obj.R_CALLARM
|
rel.Type = objabi.R_CALLARM
|
||||||
break
|
break
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -1612,7 +1613,7 @@ func (c *ctxt5) asmout(p *obj.Prog, o *Optab, out []uint32) {
|
||||||
rel := obj.Addrel(c.cursym)
|
rel := obj.Addrel(c.cursym)
|
||||||
rel.Off = int32(c.pc)
|
rel.Off = int32(c.pc)
|
||||||
rel.Siz = 0
|
rel.Siz = 0
|
||||||
rel.Type = obj.R_CALLIND
|
rel.Type = objabi.R_CALLIND
|
||||||
|
|
||||||
case 8: /* sll $c,[R],R -> mov (R<<$c),R */
|
case 8: /* sll $c,[R],R -> mov (R<<$c),R */
|
||||||
c.aclass(&p.From)
|
c.aclass(&p.From)
|
||||||
|
|
@ -1661,13 +1662,13 @@ func (c *ctxt5) asmout(p *obj.Prog, o *Optab, out []uint32) {
|
||||||
|
|
||||||
if c.ctxt.Flag_shared {
|
if c.ctxt.Flag_shared {
|
||||||
if p.To.Name == obj.NAME_GOTREF {
|
if p.To.Name == obj.NAME_GOTREF {
|
||||||
rel.Type = obj.R_GOTPCREL
|
rel.Type = objabi.R_GOTPCREL
|
||||||
} else {
|
} else {
|
||||||
rel.Type = obj.R_PCREL
|
rel.Type = objabi.R_PCREL
|
||||||
}
|
}
|
||||||
rel.Add += c.pc - p.Rel.Pc - 8
|
rel.Add += c.pc - p.Rel.Pc - 8
|
||||||
} else {
|
} else {
|
||||||
rel.Type = obj.R_ADDR
|
rel.Type = objabi.R_ADDR
|
||||||
}
|
}
|
||||||
o1 = 0
|
o1 = 0
|
||||||
}
|
}
|
||||||
|
|
@ -2080,7 +2081,7 @@ func (c *ctxt5) asmout(p *obj.Prog, o *Optab, out []uint32) {
|
||||||
rel.Off = int32(c.pc)
|
rel.Off = int32(c.pc)
|
||||||
rel.Siz = 4
|
rel.Siz = 4
|
||||||
rel.Sym = p.To.Sym
|
rel.Sym = p.To.Sym
|
||||||
rel.Type = obj.R_TLS_LE
|
rel.Type = objabi.R_TLS_LE
|
||||||
o1 = 0
|
o1 = 0
|
||||||
|
|
||||||
case 104: /* word tlsvar, initial exec */
|
case 104: /* word tlsvar, initial exec */
|
||||||
|
|
@ -2094,7 +2095,7 @@ func (c *ctxt5) asmout(p *obj.Prog, o *Optab, out []uint32) {
|
||||||
rel.Off = int32(c.pc)
|
rel.Off = int32(c.pc)
|
||||||
rel.Siz = 4
|
rel.Siz = 4
|
||||||
rel.Sym = p.To.Sym
|
rel.Sym = p.To.Sym
|
||||||
rel.Type = obj.R_TLS_IE
|
rel.Type = objabi.R_TLS_IE
|
||||||
rel.Add = c.pc - p.Rel.Pc - 8 - int64(rel.Siz)
|
rel.Add = c.pc - p.Rel.Pc - 8 - int64(rel.Siz)
|
||||||
|
|
||||||
case 68: /* floating point store -> ADDR */
|
case 68: /* floating point store -> ADDR */
|
||||||
|
|
@ -2849,7 +2850,7 @@ func (c *ctxt5) omvl(p *obj.Prog, a *obj.Addr, dr int) uint32 {
|
||||||
|
|
||||||
func (c *ctxt5) chipzero5(e float64) int {
|
func (c *ctxt5) chipzero5(e float64) int {
|
||||||
// We use GOARM=7 to gate the use of VFPv3 vmov (imm) instructions.
|
// We use GOARM=7 to gate the use of VFPv3 vmov (imm) instructions.
|
||||||
if obj.GOARM < 7 || e != 0 {
|
if objabi.GOARM < 7 || e != 0 {
|
||||||
return -1
|
return -1
|
||||||
}
|
}
|
||||||
return 0
|
return 0
|
||||||
|
|
@ -2857,7 +2858,7 @@ func (c *ctxt5) chipzero5(e float64) int {
|
||||||
|
|
||||||
func (c *ctxt5) chipfloat5(e float64) int {
|
func (c *ctxt5) chipfloat5(e float64) int {
|
||||||
// We use GOARM=7 to gate the use of VFPv3 vmov (imm) instructions.
|
// We use GOARM=7 to gate the use of VFPv3 vmov (imm) instructions.
|
||||||
if obj.GOARM < 7 {
|
if objabi.GOARM < 7 {
|
||||||
return -1
|
return -1
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -32,6 +32,7 @@ package arm
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"cmd/internal/obj"
|
"cmd/internal/obj"
|
||||||
|
"cmd/internal/objabi"
|
||||||
"cmd/internal/sys"
|
"cmd/internal/sys"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
|
@ -62,7 +63,7 @@ func progedit(ctxt *obj.Link, p *obj.Prog, newprog obj.ProgAlloc) {
|
||||||
ctxt.Diag("%v: TLS MRC instruction must write to R0 as it might get translated into a BL instruction", p.Line())
|
ctxt.Diag("%v: TLS MRC instruction must write to R0 as it might get translated into a BL instruction", p.Line())
|
||||||
}
|
}
|
||||||
|
|
||||||
if obj.GOARM < 7 {
|
if objabi.GOARM < 7 {
|
||||||
// Replace it with BL runtime.read_tls_fallback(SB) for ARM CPUs that lack the tls extension.
|
// Replace it with BL runtime.read_tls_fallback(SB) for ARM CPUs that lack the tls extension.
|
||||||
if progedit_tlsfallback == nil {
|
if progedit_tlsfallback == nil {
|
||||||
progedit_tlsfallback = ctxt.Lookup("runtime.read_tls_fallback", 0)
|
progedit_tlsfallback = ctxt.Lookup("runtime.read_tls_fallback", 0)
|
||||||
|
|
@ -205,7 +206,7 @@ func (c *ctxt5) rewriteToUseGot(p *obj.Prog) {
|
||||||
if p.As == obj.ATEXT || p.As == obj.AFUNCDATA || p.As == obj.ACALL || p.As == obj.ARET || p.As == obj.AJMP {
|
if p.As == obj.ATEXT || p.As == obj.AFUNCDATA || p.As == obj.ACALL || p.As == obj.ARET || p.As == obj.AJMP {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
if source.Sym.Type == obj.STLSBSS {
|
if source.Sym.Type == objabi.STLSBSS {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
if source.Type != obj.TYPE_MEM {
|
if source.Type != obj.TYPE_MEM {
|
||||||
|
|
@ -632,7 +633,7 @@ func isfloatreg(a *obj.Addr) bool {
|
||||||
}
|
}
|
||||||
|
|
||||||
func (c *ctxt5) softfloat() {
|
func (c *ctxt5) softfloat() {
|
||||||
if obj.GOARM > 5 {
|
if objabi.GOARM > 5 {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -722,7 +723,7 @@ func (c *ctxt5) stacksplit(p *obj.Prog, framesize int32) *obj.Prog {
|
||||||
p.To.Type = obj.TYPE_REG
|
p.To.Type = obj.TYPE_REG
|
||||||
p.To.Reg = REG_R1
|
p.To.Reg = REG_R1
|
||||||
|
|
||||||
if framesize <= obj.StackSmall {
|
if framesize <= objabi.StackSmall {
|
||||||
// small stack: SP < stackguard
|
// small stack: SP < stackguard
|
||||||
// CMP stackguard, SP
|
// CMP stackguard, SP
|
||||||
p = obj.Appendp(p, c.newprog)
|
p = obj.Appendp(p, c.newprog)
|
||||||
|
|
@ -731,7 +732,7 @@ func (c *ctxt5) stacksplit(p *obj.Prog, framesize int32) *obj.Prog {
|
||||||
p.From.Type = obj.TYPE_REG
|
p.From.Type = obj.TYPE_REG
|
||||||
p.From.Reg = REG_R1
|
p.From.Reg = REG_R1
|
||||||
p.Reg = REGSP
|
p.Reg = REGSP
|
||||||
} else if framesize <= obj.StackBig {
|
} else if framesize <= objabi.StackBig {
|
||||||
// large stack: SP-framesize < stackguard-StackSmall
|
// large stack: SP-framesize < stackguard-StackSmall
|
||||||
// MOVW $-(framesize-StackSmall)(SP), R2
|
// MOVW $-(framesize-StackSmall)(SP), R2
|
||||||
// CMP stackguard, R2
|
// CMP stackguard, R2
|
||||||
|
|
@ -740,7 +741,7 @@ func (c *ctxt5) stacksplit(p *obj.Prog, framesize int32) *obj.Prog {
|
||||||
p.As = AMOVW
|
p.As = AMOVW
|
||||||
p.From.Type = obj.TYPE_ADDR
|
p.From.Type = obj.TYPE_ADDR
|
||||||
p.From.Reg = REGSP
|
p.From.Reg = REGSP
|
||||||
p.From.Offset = -(int64(framesize) - obj.StackSmall)
|
p.From.Offset = -(int64(framesize) - objabi.StackSmall)
|
||||||
p.To.Type = obj.TYPE_REG
|
p.To.Type = obj.TYPE_REG
|
||||||
p.To.Reg = REG_R2
|
p.To.Reg = REG_R2
|
||||||
|
|
||||||
|
|
@ -764,14 +765,14 @@ func (c *ctxt5) stacksplit(p *obj.Prog, framesize int32) *obj.Prog {
|
||||||
|
|
||||||
p.As = ACMP
|
p.As = ACMP
|
||||||
p.From.Type = obj.TYPE_CONST
|
p.From.Type = obj.TYPE_CONST
|
||||||
p.From.Offset = int64(uint32(obj.StackPreempt & (1<<32 - 1)))
|
p.From.Offset = int64(uint32(objabi.StackPreempt & (1<<32 - 1)))
|
||||||
p.Reg = REG_R1
|
p.Reg = REG_R1
|
||||||
|
|
||||||
p = obj.Appendp(p, c.newprog)
|
p = obj.Appendp(p, c.newprog)
|
||||||
p.As = AMOVW
|
p.As = AMOVW
|
||||||
p.From.Type = obj.TYPE_ADDR
|
p.From.Type = obj.TYPE_ADDR
|
||||||
p.From.Reg = REGSP
|
p.From.Reg = REGSP
|
||||||
p.From.Offset = obj.StackGuard
|
p.From.Offset = objabi.StackGuard
|
||||||
p.To.Type = obj.TYPE_REG
|
p.To.Type = obj.TYPE_REG
|
||||||
p.To.Reg = REG_R2
|
p.To.Reg = REG_R2
|
||||||
p.Scond = C_SCOND_NE
|
p.Scond = C_SCOND_NE
|
||||||
|
|
@ -787,7 +788,7 @@ func (c *ctxt5) stacksplit(p *obj.Prog, framesize int32) *obj.Prog {
|
||||||
p = obj.Appendp(p, c.newprog)
|
p = obj.Appendp(p, c.newprog)
|
||||||
p.As = AMOVW
|
p.As = AMOVW
|
||||||
p.From.Type = obj.TYPE_ADDR
|
p.From.Type = obj.TYPE_ADDR
|
||||||
p.From.Offset = int64(framesize) + (obj.StackGuard - obj.StackSmall)
|
p.From.Offset = int64(framesize) + (objabi.StackGuard - objabi.StackSmall)
|
||||||
p.To.Type = obj.TYPE_REG
|
p.To.Type = obj.TYPE_REG
|
||||||
p.To.Reg = REG_R3
|
p.To.Reg = REG_R3
|
||||||
p.Scond = C_SCOND_NE
|
p.Scond = C_SCOND_NE
|
||||||
|
|
@ -820,7 +821,7 @@ func (c *ctxt5) stacksplit(p *obj.Prog, framesize int32) *obj.Prog {
|
||||||
pcdata.Pos = c.cursym.Func.Text.Pos
|
pcdata.Pos = c.cursym.Func.Text.Pos
|
||||||
pcdata.As = obj.APCDATA
|
pcdata.As = obj.APCDATA
|
||||||
pcdata.From.Type = obj.TYPE_CONST
|
pcdata.From.Type = obj.TYPE_CONST
|
||||||
pcdata.From.Offset = obj.PCDATA_StackMapIndex
|
pcdata.From.Offset = objabi.PCDATA_StackMapIndex
|
||||||
pcdata.To.Type = obj.TYPE_CONST
|
pcdata.To.Type = obj.TYPE_CONST
|
||||||
pcdata.To.Offset = -1 // pcdata starts at -1 at function entry
|
pcdata.To.Offset = -1 // pcdata starts at -1 at function entry
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -32,6 +32,7 @@ package arm64
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"cmd/internal/obj"
|
"cmd/internal/obj"
|
||||||
|
"cmd/internal/objabi"
|
||||||
"fmt"
|
"fmt"
|
||||||
"log"
|
"log"
|
||||||
"math"
|
"math"
|
||||||
|
|
@ -1100,7 +1101,7 @@ func (c *ctxt7) aclass(a *obj.Addr) int {
|
||||||
}
|
}
|
||||||
c.instoffset = a.Offset
|
c.instoffset = a.Offset
|
||||||
if a.Sym != nil { // use relocation
|
if a.Sym != nil { // use relocation
|
||||||
if a.Sym.Type == obj.STLSBSS {
|
if a.Sym.Type == objabi.STLSBSS {
|
||||||
if c.ctxt.Flag_shared {
|
if c.ctxt.Flag_shared {
|
||||||
return C_TLS_IE
|
return C_TLS_IE
|
||||||
} else {
|
} else {
|
||||||
|
|
@ -1187,7 +1188,7 @@ func (c *ctxt7) aclass(a *obj.Addr) int {
|
||||||
if a.Sym == nil {
|
if a.Sym == nil {
|
||||||
break
|
break
|
||||||
}
|
}
|
||||||
if a.Sym.Type == obj.STLSBSS {
|
if a.Sym.Type == objabi.STLSBSS {
|
||||||
c.ctxt.Diag("taking address of TLS variable is not supported")
|
c.ctxt.Diag("taking address of TLS variable is not supported")
|
||||||
}
|
}
|
||||||
c.instoffset = a.Offset
|
c.instoffset = a.Offset
|
||||||
|
|
@ -2035,7 +2036,7 @@ func (c *ctxt7) asmout(p *obj.Prog, o *Optab, out []uint32) {
|
||||||
rel.Siz = 4
|
rel.Siz = 4
|
||||||
rel.Sym = p.To.Sym
|
rel.Sym = p.To.Sym
|
||||||
rel.Add = p.To.Offset
|
rel.Add = p.To.Offset
|
||||||
rel.Type = obj.R_CALLARM64
|
rel.Type = objabi.R_CALLARM64
|
||||||
|
|
||||||
case 6: /* b ,O(R); bl ,O(R) */
|
case 6: /* b ,O(R); bl ,O(R) */
|
||||||
o1 = c.opbrr(p, p.As)
|
o1 = c.opbrr(p, p.As)
|
||||||
|
|
@ -2044,7 +2045,7 @@ func (c *ctxt7) asmout(p *obj.Prog, o *Optab, out []uint32) {
|
||||||
rel := obj.Addrel(c.cursym)
|
rel := obj.Addrel(c.cursym)
|
||||||
rel.Off = int32(c.pc)
|
rel.Off = int32(c.pc)
|
||||||
rel.Siz = 0
|
rel.Siz = 0
|
||||||
rel.Type = obj.R_CALLIND
|
rel.Type = objabi.R_CALLIND
|
||||||
|
|
||||||
case 7: /* beq s */
|
case 7: /* beq s */
|
||||||
o1 = c.opbra(p, p.As)
|
o1 = c.opbra(p, p.As)
|
||||||
|
|
@ -2116,7 +2117,7 @@ func (c *ctxt7) asmout(p *obj.Prog, o *Optab, out []uint32) {
|
||||||
rel.Siz = 8
|
rel.Siz = 8
|
||||||
rel.Sym = p.To.Sym
|
rel.Sym = p.To.Sym
|
||||||
rel.Add = p.To.Offset
|
rel.Add = p.To.Offset
|
||||||
rel.Type = obj.R_ADDR
|
rel.Type = objabi.R_ADDR
|
||||||
o2 = 0
|
o2 = 0
|
||||||
o1 = o2
|
o1 = o2
|
||||||
}
|
}
|
||||||
|
|
@ -2164,7 +2165,7 @@ func (c *ctxt7) asmout(p *obj.Prog, o *Optab, out []uint32) {
|
||||||
rel.Siz = 4
|
rel.Siz = 4
|
||||||
rel.Sym = p.To.Sym
|
rel.Sym = p.To.Sym
|
||||||
rel.Add = p.To.Offset
|
rel.Add = p.To.Offset
|
||||||
rel.Type = obj.R_ADDR
|
rel.Type = objabi.R_ADDR
|
||||||
o1 = 0
|
o1 = 0
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -2875,7 +2876,7 @@ func (c *ctxt7) asmout(p *obj.Prog, o *Optab, out []uint32) {
|
||||||
rel.Siz = 8
|
rel.Siz = 8
|
||||||
rel.Sym = p.To.Sym
|
rel.Sym = p.To.Sym
|
||||||
rel.Add = p.To.Offset
|
rel.Add = p.To.Offset
|
||||||
rel.Type = obj.R_ADDRARM64
|
rel.Type = objabi.R_ADDRARM64
|
||||||
o3 = c.olsr12u(p, int32(c.opstr12(p, p.As)), 0, REGTMP, int(p.From.Reg))
|
o3 = c.olsr12u(p, int32(c.opstr12(p, p.As)), 0, REGTMP, int(p.From.Reg))
|
||||||
|
|
||||||
case 65: /* movT addr,R -> adrp + add + movT (REGTMP), R */
|
case 65: /* movT addr,R -> adrp + add + movT (REGTMP), R */
|
||||||
|
|
@ -2886,7 +2887,7 @@ func (c *ctxt7) asmout(p *obj.Prog, o *Optab, out []uint32) {
|
||||||
rel.Siz = 8
|
rel.Siz = 8
|
||||||
rel.Sym = p.From.Sym
|
rel.Sym = p.From.Sym
|
||||||
rel.Add = p.From.Offset
|
rel.Add = p.From.Offset
|
||||||
rel.Type = obj.R_ADDRARM64
|
rel.Type = objabi.R_ADDRARM64
|
||||||
o3 = c.olsr12u(p, int32(c.opldr12(p, p.As)), 0, REGTMP, int(p.To.Reg))
|
o3 = c.olsr12u(p, int32(c.opldr12(p, p.As)), 0, REGTMP, int(p.To.Reg))
|
||||||
|
|
||||||
case 66: /* ldp O(R)!, (r1, r2); ldp (R)O!, (r1, r2) */
|
case 66: /* ldp O(R)!, (r1, r2); ldp (R)O!, (r1, r2) */
|
||||||
|
|
@ -2927,7 +2928,7 @@ func (c *ctxt7) asmout(p *obj.Prog, o *Optab, out []uint32) {
|
||||||
rel.Siz = 8
|
rel.Siz = 8
|
||||||
rel.Sym = p.From.Sym
|
rel.Sym = p.From.Sym
|
||||||
rel.Add = p.From.Offset
|
rel.Add = p.From.Offset
|
||||||
rel.Type = obj.R_ADDRARM64
|
rel.Type = objabi.R_ADDRARM64
|
||||||
|
|
||||||
case 69: /* LE model movd $tlsvar, reg -> movz reg, 0 + reloc */
|
case 69: /* LE model movd $tlsvar, reg -> movz reg, 0 + reloc */
|
||||||
o1 = c.opirr(p, AMOVZ)
|
o1 = c.opirr(p, AMOVZ)
|
||||||
|
|
@ -2936,7 +2937,7 @@ func (c *ctxt7) asmout(p *obj.Prog, o *Optab, out []uint32) {
|
||||||
rel.Off = int32(c.pc)
|
rel.Off = int32(c.pc)
|
||||||
rel.Siz = 4
|
rel.Siz = 4
|
||||||
rel.Sym = p.From.Sym
|
rel.Sym = p.From.Sym
|
||||||
rel.Type = obj.R_ARM64_TLS_LE
|
rel.Type = objabi.R_ARM64_TLS_LE
|
||||||
if p.From.Offset != 0 {
|
if p.From.Offset != 0 {
|
||||||
c.ctxt.Diag("invalid offset on MOVW $tlsvar")
|
c.ctxt.Diag("invalid offset on MOVW $tlsvar")
|
||||||
}
|
}
|
||||||
|
|
@ -2949,7 +2950,7 @@ func (c *ctxt7) asmout(p *obj.Prog, o *Optab, out []uint32) {
|
||||||
rel.Siz = 8
|
rel.Siz = 8
|
||||||
rel.Sym = p.From.Sym
|
rel.Sym = p.From.Sym
|
||||||
rel.Add = 0
|
rel.Add = 0
|
||||||
rel.Type = obj.R_ARM64_TLS_IE
|
rel.Type = objabi.R_ARM64_TLS_IE
|
||||||
if p.From.Offset != 0 {
|
if p.From.Offset != 0 {
|
||||||
c.ctxt.Diag("invalid offset on MOVW $tlsvar")
|
c.ctxt.Diag("invalid offset on MOVW $tlsvar")
|
||||||
}
|
}
|
||||||
|
|
@ -2962,7 +2963,7 @@ func (c *ctxt7) asmout(p *obj.Prog, o *Optab, out []uint32) {
|
||||||
rel.Siz = 8
|
rel.Siz = 8
|
||||||
rel.Sym = p.From.Sym
|
rel.Sym = p.From.Sym
|
||||||
rel.Add = 0
|
rel.Add = 0
|
||||||
rel.Type = obj.R_ARM64_GOTPCREL
|
rel.Type = objabi.R_ARM64_GOTPCREL
|
||||||
|
|
||||||
// This is supposed to be something that stops execution.
|
// This is supposed to be something that stops execution.
|
||||||
// It's not supposed to be reached, ever, but if it is, we'd
|
// It's not supposed to be reached, ever, but if it is, we'd
|
||||||
|
|
|
||||||
|
|
@ -32,6 +32,7 @@ package arm64
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"cmd/internal/obj"
|
"cmd/internal/obj"
|
||||||
|
"cmd/internal/objabi"
|
||||||
"cmd/internal/sys"
|
"cmd/internal/sys"
|
||||||
"math"
|
"math"
|
||||||
)
|
)
|
||||||
|
|
@ -62,7 +63,7 @@ func (c *ctxt7) stacksplit(p *obj.Prog, framesize int32) *obj.Prog {
|
||||||
p.To.Reg = REG_R1
|
p.To.Reg = REG_R1
|
||||||
|
|
||||||
q := (*obj.Prog)(nil)
|
q := (*obj.Prog)(nil)
|
||||||
if framesize <= obj.StackSmall {
|
if framesize <= objabi.StackSmall {
|
||||||
// small stack: SP < stackguard
|
// small stack: SP < stackguard
|
||||||
// MOV SP, R2
|
// MOV SP, R2
|
||||||
// CMP stackguard, R2
|
// CMP stackguard, R2
|
||||||
|
|
@ -79,7 +80,7 @@ func (c *ctxt7) stacksplit(p *obj.Prog, framesize int32) *obj.Prog {
|
||||||
p.From.Type = obj.TYPE_REG
|
p.From.Type = obj.TYPE_REG
|
||||||
p.From.Reg = REG_R1
|
p.From.Reg = REG_R1
|
||||||
p.Reg = REG_R2
|
p.Reg = REG_R2
|
||||||
} else if framesize <= obj.StackBig {
|
} else if framesize <= objabi.StackBig {
|
||||||
// large stack: SP-framesize < stackguard-StackSmall
|
// large stack: SP-framesize < stackguard-StackSmall
|
||||||
// SUB $(framesize-StackSmall), SP, R2
|
// SUB $(framesize-StackSmall), SP, R2
|
||||||
// CMP stackguard, R2
|
// CMP stackguard, R2
|
||||||
|
|
@ -87,7 +88,7 @@ func (c *ctxt7) stacksplit(p *obj.Prog, framesize int32) *obj.Prog {
|
||||||
|
|
||||||
p.As = ASUB
|
p.As = ASUB
|
||||||
p.From.Type = obj.TYPE_CONST
|
p.From.Type = obj.TYPE_CONST
|
||||||
p.From.Offset = int64(framesize) - obj.StackSmall
|
p.From.Offset = int64(framesize) - objabi.StackSmall
|
||||||
p.Reg = REGSP
|
p.Reg = REGSP
|
||||||
p.To.Type = obj.TYPE_REG
|
p.To.Type = obj.TYPE_REG
|
||||||
p.To.Reg = REG_R2
|
p.To.Reg = REG_R2
|
||||||
|
|
@ -113,7 +114,7 @@ func (c *ctxt7) stacksplit(p *obj.Prog, framesize int32) *obj.Prog {
|
||||||
|
|
||||||
p.As = ACMP
|
p.As = ACMP
|
||||||
p.From.Type = obj.TYPE_CONST
|
p.From.Type = obj.TYPE_CONST
|
||||||
p.From.Offset = obj.StackPreempt
|
p.From.Offset = objabi.StackPreempt
|
||||||
p.Reg = REG_R1
|
p.Reg = REG_R1
|
||||||
|
|
||||||
p = obj.Appendp(p, c.newprog)
|
p = obj.Appendp(p, c.newprog)
|
||||||
|
|
@ -124,7 +125,7 @@ func (c *ctxt7) stacksplit(p *obj.Prog, framesize int32) *obj.Prog {
|
||||||
p = obj.Appendp(p, c.newprog)
|
p = obj.Appendp(p, c.newprog)
|
||||||
p.As = AADD
|
p.As = AADD
|
||||||
p.From.Type = obj.TYPE_CONST
|
p.From.Type = obj.TYPE_CONST
|
||||||
p.From.Offset = obj.StackGuard
|
p.From.Offset = objabi.StackGuard
|
||||||
p.Reg = REGSP
|
p.Reg = REGSP
|
||||||
p.To.Type = obj.TYPE_REG
|
p.To.Type = obj.TYPE_REG
|
||||||
p.To.Reg = REG_R2
|
p.To.Reg = REG_R2
|
||||||
|
|
@ -139,7 +140,7 @@ func (c *ctxt7) stacksplit(p *obj.Prog, framesize int32) *obj.Prog {
|
||||||
p = obj.Appendp(p, c.newprog)
|
p = obj.Appendp(p, c.newprog)
|
||||||
p.As = AMOVD
|
p.As = AMOVD
|
||||||
p.From.Type = obj.TYPE_CONST
|
p.From.Type = obj.TYPE_CONST
|
||||||
p.From.Offset = int64(framesize) + (obj.StackGuard - obj.StackSmall)
|
p.From.Offset = int64(framesize) + (objabi.StackGuard - objabi.StackSmall)
|
||||||
p.To.Type = obj.TYPE_REG
|
p.To.Type = obj.TYPE_REG
|
||||||
p.To.Reg = REG_R3
|
p.To.Reg = REG_R3
|
||||||
|
|
||||||
|
|
@ -170,7 +171,7 @@ func (c *ctxt7) stacksplit(p *obj.Prog, framesize int32) *obj.Prog {
|
||||||
pcdata.Pos = c.cursym.Func.Text.Pos
|
pcdata.Pos = c.cursym.Func.Text.Pos
|
||||||
pcdata.As = obj.APCDATA
|
pcdata.As = obj.APCDATA
|
||||||
pcdata.From.Type = obj.TYPE_CONST
|
pcdata.From.Type = obj.TYPE_CONST
|
||||||
pcdata.From.Offset = obj.PCDATA_StackMapIndex
|
pcdata.From.Offset = objabi.PCDATA_StackMapIndex
|
||||||
pcdata.To.Type = obj.TYPE_CONST
|
pcdata.To.Type = obj.TYPE_CONST
|
||||||
pcdata.To.Offset = -1 // pcdata starts at -1 at function entry
|
pcdata.To.Offset = -1 // pcdata starts at -1 at function entry
|
||||||
|
|
||||||
|
|
@ -401,7 +402,7 @@ func (c *ctxt7) rewriteToUseGot(p *obj.Prog) {
|
||||||
if p.As == obj.ATEXT || p.As == obj.AFUNCDATA || p.As == obj.ACALL || p.As == obj.ARET || p.As == obj.AJMP {
|
if p.As == obj.ATEXT || p.As == obj.AFUNCDATA || p.As == obj.ACALL || p.As == obj.ARET || p.As == obj.AJMP {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
if source.Sym.Type == obj.STLSBSS {
|
if source.Sym.Type == objabi.STLSBSS {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
if source.Type != obj.TYPE_MEM {
|
if source.Type != obj.TYPE_MEM {
|
||||||
|
|
|
||||||
|
|
@ -32,6 +32,7 @@
|
||||||
package obj
|
package obj
|
||||||
|
|
||||||
import (
|
import (
|
||||||
|
"cmd/internal/objabi"
|
||||||
"log"
|
"log"
|
||||||
"math"
|
"math"
|
||||||
)
|
)
|
||||||
|
|
@ -72,7 +73,7 @@ func (s *LSym) prepwrite(ctxt *Link, off int64, siz int) {
|
||||||
if off < 0 || siz < 0 || off >= 1<<30 {
|
if off < 0 || siz < 0 || off >= 1<<30 {
|
||||||
ctxt.Diag("prepwrite: bad off=%d siz=%d s=%v", off, siz, s)
|
ctxt.Diag("prepwrite: bad off=%d siz=%d s=%v", off, siz, s)
|
||||||
}
|
}
|
||||||
if s.Type == SBSS || s.Type == STLSBSS {
|
if s.Type == objabi.SBSS || s.Type == objabi.STLSBSS {
|
||||||
ctxt.Diag("cannot supply data for BSS var")
|
ctxt.Diag("cannot supply data for BSS var")
|
||||||
}
|
}
|
||||||
l := off + int64(siz)
|
l := off + int64(siz)
|
||||||
|
|
@ -125,7 +126,7 @@ func (s *LSym) WriteAddr(ctxt *Link, off int64, siz int, rsym *LSym, roff int64)
|
||||||
}
|
}
|
||||||
r.Siz = uint8(siz)
|
r.Siz = uint8(siz)
|
||||||
r.Sym = rsym
|
r.Sym = rsym
|
||||||
r.Type = R_ADDR
|
r.Type = objabi.R_ADDR
|
||||||
r.Add = roff
|
r.Add = roff
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -141,7 +142,7 @@ func (s *LSym) WriteOff(ctxt *Link, off int64, rsym *LSym, roff int64) {
|
||||||
}
|
}
|
||||||
r.Siz = 4
|
r.Siz = 4
|
||||||
r.Sym = rsym
|
r.Sym = rsym
|
||||||
r.Type = R_ADDROFF
|
r.Type = objabi.R_ADDROFF
|
||||||
r.Add = roff
|
r.Add = roff
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -157,7 +158,7 @@ func (s *LSym) WriteWeakOff(ctxt *Link, off int64, rsym *LSym, roff int64) {
|
||||||
}
|
}
|
||||||
r.Siz = 4
|
r.Siz = 4
|
||||||
r.Sym = rsym
|
r.Sym = rsym
|
||||||
r.Type = R_WEAKADDROFF
|
r.Type = objabi.R_WEAKADDROFF
|
||||||
r.Add = roff
|
r.Add = roff
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -4,67 +4,8 @@
|
||||||
|
|
||||||
package obj
|
package obj
|
||||||
|
|
||||||
import (
|
|
||||||
"fmt"
|
|
||||||
"os"
|
|
||||||
"strings"
|
|
||||||
)
|
|
||||||
|
|
||||||
// go-specific code shared across loaders (5l, 6l, 8l).
|
// go-specific code shared across loaders (5l, 6l, 8l).
|
||||||
|
|
||||||
var (
|
|
||||||
framepointer_enabled int
|
|
||||||
Fieldtrack_enabled int
|
|
||||||
Preemptibleloops_enabled int
|
|
||||||
)
|
|
||||||
|
|
||||||
// Toolchain experiments.
|
|
||||||
// These are controlled by the GOEXPERIMENT environment
|
|
||||||
// variable recorded when the toolchain is built.
|
|
||||||
// This list is also known to cmd/gc.
|
|
||||||
var exper = []struct {
|
|
||||||
name string
|
|
||||||
val *int
|
|
||||||
}{
|
|
||||||
{"fieldtrack", &Fieldtrack_enabled},
|
|
||||||
{"framepointer", &framepointer_enabled},
|
|
||||||
{"preemptibleloops", &Preemptibleloops_enabled},
|
|
||||||
}
|
|
||||||
|
|
||||||
func addexp(s string) {
|
|
||||||
// Could do general integer parsing here, but the runtime copy doesn't yet.
|
|
||||||
v := 1
|
|
||||||
name := s
|
|
||||||
if len(name) > 2 && name[:2] == "no" {
|
|
||||||
v = 0
|
|
||||||
name = name[2:]
|
|
||||||
}
|
|
||||||
for i := 0; i < len(exper); i++ {
|
|
||||||
if exper[i].name == name {
|
|
||||||
if exper[i].val != nil {
|
|
||||||
*exper[i].val = v
|
|
||||||
}
|
|
||||||
return
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
fmt.Printf("unknown experiment %s\n", s)
|
|
||||||
os.Exit(2)
|
|
||||||
}
|
|
||||||
|
|
||||||
func init() {
|
|
||||||
framepointer_enabled = 1 // default
|
|
||||||
for _, f := range strings.Split(goexperiment, ",") {
|
|
||||||
if f != "" {
|
|
||||||
addexp(f)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
func Framepointer_enabled(goos, goarch string) bool {
|
|
||||||
return framepointer_enabled != 0 && goarch == "amd64" && goos != "nacl"
|
|
||||||
}
|
|
||||||
|
|
||||||
func Nopout(p *Prog) {
|
func Nopout(p *Prog) {
|
||||||
p.As = ANOP
|
p.As = ANOP
|
||||||
p.Scond = 0
|
p.Scond = 0
|
||||||
|
|
@ -73,16 +14,3 @@ func Nopout(p *Prog) {
|
||||||
p.Reg = 0
|
p.Reg = 0
|
||||||
p.To = Addr{}
|
p.To = Addr{}
|
||||||
}
|
}
|
||||||
|
|
||||||
func Expstring() string {
|
|
||||||
buf := "X"
|
|
||||||
for i := range exper {
|
|
||||||
if *exper[i].val != 0 {
|
|
||||||
buf += "," + exper[i].name
|
|
||||||
}
|
|
||||||
}
|
|
||||||
if buf == "X" {
|
|
||||||
buf += ",none"
|
|
||||||
}
|
|
||||||
return "X:" + buf[2:]
|
|
||||||
}
|
|
||||||
|
|
|
||||||
|
|
@ -6,69 +6,8 @@ package obj
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"cmd/internal/src"
|
"cmd/internal/src"
|
||||||
"path/filepath"
|
|
||||||
)
|
)
|
||||||
|
|
||||||
// AbsFile returns the absolute filename for file in the given directory.
|
|
||||||
// It also removes a leading pathPrefix, or else rewrites a leading $GOROOT
|
|
||||||
// prefix to the literal "$GOROOT".
|
|
||||||
// If the resulting path is the empty string, the result is "??".
|
|
||||||
func AbsFile(dir, file, pathPrefix string) string {
|
|
||||||
abs := file
|
|
||||||
if dir != "" && !filepath.IsAbs(file) {
|
|
||||||
abs = filepath.Join(dir, file)
|
|
||||||
}
|
|
||||||
|
|
||||||
if pathPrefix != "" && hasPathPrefix(abs, pathPrefix) {
|
|
||||||
if abs == pathPrefix {
|
|
||||||
abs = ""
|
|
||||||
} else {
|
|
||||||
abs = abs[len(pathPrefix)+1:]
|
|
||||||
}
|
|
||||||
} else if hasPathPrefix(abs, GOROOT) {
|
|
||||||
abs = "$GOROOT" + abs[len(GOROOT):]
|
|
||||||
}
|
|
||||||
if abs == "" {
|
|
||||||
abs = "??"
|
|
||||||
}
|
|
||||||
|
|
||||||
return filepath.Clean(abs)
|
|
||||||
}
|
|
||||||
|
|
||||||
// Does s have t as a path prefix?
|
|
||||||
// That is, does s == t or does s begin with t followed by a slash?
|
|
||||||
// For portability, we allow ASCII case folding, so that hasPathPrefix("a/b/c", "A/B") is true.
|
|
||||||
// Similarly, we allow slash folding, so that hasPathPrefix("a/b/c", "a\\b") is true.
|
|
||||||
// We do not allow full Unicode case folding, for fear of causing more confusion
|
|
||||||
// or harm than good. (For an example of the kinds of things that can go wrong,
|
|
||||||
// see http://article.gmane.org/gmane.linux.kernel/1853266.)
|
|
||||||
func hasPathPrefix(s string, t string) bool {
|
|
||||||
if len(t) > len(s) {
|
|
||||||
return false
|
|
||||||
}
|
|
||||||
var i int
|
|
||||||
for i = 0; i < len(t); i++ {
|
|
||||||
cs := int(s[i])
|
|
||||||
ct := int(t[i])
|
|
||||||
if 'A' <= cs && cs <= 'Z' {
|
|
||||||
cs += 'a' - 'A'
|
|
||||||
}
|
|
||||||
if 'A' <= ct && ct <= 'Z' {
|
|
||||||
ct += 'a' - 'A'
|
|
||||||
}
|
|
||||||
if cs == '\\' {
|
|
||||||
cs = '/'
|
|
||||||
}
|
|
||||||
if ct == '\\' {
|
|
||||||
ct = '/'
|
|
||||||
}
|
|
||||||
if cs != ct {
|
|
||||||
return false
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return i >= len(s) || s[i] == '/' || s[i] == '\\'
|
|
||||||
}
|
|
||||||
|
|
||||||
// AddImport adds a package to the list of imported packages.
|
// AddImport adds a package to the list of imported packages.
|
||||||
func (ctxt *Link) AddImport(pkg string) {
|
func (ctxt *Link) AddImport(pkg string) {
|
||||||
ctxt.Imports = append(ctxt.Imports, pkg)
|
ctxt.Imports = append(ctxt.Imports, pkg)
|
||||||
|
|
|
||||||
|
|
@ -33,6 +33,7 @@ package obj
|
||||||
import (
|
import (
|
||||||
"bufio"
|
"bufio"
|
||||||
"cmd/internal/dwarf"
|
"cmd/internal/dwarf"
|
||||||
|
"cmd/internal/objabi"
|
||||||
"cmd/internal/src"
|
"cmd/internal/src"
|
||||||
"cmd/internal/sys"
|
"cmd/internal/sys"
|
||||||
"fmt"
|
"fmt"
|
||||||
|
|
@ -308,7 +309,7 @@ const (
|
||||||
// An LSym is the sort of symbol that is written to an object file.
|
// An LSym is the sort of symbol that is written to an object file.
|
||||||
type LSym struct {
|
type LSym struct {
|
||||||
Name string
|
Name string
|
||||||
Type SymKind
|
Type objabi.SymKind
|
||||||
Version int16
|
Version int16
|
||||||
Attribute
|
Attribute
|
||||||
|
|
||||||
|
|
@ -447,289 +448,14 @@ type Pcln struct {
|
||||||
InlTree InlTree // per-function inlining tree extracted from the global tree
|
InlTree InlTree // per-function inlining tree extracted from the global tree
|
||||||
}
|
}
|
||||||
|
|
||||||
// A SymKind describes the kind of memory represented by a symbol.
|
|
||||||
type SymKind int16
|
|
||||||
|
|
||||||
// Defined SymKind values.
|
|
||||||
//
|
|
||||||
// TODO(rsc): Give idiomatic Go names.
|
|
||||||
// TODO(rsc): Reduce the number of symbol types in the object files.
|
|
||||||
//go:generate stringer -type=SymKind
|
|
||||||
const (
|
|
||||||
Sxxx SymKind = iota
|
|
||||||
STEXT
|
|
||||||
SELFRXSECT
|
|
||||||
|
|
||||||
// Read-only sections.
|
|
||||||
STYPE
|
|
||||||
SSTRING
|
|
||||||
SGOSTRING
|
|
||||||
SGOFUNC
|
|
||||||
SGCBITS
|
|
||||||
SRODATA
|
|
||||||
SFUNCTAB
|
|
||||||
|
|
||||||
SELFROSECT
|
|
||||||
SMACHOPLT
|
|
||||||
|
|
||||||
// Read-only sections with relocations.
|
|
||||||
//
|
|
||||||
// Types STYPE-SFUNCTAB above are written to the .rodata section by default.
|
|
||||||
// When linking a shared object, some conceptually "read only" types need to
|
|
||||||
// be written to by relocations and putting them in a section called
|
|
||||||
// ".rodata" interacts poorly with the system linkers. The GNU linkers
|
|
||||||
// support this situation by arranging for sections of the name
|
|
||||||
// ".data.rel.ro.XXX" to be mprotected read only by the dynamic linker after
|
|
||||||
// relocations have applied, so when the Go linker is creating a shared
|
|
||||||
// object it checks all objects of the above types and bumps any object that
|
|
||||||
// has a relocation to it to the corresponding type below, which are then
|
|
||||||
// written to sections with appropriate magic names.
|
|
||||||
STYPERELRO
|
|
||||||
SSTRINGRELRO
|
|
||||||
SGOSTRINGRELRO
|
|
||||||
SGOFUNCRELRO
|
|
||||||
SGCBITSRELRO
|
|
||||||
SRODATARELRO
|
|
||||||
SFUNCTABRELRO
|
|
||||||
|
|
||||||
// Part of .data.rel.ro if it exists, otherwise part of .rodata.
|
|
||||||
STYPELINK
|
|
||||||
SITABLINK
|
|
||||||
SSYMTAB
|
|
||||||
SPCLNTAB
|
|
||||||
|
|
||||||
// Writable sections.
|
|
||||||
SELFSECT
|
|
||||||
SMACHO
|
|
||||||
SMACHOGOT
|
|
||||||
SWINDOWS
|
|
||||||
SELFGOT
|
|
||||||
SNOPTRDATA
|
|
||||||
SINITARR
|
|
||||||
SDATA
|
|
||||||
SBSS
|
|
||||||
SNOPTRBSS
|
|
||||||
STLSBSS
|
|
||||||
SXREF
|
|
||||||
SMACHOSYMSTR
|
|
||||||
SMACHOSYMTAB
|
|
||||||
SMACHOINDIRECTPLT
|
|
||||||
SMACHOINDIRECTGOT
|
|
||||||
SFILE
|
|
||||||
SFILEPATH
|
|
||||||
SCONST
|
|
||||||
SDYNIMPORT
|
|
||||||
SHOSTOBJ
|
|
||||||
SDWARFSECT
|
|
||||||
SDWARFINFO
|
|
||||||
SSUB = SymKind(1 << 8)
|
|
||||||
SMASK = SymKind(SSUB - 1)
|
|
||||||
SHIDDEN = SymKind(1 << 9)
|
|
||||||
SCONTAINER = SymKind(1 << 10) // has a sub-symbol
|
|
||||||
)
|
|
||||||
|
|
||||||
// ReadOnly are the symbol kinds that form read-only sections. In some
|
|
||||||
// cases, if they will require relocations, they are transformed into
|
|
||||||
// rel-ro sections using RelROMap.
|
|
||||||
var ReadOnly = []SymKind{
|
|
||||||
STYPE,
|
|
||||||
SSTRING,
|
|
||||||
SGOSTRING,
|
|
||||||
SGOFUNC,
|
|
||||||
SGCBITS,
|
|
||||||
SRODATA,
|
|
||||||
SFUNCTAB,
|
|
||||||
}
|
|
||||||
|
|
||||||
// RelROMap describes the transformation of read-only symbols to rel-ro
|
|
||||||
// symbols.
|
|
||||||
var RelROMap = map[SymKind]SymKind{
|
|
||||||
STYPE: STYPERELRO,
|
|
||||||
SSTRING: SSTRINGRELRO,
|
|
||||||
SGOSTRING: SGOSTRINGRELRO,
|
|
||||||
SGOFUNC: SGOFUNCRELRO,
|
|
||||||
SGCBITS: SGCBITSRELRO,
|
|
||||||
SRODATA: SRODATARELRO,
|
|
||||||
SFUNCTAB: SFUNCTABRELRO,
|
|
||||||
}
|
|
||||||
|
|
||||||
type Reloc struct {
|
type Reloc struct {
|
||||||
Off int32
|
Off int32
|
||||||
Siz uint8
|
Siz uint8
|
||||||
Type RelocType
|
Type objabi.RelocType
|
||||||
Add int64
|
Add int64
|
||||||
Sym *LSym
|
Sym *LSym
|
||||||
}
|
}
|
||||||
|
|
||||||
type RelocType int32
|
|
||||||
|
|
||||||
//go:generate stringer -type=RelocType
|
|
||||||
const (
|
|
||||||
R_ADDR RelocType = 1 + iota
|
|
||||||
// R_ADDRPOWER relocates a pair of "D-form" instructions (instructions with 16-bit
|
|
||||||
// immediates in the low half of the instruction word), usually addis followed by
|
|
||||||
// another add or a load, inserting the "high adjusted" 16 bits of the address of
|
|
||||||
// the referenced symbol into the immediate field of the first instruction and the
|
|
||||||
// low 16 bits into that of the second instruction.
|
|
||||||
R_ADDRPOWER
|
|
||||||
// R_ADDRARM64 relocates an adrp, add pair to compute the address of the
|
|
||||||
// referenced symbol.
|
|
||||||
R_ADDRARM64
|
|
||||||
// R_ADDRMIPS (only used on mips/mips64) resolves to the low 16 bits of an external
|
|
||||||
// address, by encoding it into the instruction.
|
|
||||||
R_ADDRMIPS
|
|
||||||
// R_ADDROFF resolves to a 32-bit offset from the beginning of the section
|
|
||||||
// holding the data being relocated to the referenced symbol.
|
|
||||||
R_ADDROFF
|
|
||||||
// R_WEAKADDROFF resolves just like R_ADDROFF but is a weak relocation.
|
|
||||||
// A weak relocation does not make the symbol it refers to reachable,
|
|
||||||
// and is only honored by the linker if the symbol is in some other way
|
|
||||||
// reachable.
|
|
||||||
R_WEAKADDROFF
|
|
||||||
R_SIZE
|
|
||||||
R_CALL
|
|
||||||
R_CALLARM
|
|
||||||
R_CALLARM64
|
|
||||||
R_CALLIND
|
|
||||||
R_CALLPOWER
|
|
||||||
// R_CALLMIPS (only used on mips64) resolves to non-PC-relative target address
|
|
||||||
// of a CALL (JAL) instruction, by encoding the address into the instruction.
|
|
||||||
R_CALLMIPS
|
|
||||||
R_CONST
|
|
||||||
R_PCREL
|
|
||||||
// R_TLS_LE, used on 386, amd64, and ARM, resolves to the offset of the
|
|
||||||
// thread-local symbol from the thread local base and is used to implement the
|
|
||||||
// "local exec" model for tls access (r.Sym is not set on intel platforms but is
|
|
||||||
// set to a TLS symbol -- runtime.tlsg -- in the linker when externally linking).
|
|
||||||
R_TLS_LE
|
|
||||||
// R_TLS_IE, used 386, amd64, and ARM resolves to the PC-relative offset to a GOT
|
|
||||||
// slot containing the offset from the thread-local symbol from the thread local
|
|
||||||
// base and is used to implemented the "initial exec" model for tls access (r.Sym
|
|
||||||
// is not set on intel platforms but is set to a TLS symbol -- runtime.tlsg -- in
|
|
||||||
// the linker when externally linking).
|
|
||||||
R_TLS_IE
|
|
||||||
R_GOTOFF
|
|
||||||
R_PLT0
|
|
||||||
R_PLT1
|
|
||||||
R_PLT2
|
|
||||||
R_USEFIELD
|
|
||||||
// R_USETYPE resolves to an *rtype, but no relocation is created. The
|
|
||||||
// linker uses this as a signal that the pointed-to type information
|
|
||||||
// should be linked into the final binary, even if there are no other
|
|
||||||
// direct references. (This is used for types reachable by reflection.)
|
|
||||||
R_USETYPE
|
|
||||||
// R_METHODOFF resolves to a 32-bit offset from the beginning of the section
|
|
||||||
// holding the data being relocated to the referenced symbol.
|
|
||||||
// It is a variant of R_ADDROFF used when linking from the uncommonType of a
|
|
||||||
// *rtype, and may be set to zero by the linker if it determines the method
|
|
||||||
// text is unreachable by the linked program.
|
|
||||||
R_METHODOFF
|
|
||||||
R_POWER_TOC
|
|
||||||
R_GOTPCREL
|
|
||||||
// R_JMPMIPS (only used on mips64) resolves to non-PC-relative target address
|
|
||||||
// of a JMP instruction, by encoding the address into the instruction.
|
|
||||||
// The stack nosplit check ignores this since it is not a function call.
|
|
||||||
R_JMPMIPS
|
|
||||||
// R_DWARFREF resolves to the offset of the symbol from its section.
|
|
||||||
R_DWARFREF
|
|
||||||
|
|
||||||
// Platform dependent relocations. Architectures with fixed width instructions
|
|
||||||
// have the inherent issue that a 32-bit (or 64-bit!) displacement cannot be
|
|
||||||
// stuffed into a 32-bit instruction, so an address needs to be spread across
|
|
||||||
// several instructions, and in turn this requires a sequence of relocations, each
|
|
||||||
// updating a part of an instruction. This leads to relocation codes that are
|
|
||||||
// inherently processor specific.
|
|
||||||
|
|
||||||
// Arm64.
|
|
||||||
|
|
||||||
// Set a MOV[NZ] immediate field to bits [15:0] of the offset from the thread
|
|
||||||
// local base to the thread local variable defined by the referenced (thread
|
|
||||||
// local) symbol. Error if the offset does not fit into 16 bits.
|
|
||||||
R_ARM64_TLS_LE
|
|
||||||
|
|
||||||
// Relocates an ADRP; LD64 instruction sequence to load the offset between
|
|
||||||
// the thread local base and the thread local variable defined by the
|
|
||||||
// referenced (thread local) symbol from the GOT.
|
|
||||||
R_ARM64_TLS_IE
|
|
||||||
|
|
||||||
// R_ARM64_GOTPCREL relocates an adrp, ld64 pair to compute the address of the GOT
|
|
||||||
// slot of the referenced symbol.
|
|
||||||
R_ARM64_GOTPCREL
|
|
||||||
|
|
||||||
// PPC64.
|
|
||||||
|
|
||||||
// R_POWER_TLS_LE is used to implement the "local exec" model for tls
|
|
||||||
// access. It resolves to the offset of the thread-local symbol from the
|
|
||||||
// thread pointer (R13) and inserts this value into the low 16 bits of an
|
|
||||||
// instruction word.
|
|
||||||
R_POWER_TLS_LE
|
|
||||||
|
|
||||||
// R_POWER_TLS_IE is used to implement the "initial exec" model for tls access. It
|
|
||||||
// relocates a D-form, DS-form instruction sequence like R_ADDRPOWER_DS. It
|
|
||||||
// inserts to the offset of GOT slot for the thread-local symbol from the TOC (the
|
|
||||||
// GOT slot is filled by the dynamic linker with the offset of the thread-local
|
|
||||||
// symbol from the thread pointer (R13)).
|
|
||||||
R_POWER_TLS_IE
|
|
||||||
|
|
||||||
// R_POWER_TLS marks an X-form instruction such as "MOVD 0(R13)(R31*1), g" as
|
|
||||||
// accessing a particular thread-local symbol. It does not affect code generation
|
|
||||||
// but is used by the system linker when relaxing "initial exec" model code to
|
|
||||||
// "local exec" model code.
|
|
||||||
R_POWER_TLS
|
|
||||||
|
|
||||||
// R_ADDRPOWER_DS is similar to R_ADDRPOWER above, but assumes the second
|
|
||||||
// instruction is a "DS-form" instruction, which has an immediate field occupying
|
|
||||||
// bits [15:2] of the instruction word. Bits [15:2] of the address of the
|
|
||||||
// relocated symbol are inserted into this field; it is an error if the last two
|
|
||||||
// bits of the address are not 0.
|
|
||||||
R_ADDRPOWER_DS
|
|
||||||
|
|
||||||
// R_ADDRPOWER_PCREL relocates a D-form, DS-form instruction sequence like
|
|
||||||
// R_ADDRPOWER_DS but inserts the offset of the GOT slot for the referenced symbol
|
|
||||||
// from the TOC rather than the symbol's address.
|
|
||||||
R_ADDRPOWER_GOT
|
|
||||||
|
|
||||||
// R_ADDRPOWER_PCREL relocates two D-form instructions like R_ADDRPOWER, but
|
|
||||||
// inserts the displacement from the place being relocated to the address of the
|
|
||||||
// the relocated symbol instead of just its address.
|
|
||||||
R_ADDRPOWER_PCREL
|
|
||||||
|
|
||||||
// R_ADDRPOWER_TOCREL relocates two D-form instructions like R_ADDRPOWER, but
|
|
||||||
// inserts the offset from the TOC to the address of the relocated symbol
|
|
||||||
// rather than the symbol's address.
|
|
||||||
R_ADDRPOWER_TOCREL
|
|
||||||
|
|
||||||
// R_ADDRPOWER_TOCREL relocates a D-form, DS-form instruction sequence like
|
|
||||||
// R_ADDRPOWER_DS but inserts the offset from the TOC to the address of the the
|
|
||||||
// relocated symbol rather than the symbol's address.
|
|
||||||
R_ADDRPOWER_TOCREL_DS
|
|
||||||
|
|
||||||
// R_PCRELDBL relocates s390x 2-byte aligned PC-relative addresses.
|
|
||||||
// TODO(mundaym): remove once variants can be serialized - see issue 14218.
|
|
||||||
R_PCRELDBL
|
|
||||||
|
|
||||||
// R_ADDRMIPSU (only used on mips/mips64) resolves to the sign-adjusted "upper" 16
|
|
||||||
// bits (bit 16-31) of an external address, by encoding it into the instruction.
|
|
||||||
R_ADDRMIPSU
|
|
||||||
// R_ADDRMIPSTLS (only used on mips64) resolves to the low 16 bits of a TLS
|
|
||||||
// address (offset from thread pointer), by encoding it into the instruction.
|
|
||||||
R_ADDRMIPSTLS
|
|
||||||
)
|
|
||||||
|
|
||||||
// IsDirectJump returns whether r is a relocation for a direct jump.
|
|
||||||
// A direct jump is a CALL or JMP instruction that takes the target address
|
|
||||||
// as immediate. The address is embedded into the instruction, possibly
|
|
||||||
// with limited width.
|
|
||||||
// An indirect jump is a CALL or JMP instruction that takes the target address
|
|
||||||
// in register or memory.
|
|
||||||
func (r RelocType) IsDirectJump() bool {
|
|
||||||
switch r {
|
|
||||||
case R_CALL, R_CALLARM, R_CALLARM64, R_CALLPOWER, R_CALLMIPS, R_JMPMIPS:
|
|
||||||
return true
|
|
||||||
}
|
|
||||||
return false
|
|
||||||
}
|
|
||||||
|
|
||||||
type Auto struct {
|
type Auto struct {
|
||||||
Asym *LSym
|
Asym *LSym
|
||||||
Aoffset int32
|
Aoffset int32
|
||||||
|
|
@ -737,12 +463,6 @@ type Auto struct {
|
||||||
Gotype *LSym
|
Gotype *LSym
|
||||||
}
|
}
|
||||||
|
|
||||||
// Auto.name
|
|
||||||
const (
|
|
||||||
A_AUTO = 1 + iota
|
|
||||||
A_PARAM
|
|
||||||
)
|
|
||||||
|
|
||||||
type Pcdata struct {
|
type Pcdata struct {
|
||||||
P []byte
|
P []byte
|
||||||
}
|
}
|
||||||
|
|
@ -750,7 +470,7 @@ type Pcdata struct {
|
||||||
// Link holds the context for writing object code from a compiler
|
// Link holds the context for writing object code from a compiler
|
||||||
// to be linker input or for reading that input into the linker.
|
// to be linker input or for reading that input into the linker.
|
||||||
type Link struct {
|
type Link struct {
|
||||||
Headtype HeadType
|
Headtype objabi.HeadType
|
||||||
Arch *LinkArch
|
Arch *LinkArch
|
||||||
Debugasm bool
|
Debugasm bool
|
||||||
Debugvlog bool
|
Debugvlog bool
|
||||||
|
|
@ -816,74 +536,3 @@ type LinkArch struct {
|
||||||
Progedit func(*Link, *Prog, ProgAlloc)
|
Progedit func(*Link, *Prog, ProgAlloc)
|
||||||
UnaryDst map[As]bool // Instruction takes one operand, a destination.
|
UnaryDst map[As]bool // Instruction takes one operand, a destination.
|
||||||
}
|
}
|
||||||
|
|
||||||
// HeadType is the executable header type.
|
|
||||||
type HeadType uint8
|
|
||||||
|
|
||||||
const (
|
|
||||||
Hunknown HeadType = iota
|
|
||||||
Hdarwin
|
|
||||||
Hdragonfly
|
|
||||||
Hfreebsd
|
|
||||||
Hlinux
|
|
||||||
Hnacl
|
|
||||||
Hnetbsd
|
|
||||||
Hopenbsd
|
|
||||||
Hplan9
|
|
||||||
Hsolaris
|
|
||||||
Hwindows
|
|
||||||
)
|
|
||||||
|
|
||||||
func (h *HeadType) Set(s string) error {
|
|
||||||
switch s {
|
|
||||||
case "darwin":
|
|
||||||
*h = Hdarwin
|
|
||||||
case "dragonfly":
|
|
||||||
*h = Hdragonfly
|
|
||||||
case "freebsd":
|
|
||||||
*h = Hfreebsd
|
|
||||||
case "linux", "android":
|
|
||||||
*h = Hlinux
|
|
||||||
case "nacl":
|
|
||||||
*h = Hnacl
|
|
||||||
case "netbsd":
|
|
||||||
*h = Hnetbsd
|
|
||||||
case "openbsd":
|
|
||||||
*h = Hopenbsd
|
|
||||||
case "plan9":
|
|
||||||
*h = Hplan9
|
|
||||||
case "solaris":
|
|
||||||
*h = Hsolaris
|
|
||||||
case "windows":
|
|
||||||
*h = Hwindows
|
|
||||||
default:
|
|
||||||
return fmt.Errorf("invalid headtype: %q", s)
|
|
||||||
}
|
|
||||||
return nil
|
|
||||||
}
|
|
||||||
|
|
||||||
func (h *HeadType) String() string {
|
|
||||||
switch *h {
|
|
||||||
case Hdarwin:
|
|
||||||
return "darwin"
|
|
||||||
case Hdragonfly:
|
|
||||||
return "dragonfly"
|
|
||||||
case Hfreebsd:
|
|
||||||
return "freebsd"
|
|
||||||
case Hlinux:
|
|
||||||
return "linux"
|
|
||||||
case Hnacl:
|
|
||||||
return "nacl"
|
|
||||||
case Hnetbsd:
|
|
||||||
return "netbsd"
|
|
||||||
case Hopenbsd:
|
|
||||||
return "openbsd"
|
|
||||||
case Hplan9:
|
|
||||||
return "plan9"
|
|
||||||
case Hsolaris:
|
|
||||||
return "solaris"
|
|
||||||
case Hwindows:
|
|
||||||
return "windows"
|
|
||||||
}
|
|
||||||
return fmt.Sprintf("HeadType(%d)", *h)
|
|
||||||
}
|
|
||||||
|
|
|
||||||
|
|
@ -31,6 +31,7 @@ package mips
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"cmd/internal/obj"
|
"cmd/internal/obj"
|
||||||
|
"cmd/internal/objabi"
|
||||||
"cmd/internal/sys"
|
"cmd/internal/sys"
|
||||||
"fmt"
|
"fmt"
|
||||||
"log"
|
"log"
|
||||||
|
|
@ -545,7 +546,7 @@ func (c *ctxt0) aclass(a *obj.Addr) int {
|
||||||
}
|
}
|
||||||
c.instoffset = a.Offset
|
c.instoffset = a.Offset
|
||||||
if a.Sym != nil { // use relocation
|
if a.Sym != nil { // use relocation
|
||||||
if a.Sym.Type == obj.STLSBSS {
|
if a.Sym.Type == objabi.STLSBSS {
|
||||||
return C_TLS
|
return C_TLS
|
||||||
}
|
}
|
||||||
return C_ADDR
|
return C_ADDR
|
||||||
|
|
@ -605,13 +606,13 @@ func (c *ctxt0) aclass(a *obj.Addr) int {
|
||||||
if s == nil {
|
if s == nil {
|
||||||
break
|
break
|
||||||
}
|
}
|
||||||
if s.Type == obj.SCONST {
|
if s.Type == objabi.SCONST {
|
||||||
c.instoffset = a.Offset
|
c.instoffset = a.Offset
|
||||||
goto consize
|
goto consize
|
||||||
}
|
}
|
||||||
|
|
||||||
c.instoffset = a.Offset
|
c.instoffset = a.Offset
|
||||||
if s.Type == obj.STLSBSS {
|
if s.Type == objabi.STLSBSS {
|
||||||
return C_STCON // address of TLS variable
|
return C_STCON // address of TLS variable
|
||||||
}
|
}
|
||||||
return C_LECON
|
return C_LECON
|
||||||
|
|
@ -1219,9 +1220,9 @@ func (c *ctxt0) asmout(p *obj.Prog, o *Optab, out []uint32) {
|
||||||
rel.Sym = p.To.Sym
|
rel.Sym = p.To.Sym
|
||||||
rel.Add = p.To.Offset
|
rel.Add = p.To.Offset
|
||||||
if p.As == AJAL {
|
if p.As == AJAL {
|
||||||
rel.Type = obj.R_CALLMIPS
|
rel.Type = objabi.R_CALLMIPS
|
||||||
} else {
|
} else {
|
||||||
rel.Type = obj.R_JMPMIPS
|
rel.Type = objabi.R_JMPMIPS
|
||||||
}
|
}
|
||||||
|
|
||||||
case 12: /* movbs r,r */
|
case 12: /* movbs r,r */
|
||||||
|
|
@ -1278,7 +1279,7 @@ func (c *ctxt0) asmout(p *obj.Prog, o *Optab, out []uint32) {
|
||||||
rel := obj.Addrel(c.cursym)
|
rel := obj.Addrel(c.cursym)
|
||||||
rel.Off = int32(c.pc)
|
rel.Off = int32(c.pc)
|
||||||
rel.Siz = 0
|
rel.Siz = 0
|
||||||
rel.Type = obj.R_CALLIND
|
rel.Type = objabi.R_CALLIND
|
||||||
|
|
||||||
case 19: /* mov $lcon,r ==> lu+or */
|
case 19: /* mov $lcon,r ==> lu+or */
|
||||||
v := c.regoff(&p.From)
|
v := c.regoff(&p.From)
|
||||||
|
|
@ -1474,14 +1475,14 @@ func (c *ctxt0) asmout(p *obj.Prog, o *Optab, out []uint32) {
|
||||||
rel.Siz = 4
|
rel.Siz = 4
|
||||||
rel.Sym = p.To.Sym
|
rel.Sym = p.To.Sym
|
||||||
rel.Add = p.To.Offset
|
rel.Add = p.To.Offset
|
||||||
rel.Type = obj.R_ADDRMIPSU
|
rel.Type = objabi.R_ADDRMIPSU
|
||||||
o2 = OP_IRR(c.opirr(p.As), uint32(0), uint32(REGTMP), uint32(p.From.Reg))
|
o2 = OP_IRR(c.opirr(p.As), uint32(0), uint32(REGTMP), uint32(p.From.Reg))
|
||||||
rel2 := obj.Addrel(c.cursym)
|
rel2 := obj.Addrel(c.cursym)
|
||||||
rel2.Off = int32(c.pc + 4)
|
rel2.Off = int32(c.pc + 4)
|
||||||
rel2.Siz = 4
|
rel2.Siz = 4
|
||||||
rel2.Sym = p.To.Sym
|
rel2.Sym = p.To.Sym
|
||||||
rel2.Add = p.To.Offset
|
rel2.Add = p.To.Offset
|
||||||
rel2.Type = obj.R_ADDRMIPS
|
rel2.Type = objabi.R_ADDRMIPS
|
||||||
|
|
||||||
if o.size == 12 {
|
if o.size == 12 {
|
||||||
o3 = o2
|
o3 = o2
|
||||||
|
|
@ -1496,14 +1497,14 @@ func (c *ctxt0) asmout(p *obj.Prog, o *Optab, out []uint32) {
|
||||||
rel.Siz = 4
|
rel.Siz = 4
|
||||||
rel.Sym = p.From.Sym
|
rel.Sym = p.From.Sym
|
||||||
rel.Add = p.From.Offset
|
rel.Add = p.From.Offset
|
||||||
rel.Type = obj.R_ADDRMIPSU
|
rel.Type = objabi.R_ADDRMIPSU
|
||||||
o2 = OP_IRR(c.opirr(-p.As), uint32(0), uint32(REGTMP), uint32(p.To.Reg))
|
o2 = OP_IRR(c.opirr(-p.As), uint32(0), uint32(REGTMP), uint32(p.To.Reg))
|
||||||
rel2 := obj.Addrel(c.cursym)
|
rel2 := obj.Addrel(c.cursym)
|
||||||
rel2.Off = int32(c.pc + 4)
|
rel2.Off = int32(c.pc + 4)
|
||||||
rel2.Siz = 4
|
rel2.Siz = 4
|
||||||
rel2.Sym = p.From.Sym
|
rel2.Sym = p.From.Sym
|
||||||
rel2.Add = p.From.Offset
|
rel2.Add = p.From.Offset
|
||||||
rel2.Type = obj.R_ADDRMIPS
|
rel2.Type = objabi.R_ADDRMIPS
|
||||||
|
|
||||||
if o.size == 12 {
|
if o.size == 12 {
|
||||||
o3 = o2
|
o3 = o2
|
||||||
|
|
@ -1518,14 +1519,14 @@ func (c *ctxt0) asmout(p *obj.Prog, o *Optab, out []uint32) {
|
||||||
rel.Siz = 4
|
rel.Siz = 4
|
||||||
rel.Sym = p.From.Sym
|
rel.Sym = p.From.Sym
|
||||||
rel.Add = p.From.Offset
|
rel.Add = p.From.Offset
|
||||||
rel.Type = obj.R_ADDRMIPSU
|
rel.Type = objabi.R_ADDRMIPSU
|
||||||
o2 = OP_IRR(c.opirr(add), uint32(0), uint32(p.To.Reg), uint32(p.To.Reg))
|
o2 = OP_IRR(c.opirr(add), uint32(0), uint32(p.To.Reg), uint32(p.To.Reg))
|
||||||
rel2 := obj.Addrel(c.cursym)
|
rel2 := obj.Addrel(c.cursym)
|
||||||
rel2.Off = int32(c.pc + 4)
|
rel2.Off = int32(c.pc + 4)
|
||||||
rel2.Siz = 4
|
rel2.Siz = 4
|
||||||
rel2.Sym = p.From.Sym
|
rel2.Sym = p.From.Sym
|
||||||
rel2.Add = p.From.Offset
|
rel2.Add = p.From.Offset
|
||||||
rel2.Type = obj.R_ADDRMIPS
|
rel2.Type = objabi.R_ADDRMIPS
|
||||||
|
|
||||||
if o.size == 12 {
|
if o.size == 12 {
|
||||||
o3 = o2
|
o3 = o2
|
||||||
|
|
@ -1543,7 +1544,7 @@ func (c *ctxt0) asmout(p *obj.Prog, o *Optab, out []uint32) {
|
||||||
rel.Siz = 4
|
rel.Siz = 4
|
||||||
rel.Sym = p.To.Sym
|
rel.Sym = p.To.Sym
|
||||||
rel.Add = p.To.Offset
|
rel.Add = p.To.Offset
|
||||||
rel.Type = obj.R_ADDRMIPSTLS
|
rel.Type = objabi.R_ADDRMIPSTLS
|
||||||
|
|
||||||
case 54: /* mov tlsvar, r ==> rdhwr + lw o(r3) */
|
case 54: /* mov tlsvar, r ==> rdhwr + lw o(r3) */
|
||||||
// clobbers R3 !
|
// clobbers R3 !
|
||||||
|
|
@ -1554,7 +1555,7 @@ func (c *ctxt0) asmout(p *obj.Prog, o *Optab, out []uint32) {
|
||||||
rel.Siz = 4
|
rel.Siz = 4
|
||||||
rel.Sym = p.From.Sym
|
rel.Sym = p.From.Sym
|
||||||
rel.Add = p.From.Offset
|
rel.Add = p.From.Offset
|
||||||
rel.Type = obj.R_ADDRMIPSTLS
|
rel.Type = objabi.R_ADDRMIPSTLS
|
||||||
|
|
||||||
case 55: /* mov $tlsvar, r ==> rdhwr + add */
|
case 55: /* mov $tlsvar, r ==> rdhwr + add */
|
||||||
// clobbers R3 !
|
// clobbers R3 !
|
||||||
|
|
@ -1565,7 +1566,7 @@ func (c *ctxt0) asmout(p *obj.Prog, o *Optab, out []uint32) {
|
||||||
rel.Siz = 4
|
rel.Siz = 4
|
||||||
rel.Sym = p.From.Sym
|
rel.Sym = p.From.Sym
|
||||||
rel.Add = p.From.Offset
|
rel.Add = p.From.Offset
|
||||||
rel.Type = obj.R_ADDRMIPSTLS
|
rel.Type = objabi.R_ADDRMIPSTLS
|
||||||
}
|
}
|
||||||
|
|
||||||
out[0] = o1
|
out[0] = o1
|
||||||
|
|
|
||||||
|
|
@ -31,6 +31,7 @@ package mips
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"cmd/internal/obj"
|
"cmd/internal/obj"
|
||||||
|
"cmd/internal/objabi"
|
||||||
"cmd/internal/sys"
|
"cmd/internal/sys"
|
||||||
"encoding/binary"
|
"encoding/binary"
|
||||||
"fmt"
|
"fmt"
|
||||||
|
|
@ -634,7 +635,7 @@ func (c *ctxt0) stacksplit(p *obj.Prog, framesize int32) *obj.Prog {
|
||||||
p.To.Reg = REG_R1
|
p.To.Reg = REG_R1
|
||||||
|
|
||||||
var q *obj.Prog
|
var q *obj.Prog
|
||||||
if framesize <= obj.StackSmall {
|
if framesize <= objabi.StackSmall {
|
||||||
// small stack: SP < stackguard
|
// small stack: SP < stackguard
|
||||||
// AGTU SP, stackguard, R1
|
// AGTU SP, stackguard, R1
|
||||||
p = obj.Appendp(p, c.newprog)
|
p = obj.Appendp(p, c.newprog)
|
||||||
|
|
@ -645,7 +646,7 @@ func (c *ctxt0) stacksplit(p *obj.Prog, framesize int32) *obj.Prog {
|
||||||
p.Reg = REG_R1
|
p.Reg = REG_R1
|
||||||
p.To.Type = obj.TYPE_REG
|
p.To.Type = obj.TYPE_REG
|
||||||
p.To.Reg = REG_R1
|
p.To.Reg = REG_R1
|
||||||
} else if framesize <= obj.StackBig {
|
} else if framesize <= objabi.StackBig {
|
||||||
// large stack: SP-framesize < stackguard-StackSmall
|
// large stack: SP-framesize < stackguard-StackSmall
|
||||||
// ADD $-(framesize-StackSmall), SP, R2
|
// ADD $-(framesize-StackSmall), SP, R2
|
||||||
// SGTU R2, stackguard, R1
|
// SGTU R2, stackguard, R1
|
||||||
|
|
@ -653,7 +654,7 @@ func (c *ctxt0) stacksplit(p *obj.Prog, framesize int32) *obj.Prog {
|
||||||
|
|
||||||
p.As = add
|
p.As = add
|
||||||
p.From.Type = obj.TYPE_CONST
|
p.From.Type = obj.TYPE_CONST
|
||||||
p.From.Offset = -(int64(framesize) - obj.StackSmall)
|
p.From.Offset = -(int64(framesize) - objabi.StackSmall)
|
||||||
p.Reg = REGSP
|
p.Reg = REGSP
|
||||||
p.To.Type = obj.TYPE_REG
|
p.To.Type = obj.TYPE_REG
|
||||||
p.To.Reg = REG_R2
|
p.To.Reg = REG_R2
|
||||||
|
|
@ -685,7 +686,7 @@ func (c *ctxt0) stacksplit(p *obj.Prog, framesize int32) *obj.Prog {
|
||||||
|
|
||||||
p.As = mov
|
p.As = mov
|
||||||
p.From.Type = obj.TYPE_CONST
|
p.From.Type = obj.TYPE_CONST
|
||||||
p.From.Offset = obj.StackPreempt
|
p.From.Offset = objabi.StackPreempt
|
||||||
p.To.Type = obj.TYPE_REG
|
p.To.Type = obj.TYPE_REG
|
||||||
p.To.Reg = REG_R2
|
p.To.Reg = REG_R2
|
||||||
|
|
||||||
|
|
@ -701,7 +702,7 @@ func (c *ctxt0) stacksplit(p *obj.Prog, framesize int32) *obj.Prog {
|
||||||
p = obj.Appendp(p, c.newprog)
|
p = obj.Appendp(p, c.newprog)
|
||||||
p.As = add
|
p.As = add
|
||||||
p.From.Type = obj.TYPE_CONST
|
p.From.Type = obj.TYPE_CONST
|
||||||
p.From.Offset = obj.StackGuard
|
p.From.Offset = objabi.StackGuard
|
||||||
p.Reg = REGSP
|
p.Reg = REGSP
|
||||||
p.To.Type = obj.TYPE_REG
|
p.To.Type = obj.TYPE_REG
|
||||||
p.To.Reg = REG_R2
|
p.To.Reg = REG_R2
|
||||||
|
|
@ -716,7 +717,7 @@ func (c *ctxt0) stacksplit(p *obj.Prog, framesize int32) *obj.Prog {
|
||||||
p = obj.Appendp(p, c.newprog)
|
p = obj.Appendp(p, c.newprog)
|
||||||
p.As = mov
|
p.As = mov
|
||||||
p.From.Type = obj.TYPE_CONST
|
p.From.Type = obj.TYPE_CONST
|
||||||
p.From.Offset = int64(framesize) + obj.StackGuard - obj.StackSmall
|
p.From.Offset = int64(framesize) + objabi.StackGuard - objabi.StackSmall
|
||||||
p.To.Type = obj.TYPE_REG
|
p.To.Type = obj.TYPE_REG
|
||||||
p.To.Reg = REG_R1
|
p.To.Reg = REG_R1
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -3,118 +3,13 @@
|
||||||
// license that can be found in the LICENSE file.
|
// license that can be found in the LICENSE file.
|
||||||
|
|
||||||
// Writing of Go object files.
|
// Writing of Go object files.
|
||||||
//
|
|
||||||
// Originally, Go object files were Plan 9 object files, but no longer.
|
|
||||||
// Now they are more like standard object files, in that each symbol is defined
|
|
||||||
// by an associated memory image (bytes) and a list of relocations to apply
|
|
||||||
// during linking. We do not (yet?) use a standard file format, however.
|
|
||||||
// For now, the format is chosen to be as simple as possible to read and write.
|
|
||||||
// It may change for reasons of efficiency, or we may even switch to a
|
|
||||||
// standard file format if there are compelling benefits to doing so.
|
|
||||||
// See golang.org/s/go13linker for more background.
|
|
||||||
//
|
|
||||||
// The file format is:
|
|
||||||
//
|
|
||||||
// - magic header: "\x00\x00go19ld"
|
|
||||||
// - byte 1 - version number
|
|
||||||
// - sequence of strings giving dependencies (imported packages)
|
|
||||||
// - empty string (marks end of sequence)
|
|
||||||
// - sequence of symbol references used by the defined symbols
|
|
||||||
// - byte 0xff (marks end of sequence)
|
|
||||||
// - sequence of integer lengths:
|
|
||||||
// - total data length
|
|
||||||
// - total number of relocations
|
|
||||||
// - total number of pcdata
|
|
||||||
// - total number of automatics
|
|
||||||
// - total number of funcdata
|
|
||||||
// - total number of files
|
|
||||||
// - data, the content of the defined symbols
|
|
||||||
// - sequence of defined symbols
|
|
||||||
// - byte 0xff (marks end of sequence)
|
|
||||||
// - magic footer: "\xff\xffgo19ld"
|
|
||||||
//
|
|
||||||
// All integers are stored in a zigzag varint format.
|
|
||||||
// See golang.org/s/go12symtab for a definition.
|
|
||||||
//
|
|
||||||
// Data blocks and strings are both stored as an integer
|
|
||||||
// followed by that many bytes.
|
|
||||||
//
|
|
||||||
// A symbol reference is a string name followed by a version.
|
|
||||||
//
|
|
||||||
// A symbol points to other symbols using an index into the symbol
|
|
||||||
// reference sequence. Index 0 corresponds to a nil LSym* pointer.
|
|
||||||
// In the symbol layout described below "symref index" stands for this
|
|
||||||
// index.
|
|
||||||
//
|
|
||||||
// Each symbol is laid out as the following fields (taken from LSym*):
|
|
||||||
//
|
|
||||||
// - byte 0xfe (sanity check for synchronization)
|
|
||||||
// - type [int]
|
|
||||||
// - name & version [symref index]
|
|
||||||
// - flags [int]
|
|
||||||
// 1<<0 dupok
|
|
||||||
// 1<<1 local
|
|
||||||
// 1<<2 add to typelink table
|
|
||||||
// - size [int]
|
|
||||||
// - gotype [symref index]
|
|
||||||
// - p [data block]
|
|
||||||
// - nr [int]
|
|
||||||
// - r [nr relocations, sorted by off]
|
|
||||||
//
|
|
||||||
// If type == STEXT, there are a few more fields:
|
|
||||||
//
|
|
||||||
// - args [int]
|
|
||||||
// - locals [int]
|
|
||||||
// - nosplit [int]
|
|
||||||
// - flags [int]
|
|
||||||
// 1<<0 leaf
|
|
||||||
// 1<<1 C function
|
|
||||||
// 1<<2 function may call reflect.Type.Method
|
|
||||||
// - nlocal [int]
|
|
||||||
// - local [nlocal automatics]
|
|
||||||
// - pcln [pcln table]
|
|
||||||
//
|
|
||||||
// Each relocation has the encoding:
|
|
||||||
//
|
|
||||||
// - off [int]
|
|
||||||
// - siz [int]
|
|
||||||
// - type [int]
|
|
||||||
// - add [int]
|
|
||||||
// - sym [symref index]
|
|
||||||
//
|
|
||||||
// Each local has the encoding:
|
|
||||||
//
|
|
||||||
// - asym [symref index]
|
|
||||||
// - offset [int]
|
|
||||||
// - type [int]
|
|
||||||
// - gotype [symref index]
|
|
||||||
//
|
|
||||||
// The pcln table has the encoding:
|
|
||||||
//
|
|
||||||
// - pcsp [data block]
|
|
||||||
// - pcfile [data block]
|
|
||||||
// - pcline [data block]
|
|
||||||
// - pcinline [data block]
|
|
||||||
// - npcdata [int]
|
|
||||||
// - pcdata [npcdata data blocks]
|
|
||||||
// - nfuncdata [int]
|
|
||||||
// - funcdata [nfuncdata symref index]
|
|
||||||
// - funcdatasym [nfuncdata ints]
|
|
||||||
// - nfile [int]
|
|
||||||
// - file [nfile symref index]
|
|
||||||
// - ninlinedcall [int]
|
|
||||||
// - inlinedcall [ninlinedcall int symref int symref]
|
|
||||||
//
|
|
||||||
// The file layout and meaning of type integers are architecture-independent.
|
|
||||||
//
|
|
||||||
// TODO(rsc): The file format is good for a first pass but needs work.
|
|
||||||
// - There are SymID in the object file that should really just be strings.
|
|
||||||
|
|
||||||
package obj
|
package obj
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"bufio"
|
"bufio"
|
||||||
"cmd/internal/dwarf"
|
"cmd/internal/dwarf"
|
||||||
|
"cmd/internal/objabi"
|
||||||
"cmd/internal/sys"
|
"cmd/internal/sys"
|
||||||
"fmt"
|
"fmt"
|
||||||
"log"
|
"log"
|
||||||
|
|
@ -149,7 +44,7 @@ func (w *objWriter) addLengths(s *LSym) {
|
||||||
w.nData += len(s.P)
|
w.nData += len(s.P)
|
||||||
w.nReloc += len(s.R)
|
w.nReloc += len(s.R)
|
||||||
|
|
||||||
if s.Type != STEXT {
|
if s.Type != objabi.STEXT {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -289,7 +184,7 @@ func (w *objWriter) writeRefs(s *LSym) {
|
||||||
w.writeRef(s.R[i].Sym, false)
|
w.writeRef(s.R[i].Sym, false)
|
||||||
}
|
}
|
||||||
|
|
||||||
if s.Type == STEXT {
|
if s.Type == objabi.STEXT {
|
||||||
for _, a := range s.Func.Autom {
|
for _, a := range s.Func.Autom {
|
||||||
w.writeRef(a.Asym, false)
|
w.writeRef(a.Asym, false)
|
||||||
w.writeRef(a.Gotype, false)
|
w.writeRef(a.Gotype, false)
|
||||||
|
|
@ -330,14 +225,14 @@ func (w *objWriter) writeSymDebug(s *LSym) {
|
||||||
fmt.Fprintf(ctxt.Bso, "nosplit ")
|
fmt.Fprintf(ctxt.Bso, "nosplit ")
|
||||||
}
|
}
|
||||||
fmt.Fprintf(ctxt.Bso, "size=%d", s.Size)
|
fmt.Fprintf(ctxt.Bso, "size=%d", s.Size)
|
||||||
if s.Type == STEXT {
|
if s.Type == objabi.STEXT {
|
||||||
fmt.Fprintf(ctxt.Bso, " args=%#x locals=%#x", uint64(s.Func.Args), uint64(s.Func.Locals))
|
fmt.Fprintf(ctxt.Bso, " args=%#x locals=%#x", uint64(s.Func.Args), uint64(s.Func.Locals))
|
||||||
if s.Leaf() {
|
if s.Leaf() {
|
||||||
fmt.Fprintf(ctxt.Bso, " leaf")
|
fmt.Fprintf(ctxt.Bso, " leaf")
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
fmt.Fprintf(ctxt.Bso, "\n")
|
fmt.Fprintf(ctxt.Bso, "\n")
|
||||||
if s.Type == STEXT {
|
if s.Type == objabi.STEXT {
|
||||||
for p := s.Func.Text; p != nil; p = p.Link {
|
for p := s.Func.Text; p != nil; p = p.Link {
|
||||||
fmt.Fprintf(ctxt.Bso, "\t%#04x %v\n", uint(int(p.Pc)), p)
|
fmt.Fprintf(ctxt.Bso, "\t%#04x %v\n", uint(int(p.Pc)), p)
|
||||||
}
|
}
|
||||||
|
|
@ -369,7 +264,7 @@ func (w *objWriter) writeSymDebug(s *LSym) {
|
||||||
name := ""
|
name := ""
|
||||||
if r.Sym != nil {
|
if r.Sym != nil {
|
||||||
name = r.Sym.Name
|
name = r.Sym.Name
|
||||||
} else if r.Type == R_TLS_LE {
|
} else if r.Type == objabi.R_TLS_LE {
|
||||||
name = "TLS"
|
name = "TLS"
|
||||||
}
|
}
|
||||||
if ctxt.Arch.InFamily(sys.ARM, sys.PPC64) {
|
if ctxt.Arch.InFamily(sys.ARM, sys.PPC64) {
|
||||||
|
|
@ -415,7 +310,7 @@ func (w *objWriter) writeSym(s *LSym) {
|
||||||
w.writeRefIndex(r.Sym)
|
w.writeRefIndex(r.Sym)
|
||||||
}
|
}
|
||||||
|
|
||||||
if s.Type != STEXT {
|
if s.Type != objabi.STEXT {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -442,9 +337,9 @@ func (w *objWriter) writeSym(s *LSym) {
|
||||||
w.writeRefIndex(a.Asym)
|
w.writeRefIndex(a.Asym)
|
||||||
w.writeInt(int64(a.Aoffset))
|
w.writeInt(int64(a.Aoffset))
|
||||||
if a.Name == NAME_AUTO {
|
if a.Name == NAME_AUTO {
|
||||||
w.writeInt(A_AUTO)
|
w.writeInt(objabi.A_AUTO)
|
||||||
} else if a.Name == NAME_PARAM {
|
} else if a.Name == NAME_PARAM {
|
||||||
w.writeInt(A_PARAM)
|
w.writeInt(objabi.A_PARAM)
|
||||||
} else {
|
} else {
|
||||||
log.Fatalf("%s: invalid local variable type %d", s.Name, a.Name)
|
log.Fatalf("%s: invalid local variable type %d", s.Name, a.Name)
|
||||||
}
|
}
|
||||||
|
|
@ -552,12 +447,12 @@ func (c dwCtxt) AddSectionOffset(s dwarf.Sym, size int, t interface{}, ofs int64
|
||||||
rsym := t.(*LSym)
|
rsym := t.(*LSym)
|
||||||
ls.WriteAddr(c.Link, ls.Size, size, rsym, ofs)
|
ls.WriteAddr(c.Link, ls.Size, size, rsym, ofs)
|
||||||
r := &ls.R[len(ls.R)-1]
|
r := &ls.R[len(ls.R)-1]
|
||||||
r.Type = R_DWARFREF
|
r.Type = objabi.R_DWARFREF
|
||||||
}
|
}
|
||||||
|
|
||||||
// dwarfSym returns the DWARF symbol for TEXT symbol.
|
// dwarfSym returns the DWARF symbol for TEXT symbol.
|
||||||
func (ctxt *Link) dwarfSym(s *LSym) *LSym {
|
func (ctxt *Link) dwarfSym(s *LSym) *LSym {
|
||||||
if s.Type != STEXT {
|
if s.Type != objabi.STEXT {
|
||||||
ctxt.Diag("dwarfSym of non-TEXT %v", s)
|
ctxt.Diag("dwarfSym of non-TEXT %v", s)
|
||||||
}
|
}
|
||||||
if s.Func.dwarfSym == nil {
|
if s.Func.dwarfSym == nil {
|
||||||
|
|
|
||||||
|
|
@ -5,6 +5,7 @@
|
||||||
package obj
|
package obj
|
||||||
|
|
||||||
import (
|
import (
|
||||||
|
"cmd/internal/objabi"
|
||||||
"fmt"
|
"fmt"
|
||||||
"strings"
|
"strings"
|
||||||
)
|
)
|
||||||
|
|
@ -54,7 +55,7 @@ func Flushplist(ctxt *Link, plist *Plist, newprog ProgAlloc) {
|
||||||
continue
|
continue
|
||||||
}
|
}
|
||||||
if p.To.Sym.Name == "go_args_stackmap" {
|
if p.To.Sym.Name == "go_args_stackmap" {
|
||||||
if p.From.Type != TYPE_CONST || p.From.Offset != FUNCDATA_ArgsPointerMaps {
|
if p.From.Type != TYPE_CONST || p.From.Offset != objabi.FUNCDATA_ArgsPointerMaps {
|
||||||
ctxt.Diag("FUNCDATA use of go_args_stackmap(SB) without FUNCDATA_ArgsPointerMaps")
|
ctxt.Diag("FUNCDATA use of go_args_stackmap(SB) without FUNCDATA_ArgsPointerMaps")
|
||||||
}
|
}
|
||||||
p.To.Sym = ctxt.Lookup(fmt.Sprintf("%s.args_stackmap", curtext.Name), int(curtext.Version))
|
p.To.Sym = ctxt.Lookup(fmt.Sprintf("%s.args_stackmap", curtext.Name), int(curtext.Version))
|
||||||
|
|
@ -81,7 +82,7 @@ func Flushplist(ctxt *Link, plist *Plist, newprog ProgAlloc) {
|
||||||
}
|
}
|
||||||
found := false
|
found := false
|
||||||
for p := s.Func.Text; p != nil; p = p.Link {
|
for p := s.Func.Text; p != nil; p = p.Link {
|
||||||
if p.As == AFUNCDATA && p.From.Type == TYPE_CONST && p.From.Offset == FUNCDATA_ArgsPointerMaps {
|
if p.As == AFUNCDATA && p.From.Type == TYPE_CONST && p.From.Offset == objabi.FUNCDATA_ArgsPointerMaps {
|
||||||
found = true
|
found = true
|
||||||
break
|
break
|
||||||
}
|
}
|
||||||
|
|
@ -91,7 +92,7 @@ func Flushplist(ctxt *Link, plist *Plist, newprog ProgAlloc) {
|
||||||
p := Appendp(s.Func.Text, newprog)
|
p := Appendp(s.Func.Text, newprog)
|
||||||
p.As = AFUNCDATA
|
p.As = AFUNCDATA
|
||||||
p.From.Type = TYPE_CONST
|
p.From.Type = TYPE_CONST
|
||||||
p.From.Offset = FUNCDATA_ArgsPointerMaps
|
p.From.Offset = objabi.FUNCDATA_ArgsPointerMaps
|
||||||
p.To.Type = TYPE_MEM
|
p.To.Type = TYPE_MEM
|
||||||
p.To.Name = NAME_EXTERN
|
p.To.Name = NAME_EXTERN
|
||||||
p.To.Sym = ctxt.Lookup(fmt.Sprintf("%s.args_stackmap", s.Name), int(s.Version))
|
p.To.Sym = ctxt.Lookup(fmt.Sprintf("%s.args_stackmap", s.Name), int(s.Version))
|
||||||
|
|
@ -131,12 +132,12 @@ func (ctxt *Link) InitTextSym(s *LSym, flag int) {
|
||||||
s.Set(AttrWrapper, flag&WRAPPER != 0)
|
s.Set(AttrWrapper, flag&WRAPPER != 0)
|
||||||
s.Set(AttrNeedCtxt, flag&NEEDCTXT != 0)
|
s.Set(AttrNeedCtxt, flag&NEEDCTXT != 0)
|
||||||
s.Set(AttrNoFrame, flag&NOFRAME != 0)
|
s.Set(AttrNoFrame, flag&NOFRAME != 0)
|
||||||
s.Type = STEXT
|
s.Type = objabi.STEXT
|
||||||
ctxt.Text = append(ctxt.Text, s)
|
ctxt.Text = append(ctxt.Text, s)
|
||||||
|
|
||||||
// Set up DWARF entry for s.
|
// Set up DWARF entry for s.
|
||||||
dsym := ctxt.dwarfSym(s)
|
dsym := ctxt.dwarfSym(s)
|
||||||
dsym.Type = SDWARFINFO
|
dsym.Type = objabi.SDWARFINFO
|
||||||
dsym.Set(AttrDuplicateOK, s.DuplicateOK())
|
dsym.Set(AttrDuplicateOK, s.DuplicateOK())
|
||||||
ctxt.Data = append(ctxt.Data, dsym)
|
ctxt.Data = append(ctxt.Data, dsym)
|
||||||
|
|
||||||
|
|
@ -144,10 +145,10 @@ func (ctxt *Link) InitTextSym(s *LSym, flag int) {
|
||||||
// They will be filled in later if needed.
|
// They will be filled in later if needed.
|
||||||
gcargs := &s.Func.GCArgs
|
gcargs := &s.Func.GCArgs
|
||||||
gcargs.Set(AttrDuplicateOK, true)
|
gcargs.Set(AttrDuplicateOK, true)
|
||||||
gcargs.Type = SRODATA
|
gcargs.Type = objabi.SRODATA
|
||||||
gclocals := &s.Func.GCLocals
|
gclocals := &s.Func.GCLocals
|
||||||
gclocals.Set(AttrDuplicateOK, true)
|
gclocals.Set(AttrDuplicateOK, true)
|
||||||
gclocals.Type = SRODATA
|
gclocals.Type = objabi.SRODATA
|
||||||
}
|
}
|
||||||
|
|
||||||
func (ctxt *Link) Globl(s *LSym, size int64, flag int) {
|
func (ctxt *Link) Globl(s *LSym, size int64, flag int) {
|
||||||
|
|
@ -161,17 +162,17 @@ func (ctxt *Link) Globl(s *LSym, size int64, flag int) {
|
||||||
s.Set(AttrOnList, true)
|
s.Set(AttrOnList, true)
|
||||||
ctxt.Data = append(ctxt.Data, s)
|
ctxt.Data = append(ctxt.Data, s)
|
||||||
s.Size = size
|
s.Size = size
|
||||||
if s.Type == 0 || s.Type == SXREF {
|
if s.Type == 0 || s.Type == objabi.SXREF {
|
||||||
s.Type = SBSS
|
s.Type = objabi.SBSS
|
||||||
}
|
}
|
||||||
if flag&DUPOK != 0 {
|
if flag&DUPOK != 0 {
|
||||||
s.Set(AttrDuplicateOK, true)
|
s.Set(AttrDuplicateOK, true)
|
||||||
}
|
}
|
||||||
if flag&RODATA != 0 {
|
if flag&RODATA != 0 {
|
||||||
s.Type = SRODATA
|
s.Type = objabi.SRODATA
|
||||||
} else if flag&NOPTR != 0 {
|
} else if flag&NOPTR != 0 {
|
||||||
s.Type = SNOPTRBSS
|
s.Type = objabi.SNOPTRBSS
|
||||||
} else if flag&TLSBSS != 0 {
|
} else if flag&TLSBSS != 0 {
|
||||||
s.Type = STLSBSS
|
s.Type = objabi.STLSBSS
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -31,6 +31,7 @@ package ppc64
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"cmd/internal/obj"
|
"cmd/internal/obj"
|
||||||
|
"cmd/internal/objabi"
|
||||||
"encoding/binary"
|
"encoding/binary"
|
||||||
"fmt"
|
"fmt"
|
||||||
"log"
|
"log"
|
||||||
|
|
@ -742,7 +743,7 @@ func (c *ctxt9) aclass(a *obj.Addr) int {
|
||||||
}
|
}
|
||||||
c.instoffset = a.Offset
|
c.instoffset = a.Offset
|
||||||
if a.Sym != nil { // use relocation
|
if a.Sym != nil { // use relocation
|
||||||
if a.Sym.Type == obj.STLSBSS {
|
if a.Sym.Type == objabi.STLSBSS {
|
||||||
if c.ctxt.Flag_shared {
|
if c.ctxt.Flag_shared {
|
||||||
return C_TLS_IE
|
return C_TLS_IE
|
||||||
} else {
|
} else {
|
||||||
|
|
@ -809,7 +810,7 @@ func (c *ctxt9) aclass(a *obj.Addr) int {
|
||||||
if s == nil {
|
if s == nil {
|
||||||
break
|
break
|
||||||
}
|
}
|
||||||
if s.Type == obj.SCONST {
|
if s.Type == objabi.SCONST {
|
||||||
c.instoffset = a.Offset
|
c.instoffset = a.Offset
|
||||||
goto consize
|
goto consize
|
||||||
}
|
}
|
||||||
|
|
@ -2052,17 +2053,17 @@ func (c *ctxt9) symbolAccess(s *obj.LSym, d int64, reg int16, op uint32) (o1, o2
|
||||||
if c.ctxt.Flag_shared {
|
if c.ctxt.Flag_shared {
|
||||||
switch form {
|
switch form {
|
||||||
case D_FORM:
|
case D_FORM:
|
||||||
rel.Type = obj.R_ADDRPOWER_TOCREL
|
rel.Type = objabi.R_ADDRPOWER_TOCREL
|
||||||
case DS_FORM:
|
case DS_FORM:
|
||||||
rel.Type = obj.R_ADDRPOWER_TOCREL_DS
|
rel.Type = objabi.R_ADDRPOWER_TOCREL_DS
|
||||||
}
|
}
|
||||||
|
|
||||||
} else {
|
} else {
|
||||||
switch form {
|
switch form {
|
||||||
case D_FORM:
|
case D_FORM:
|
||||||
rel.Type = obj.R_ADDRPOWER
|
rel.Type = objabi.R_ADDRPOWER
|
||||||
case DS_FORM:
|
case DS_FORM:
|
||||||
rel.Type = obj.R_ADDRPOWER_DS
|
rel.Type = objabi.R_ADDRPOWER_DS
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
return
|
return
|
||||||
|
|
@ -2280,7 +2281,7 @@ func (c *ctxt9) asmout(p *obj.Prog, o *Optab, out []uint32) {
|
||||||
// we could add some assembly syntax so that the name
|
// we could add some assembly syntax so that the name
|
||||||
// of the variable does not have to be assumed.
|
// of the variable does not have to be assumed.
|
||||||
rel.Sym = c.ctxt.Lookup("runtime.tls_g", 0)
|
rel.Sym = c.ctxt.Lookup("runtime.tls_g", 0)
|
||||||
rel.Type = obj.R_POWER_TLS
|
rel.Type = objabi.R_POWER_TLS
|
||||||
}
|
}
|
||||||
o1 = AOP_RRR(c.opstorex(p.As), uint32(p.From.Reg), uint32(p.To.Index), uint32(r))
|
o1 = AOP_RRR(c.opstorex(p.As), uint32(p.From.Reg), uint32(p.To.Index), uint32(r))
|
||||||
} else {
|
} else {
|
||||||
|
|
@ -2311,7 +2312,7 @@ func (c *ctxt9) asmout(p *obj.Prog, o *Optab, out []uint32) {
|
||||||
rel.Off = int32(c.pc)
|
rel.Off = int32(c.pc)
|
||||||
rel.Siz = 4
|
rel.Siz = 4
|
||||||
rel.Sym = c.ctxt.Lookup("runtime.tls_g", 0)
|
rel.Sym = c.ctxt.Lookup("runtime.tls_g", 0)
|
||||||
rel.Type = obj.R_POWER_TLS
|
rel.Type = objabi.R_POWER_TLS
|
||||||
}
|
}
|
||||||
o1 = AOP_RRR(c.oploadx(p.As), uint32(p.To.Reg), uint32(p.From.Index), uint32(r))
|
o1 = AOP_RRR(c.oploadx(p.As), uint32(p.To.Reg), uint32(p.From.Index), uint32(r))
|
||||||
} else {
|
} else {
|
||||||
|
|
@ -2379,7 +2380,7 @@ func (c *ctxt9) asmout(p *obj.Prog, o *Optab, out []uint32) {
|
||||||
}
|
}
|
||||||
|
|
||||||
rel.Add = int64(v)
|
rel.Add = int64(v)
|
||||||
rel.Type = obj.R_CALLPOWER
|
rel.Type = objabi.R_CALLPOWER
|
||||||
}
|
}
|
||||||
o2 = 0x60000000 // nop, sometimes overwritten by ld r2, 24(r1) when dynamic linking
|
o2 = 0x60000000 // nop, sometimes overwritten by ld r2, 24(r1) when dynamic linking
|
||||||
|
|
||||||
|
|
@ -2787,7 +2788,7 @@ func (c *ctxt9) asmout(p *obj.Prog, o *Optab, out []uint32) {
|
||||||
rel.Siz = 8
|
rel.Siz = 8
|
||||||
rel.Sym = p.From.Sym
|
rel.Sym = p.From.Sym
|
||||||
rel.Add = p.From.Offset
|
rel.Add = p.From.Offset
|
||||||
rel.Type = obj.R_ADDR
|
rel.Type = objabi.R_ADDR
|
||||||
o2 = 0
|
o2 = 0
|
||||||
o1 = o2
|
o1 = o2
|
||||||
}
|
}
|
||||||
|
|
@ -3195,7 +3196,7 @@ func (c *ctxt9) asmout(p *obj.Prog, o *Optab, out []uint32) {
|
||||||
rel.Off = int32(c.pc)
|
rel.Off = int32(c.pc)
|
||||||
rel.Siz = 4
|
rel.Siz = 4
|
||||||
rel.Sym = p.From.Sym
|
rel.Sym = p.From.Sym
|
||||||
rel.Type = obj.R_POWER_TLS_LE
|
rel.Type = objabi.R_POWER_TLS_LE
|
||||||
|
|
||||||
case 80:
|
case 80:
|
||||||
if p.From.Offset != 0 {
|
if p.From.Offset != 0 {
|
||||||
|
|
@ -3207,7 +3208,7 @@ func (c *ctxt9) asmout(p *obj.Prog, o *Optab, out []uint32) {
|
||||||
rel.Off = int32(c.pc)
|
rel.Off = int32(c.pc)
|
||||||
rel.Siz = 8
|
rel.Siz = 8
|
||||||
rel.Sym = p.From.Sym
|
rel.Sym = p.From.Sym
|
||||||
rel.Type = obj.R_POWER_TLS_IE
|
rel.Type = objabi.R_POWER_TLS_IE
|
||||||
|
|
||||||
case 81:
|
case 81:
|
||||||
v := c.vregoff(&p.To)
|
v := c.vregoff(&p.To)
|
||||||
|
|
@ -3221,7 +3222,7 @@ func (c *ctxt9) asmout(p *obj.Prog, o *Optab, out []uint32) {
|
||||||
rel.Off = int32(c.pc)
|
rel.Off = int32(c.pc)
|
||||||
rel.Siz = 8
|
rel.Siz = 8
|
||||||
rel.Sym = p.From.Sym
|
rel.Sym = p.From.Sym
|
||||||
rel.Type = obj.R_ADDRPOWER_GOT
|
rel.Type = objabi.R_ADDRPOWER_GOT
|
||||||
case 82: /* vector instructions, VX-form and VC-form */
|
case 82: /* vector instructions, VX-form and VC-form */
|
||||||
if p.From.Type == obj.TYPE_REG {
|
if p.From.Type == obj.TYPE_REG {
|
||||||
/* reg reg none OR reg reg reg */
|
/* reg reg none OR reg reg reg */
|
||||||
|
|
|
||||||
|
|
@ -31,6 +31,7 @@ package ppc64
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"cmd/internal/obj"
|
"cmd/internal/obj"
|
||||||
|
"cmd/internal/objabi"
|
||||||
"cmd/internal/sys"
|
"cmd/internal/sys"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
|
@ -195,7 +196,7 @@ func (c *ctxt9) rewriteToUseGot(p *obj.Prog) {
|
||||||
if p.As == obj.ATEXT || p.As == obj.AFUNCDATA || p.As == obj.ACALL || p.As == obj.ARET || p.As == obj.AJMP {
|
if p.As == obj.ATEXT || p.As == obj.AFUNCDATA || p.As == obj.ACALL || p.As == obj.ARET || p.As == obj.AJMP {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
if source.Sym.Type == obj.STLSBSS {
|
if source.Sym.Type == objabi.STLSBSS {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
if source.Type != obj.TYPE_MEM {
|
if source.Type != obj.TYPE_MEM {
|
||||||
|
|
@ -448,7 +449,7 @@ func preprocess(ctxt *obj.Link, cursym *obj.LSym, newprog obj.ProgAlloc) {
|
||||||
autosize += int32(c.ctxt.FixedFrameSize())
|
autosize += int32(c.ctxt.FixedFrameSize())
|
||||||
}
|
}
|
||||||
|
|
||||||
if p.Mark&LEAF != 0 && autosize < obj.StackSmall {
|
if p.Mark&LEAF != 0 && autosize < objabi.StackSmall {
|
||||||
// A leaf function with a small stack can be marked
|
// A leaf function with a small stack can be marked
|
||||||
// NOSPLIT, avoiding a stack check.
|
// NOSPLIT, avoiding a stack check.
|
||||||
p.From.Sym.Set(obj.AttrNoSplit, true)
|
p.From.Sym.Set(obj.AttrNoSplit, true)
|
||||||
|
|
@ -489,7 +490,7 @@ func preprocess(ctxt *obj.Link, cursym *obj.LSym, newprog obj.ProgAlloc) {
|
||||||
rel.Off = 0
|
rel.Off = 0
|
||||||
rel.Siz = 8
|
rel.Siz = 8
|
||||||
rel.Sym = c.ctxt.Lookup(".TOC.", 0)
|
rel.Sym = c.ctxt.Lookup(".TOC.", 0)
|
||||||
rel.Type = obj.R_ADDRPOWER_PCREL
|
rel.Type = objabi.R_ADDRPOWER_PCREL
|
||||||
}
|
}
|
||||||
|
|
||||||
if !c.cursym.Func.Text.From.Sym.NoSplit() {
|
if !c.cursym.Func.Text.From.Sym.NoSplit() {
|
||||||
|
|
@ -840,7 +841,7 @@ func (c *ctxt9) stacksplit(p *obj.Prog, framesize int32) *obj.Prog {
|
||||||
p.To.Reg = REG_R3
|
p.To.Reg = REG_R3
|
||||||
|
|
||||||
var q *obj.Prog
|
var q *obj.Prog
|
||||||
if framesize <= obj.StackSmall {
|
if framesize <= objabi.StackSmall {
|
||||||
// small stack: SP < stackguard
|
// small stack: SP < stackguard
|
||||||
// CMP stackguard, SP
|
// CMP stackguard, SP
|
||||||
p = obj.Appendp(p, c.newprog)
|
p = obj.Appendp(p, c.newprog)
|
||||||
|
|
@ -850,7 +851,7 @@ func (c *ctxt9) stacksplit(p *obj.Prog, framesize int32) *obj.Prog {
|
||||||
p.From.Reg = REG_R3
|
p.From.Reg = REG_R3
|
||||||
p.To.Type = obj.TYPE_REG
|
p.To.Type = obj.TYPE_REG
|
||||||
p.To.Reg = REGSP
|
p.To.Reg = REGSP
|
||||||
} else if framesize <= obj.StackBig {
|
} else if framesize <= objabi.StackBig {
|
||||||
// large stack: SP-framesize < stackguard-StackSmall
|
// large stack: SP-framesize < stackguard-StackSmall
|
||||||
// ADD $-(framesize-StackSmall), SP, R4
|
// ADD $-(framesize-StackSmall), SP, R4
|
||||||
// CMP stackguard, R4
|
// CMP stackguard, R4
|
||||||
|
|
@ -858,7 +859,7 @@ func (c *ctxt9) stacksplit(p *obj.Prog, framesize int32) *obj.Prog {
|
||||||
|
|
||||||
p.As = AADD
|
p.As = AADD
|
||||||
p.From.Type = obj.TYPE_CONST
|
p.From.Type = obj.TYPE_CONST
|
||||||
p.From.Offset = -(int64(framesize) - obj.StackSmall)
|
p.From.Offset = -(int64(framesize) - objabi.StackSmall)
|
||||||
p.Reg = REGSP
|
p.Reg = REGSP
|
||||||
p.To.Type = obj.TYPE_REG
|
p.To.Type = obj.TYPE_REG
|
||||||
p.To.Reg = REG_R4
|
p.To.Reg = REG_R4
|
||||||
|
|
@ -891,7 +892,7 @@ func (c *ctxt9) stacksplit(p *obj.Prog, framesize int32) *obj.Prog {
|
||||||
p.From.Type = obj.TYPE_REG
|
p.From.Type = obj.TYPE_REG
|
||||||
p.From.Reg = REG_R3
|
p.From.Reg = REG_R3
|
||||||
p.To.Type = obj.TYPE_CONST
|
p.To.Type = obj.TYPE_CONST
|
||||||
p.To.Offset = obj.StackPreempt
|
p.To.Offset = objabi.StackPreempt
|
||||||
|
|
||||||
p = obj.Appendp(p, c.newprog)
|
p = obj.Appendp(p, c.newprog)
|
||||||
q = p
|
q = p
|
||||||
|
|
@ -901,7 +902,7 @@ func (c *ctxt9) stacksplit(p *obj.Prog, framesize int32) *obj.Prog {
|
||||||
p = obj.Appendp(p, c.newprog)
|
p = obj.Appendp(p, c.newprog)
|
||||||
p.As = AADD
|
p.As = AADD
|
||||||
p.From.Type = obj.TYPE_CONST
|
p.From.Type = obj.TYPE_CONST
|
||||||
p.From.Offset = obj.StackGuard
|
p.From.Offset = objabi.StackGuard
|
||||||
p.Reg = REGSP
|
p.Reg = REGSP
|
||||||
p.To.Type = obj.TYPE_REG
|
p.To.Type = obj.TYPE_REG
|
||||||
p.To.Reg = REG_R4
|
p.To.Reg = REG_R4
|
||||||
|
|
@ -916,7 +917,7 @@ func (c *ctxt9) stacksplit(p *obj.Prog, framesize int32) *obj.Prog {
|
||||||
p = obj.Appendp(p, c.newprog)
|
p = obj.Appendp(p, c.newprog)
|
||||||
p.As = AMOVD
|
p.As = AMOVD
|
||||||
p.From.Type = obj.TYPE_CONST
|
p.From.Type = obj.TYPE_CONST
|
||||||
p.From.Offset = int64(framesize) + obj.StackGuard - obj.StackSmall
|
p.From.Offset = int64(framesize) + objabi.StackGuard - objabi.StackSmall
|
||||||
p.To.Type = obj.TYPE_REG
|
p.To.Type = obj.TYPE_REG
|
||||||
p.To.Reg = REGTMP
|
p.To.Reg = REGTMP
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -31,6 +31,7 @@ package s390x
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"cmd/internal/obj"
|
"cmd/internal/obj"
|
||||||
|
"cmd/internal/objabi"
|
||||||
"log"
|
"log"
|
||||||
"math"
|
"math"
|
||||||
"sort"
|
"sort"
|
||||||
|
|
@ -487,7 +488,7 @@ func (c *ctxtz) aclass(a *obj.Addr) int {
|
||||||
break
|
break
|
||||||
}
|
}
|
||||||
c.instoffset = a.Offset
|
c.instoffset = a.Offset
|
||||||
if a.Sym.Type == obj.STLSBSS {
|
if a.Sym.Type == objabi.STLSBSS {
|
||||||
if c.ctxt.Flag_shared {
|
if c.ctxt.Flag_shared {
|
||||||
return C_TLS_IE // initial exec model
|
return C_TLS_IE // initial exec model
|
||||||
}
|
}
|
||||||
|
|
@ -557,7 +558,7 @@ func (c *ctxtz) aclass(a *obj.Addr) int {
|
||||||
break
|
break
|
||||||
}
|
}
|
||||||
c.instoffset = a.Offset
|
c.instoffset = a.Offset
|
||||||
if s.Type == obj.SCONST {
|
if s.Type == objabi.SCONST {
|
||||||
goto consize
|
goto consize
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -2508,7 +2509,7 @@ func (c *ctxtz) addrilreloc(sym *obj.LSym, add int64) *obj.Reloc {
|
||||||
rel.Siz = 4
|
rel.Siz = 4
|
||||||
rel.Sym = sym
|
rel.Sym = sym
|
||||||
rel.Add = add + offset + int64(rel.Siz)
|
rel.Add = add + offset + int64(rel.Siz)
|
||||||
rel.Type = obj.R_PCRELDBL
|
rel.Type = objabi.R_PCRELDBL
|
||||||
return rel
|
return rel
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -2522,7 +2523,7 @@ func (c *ctxtz) addrilrelocoffset(sym *obj.LSym, add, offset int64) *obj.Reloc {
|
||||||
rel.Siz = 4
|
rel.Siz = 4
|
||||||
rel.Sym = sym
|
rel.Sym = sym
|
||||||
rel.Add = add + offset + int64(rel.Siz)
|
rel.Add = add + offset + int64(rel.Siz)
|
||||||
rel.Type = obj.R_PCRELDBL
|
rel.Type = objabi.R_PCRELDBL
|
||||||
return rel
|
return rel
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -2538,7 +2539,7 @@ func (c *ctxtz) addcallreloc(sym *obj.LSym, add int64) *obj.Reloc {
|
||||||
rel.Siz = 4
|
rel.Siz = 4
|
||||||
rel.Sym = sym
|
rel.Sym = sym
|
||||||
rel.Add = add + offset + int64(rel.Siz)
|
rel.Add = add + offset + int64(rel.Siz)
|
||||||
rel.Type = obj.R_CALL
|
rel.Type = objabi.R_CALL
|
||||||
return rel
|
return rel
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -3716,7 +3717,7 @@ func (c *ctxtz) asmout(p *obj.Prog, asm *[]byte) {
|
||||||
rel.Off = int32(c.pc + 2)
|
rel.Off = int32(c.pc + 2)
|
||||||
rel.Siz = 4
|
rel.Siz = 4
|
||||||
rel.Sym = p.From.Sym
|
rel.Sym = p.From.Sym
|
||||||
rel.Type = obj.R_GOTPCREL
|
rel.Type = objabi.R_GOTPCREL
|
||||||
rel.Add = 2 + int64(rel.Siz)
|
rel.Add = 2 + int64(rel.Siz)
|
||||||
|
|
||||||
case 94: // TLS local exec model
|
case 94: // TLS local exec model
|
||||||
|
|
@ -3728,7 +3729,7 @@ func (c *ctxtz) asmout(p *obj.Prog, asm *[]byte) {
|
||||||
rel.Off = int32(c.pc + sizeRIL + sizeRXY + sizeRI)
|
rel.Off = int32(c.pc + sizeRIL + sizeRXY + sizeRI)
|
||||||
rel.Siz = 8
|
rel.Siz = 8
|
||||||
rel.Sym = p.From.Sym
|
rel.Sym = p.From.Sym
|
||||||
rel.Type = obj.R_TLS_LE
|
rel.Type = objabi.R_TLS_LE
|
||||||
rel.Add = 0
|
rel.Add = 0
|
||||||
|
|
||||||
case 95: // TLS initial exec model
|
case 95: // TLS initial exec model
|
||||||
|
|
@ -3748,7 +3749,7 @@ func (c *ctxtz) asmout(p *obj.Prog, asm *[]byte) {
|
||||||
ieent.Off = int32(c.pc + 2)
|
ieent.Off = int32(c.pc + 2)
|
||||||
ieent.Siz = 4
|
ieent.Siz = 4
|
||||||
ieent.Sym = p.From.Sym
|
ieent.Sym = p.From.Sym
|
||||||
ieent.Type = obj.R_TLS_IE
|
ieent.Type = objabi.R_TLS_IE
|
||||||
ieent.Add = 2 + int64(ieent.Siz)
|
ieent.Add = 2 + int64(ieent.Siz)
|
||||||
|
|
||||||
// R_390_TLS_LOAD
|
// R_390_TLS_LOAD
|
||||||
|
|
|
||||||
|
|
@ -31,6 +31,7 @@ package s390x
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"cmd/internal/obj"
|
"cmd/internal/obj"
|
||||||
|
"cmd/internal/objabi"
|
||||||
"cmd/internal/sys"
|
"cmd/internal/sys"
|
||||||
"math"
|
"math"
|
||||||
)
|
)
|
||||||
|
|
@ -159,7 +160,7 @@ func (c *ctxtz) rewriteToUseGot(p *obj.Prog) {
|
||||||
if p.As == obj.ATEXT || p.As == obj.AFUNCDATA || p.As == obj.ACALL || p.As == obj.ARET || p.As == obj.AJMP {
|
if p.As == obj.ATEXT || p.As == obj.AFUNCDATA || p.As == obj.ACALL || p.As == obj.ARET || p.As == obj.AJMP {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
if source.Sym.Type == obj.STLSBSS {
|
if source.Sym.Type == objabi.STLSBSS {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
if source.Type != obj.TYPE_MEM {
|
if source.Type != obj.TYPE_MEM {
|
||||||
|
|
@ -302,7 +303,7 @@ func preprocess(ctxt *obj.Link, cursym *obj.LSym, newprog obj.ProgAlloc) {
|
||||||
autosize += int32(c.ctxt.FixedFrameSize())
|
autosize += int32(c.ctxt.FixedFrameSize())
|
||||||
}
|
}
|
||||||
|
|
||||||
if p.Mark&LEAF != 0 && autosize < obj.StackSmall {
|
if p.Mark&LEAF != 0 && autosize < objabi.StackSmall {
|
||||||
// A leaf function with a small stack can be marked
|
// A leaf function with a small stack can be marked
|
||||||
// NOSPLIT, avoiding a stack check.
|
// NOSPLIT, avoiding a stack check.
|
||||||
p.From.Sym.Set(obj.AttrNoSplit, true)
|
p.From.Sym.Set(obj.AttrNoSplit, true)
|
||||||
|
|
@ -537,7 +538,7 @@ func (c *ctxtz) stacksplitPre(p *obj.Prog, framesize int32) (*obj.Prog, *obj.Pro
|
||||||
p.To.Reg = REG_R3
|
p.To.Reg = REG_R3
|
||||||
|
|
||||||
q = nil
|
q = nil
|
||||||
if framesize <= obj.StackSmall {
|
if framesize <= objabi.StackSmall {
|
||||||
// small stack: SP < stackguard
|
// small stack: SP < stackguard
|
||||||
// CMP stackguard, SP
|
// CMP stackguard, SP
|
||||||
|
|
||||||
|
|
@ -565,7 +566,7 @@ func (c *ctxtz) stacksplitPre(p *obj.Prog, framesize int32) (*obj.Prog, *obj.Pro
|
||||||
//p.As = ABGE
|
//p.As = ABGE
|
||||||
//p.To.Type = obj.TYPE_BRANCH
|
//p.To.Type = obj.TYPE_BRANCH
|
||||||
|
|
||||||
} else if framesize <= obj.StackBig {
|
} else if framesize <= objabi.StackBig {
|
||||||
// large stack: SP-framesize < stackguard-StackSmall
|
// large stack: SP-framesize < stackguard-StackSmall
|
||||||
// ADD $-(framesize-StackSmall), SP, R4
|
// ADD $-(framesize-StackSmall), SP, R4
|
||||||
// CMP stackguard, R4
|
// CMP stackguard, R4
|
||||||
|
|
@ -573,7 +574,7 @@ func (c *ctxtz) stacksplitPre(p *obj.Prog, framesize int32) (*obj.Prog, *obj.Pro
|
||||||
|
|
||||||
p.As = AADD
|
p.As = AADD
|
||||||
p.From.Type = obj.TYPE_CONST
|
p.From.Type = obj.TYPE_CONST
|
||||||
p.From.Offset = -(int64(framesize) - obj.StackSmall)
|
p.From.Offset = -(int64(framesize) - objabi.StackSmall)
|
||||||
p.Reg = REGSP
|
p.Reg = REGSP
|
||||||
p.To.Type = obj.TYPE_REG
|
p.To.Type = obj.TYPE_REG
|
||||||
p.To.Reg = REG_R4
|
p.To.Reg = REG_R4
|
||||||
|
|
@ -607,7 +608,7 @@ func (c *ctxtz) stacksplitPre(p *obj.Prog, framesize int32) (*obj.Prog, *obj.Pro
|
||||||
p.From.Type = obj.TYPE_REG
|
p.From.Type = obj.TYPE_REG
|
||||||
p.From.Reg = REG_R3
|
p.From.Reg = REG_R3
|
||||||
p.To.Type = obj.TYPE_CONST
|
p.To.Type = obj.TYPE_CONST
|
||||||
p.To.Offset = obj.StackPreempt
|
p.To.Offset = objabi.StackPreempt
|
||||||
|
|
||||||
p = obj.Appendp(p, c.newprog)
|
p = obj.Appendp(p, c.newprog)
|
||||||
q = p
|
q = p
|
||||||
|
|
@ -617,7 +618,7 @@ func (c *ctxtz) stacksplitPre(p *obj.Prog, framesize int32) (*obj.Prog, *obj.Pro
|
||||||
p = obj.Appendp(p, c.newprog)
|
p = obj.Appendp(p, c.newprog)
|
||||||
p.As = AADD
|
p.As = AADD
|
||||||
p.From.Type = obj.TYPE_CONST
|
p.From.Type = obj.TYPE_CONST
|
||||||
p.From.Offset = obj.StackGuard
|
p.From.Offset = objabi.StackGuard
|
||||||
p.Reg = REGSP
|
p.Reg = REGSP
|
||||||
p.To.Type = obj.TYPE_REG
|
p.To.Type = obj.TYPE_REG
|
||||||
p.To.Reg = REG_R4
|
p.To.Reg = REG_R4
|
||||||
|
|
@ -632,7 +633,7 @@ func (c *ctxtz) stacksplitPre(p *obj.Prog, framesize int32) (*obj.Prog, *obj.Pro
|
||||||
p = obj.Appendp(p, c.newprog)
|
p = obj.Appendp(p, c.newprog)
|
||||||
p.As = AMOVD
|
p.As = AMOVD
|
||||||
p.From.Type = obj.TYPE_CONST
|
p.From.Type = obj.TYPE_CONST
|
||||||
p.From.Offset = int64(framesize) + obj.StackGuard - obj.StackSmall
|
p.From.Offset = int64(framesize) + objabi.StackGuard - objabi.StackSmall
|
||||||
p.To.Type = obj.TYPE_REG
|
p.To.Type = obj.TYPE_REG
|
||||||
p.To.Reg = REGTMP
|
p.To.Reg = REGTMP
|
||||||
|
|
||||||
|
|
@ -659,7 +660,7 @@ func (c *ctxtz) stacksplitPost(p *obj.Prog, pPre *obj.Prog, pPreempt *obj.Prog,
|
||||||
pcdata.Pos = c.cursym.Func.Text.Pos
|
pcdata.Pos = c.cursym.Func.Text.Pos
|
||||||
pcdata.As = obj.APCDATA
|
pcdata.As = obj.APCDATA
|
||||||
pcdata.From.Type = obj.TYPE_CONST
|
pcdata.From.Type = obj.TYPE_CONST
|
||||||
pcdata.From.Offset = obj.PCDATA_StackMapIndex
|
pcdata.From.Offset = objabi.PCDATA_StackMapIndex
|
||||||
pcdata.To.Type = obj.TYPE_CONST
|
pcdata.To.Type = obj.TYPE_CONST
|
||||||
pcdata.To.Offset = -1 // pcdata starts at -1 at function entry
|
pcdata.To.Offset = -1 // pcdata starts at -1 at function entry
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -32,38 +32,25 @@
|
||||||
package obj
|
package obj
|
||||||
|
|
||||||
import (
|
import (
|
||||||
|
"cmd/internal/objabi"
|
||||||
"fmt"
|
"fmt"
|
||||||
"log"
|
"log"
|
||||||
"math"
|
"math"
|
||||||
"os"
|
|
||||||
"path/filepath"
|
|
||||||
)
|
)
|
||||||
|
|
||||||
// WorkingDir returns the current working directory
|
|
||||||
// (or "/???" if the directory cannot be identified),
|
|
||||||
// with "/" as separator.
|
|
||||||
func WorkingDir() string {
|
|
||||||
var path string
|
|
||||||
path, _ = os.Getwd()
|
|
||||||
if path == "" {
|
|
||||||
path = "/???"
|
|
||||||
}
|
|
||||||
return filepath.ToSlash(path)
|
|
||||||
}
|
|
||||||
|
|
||||||
func Linknew(arch *LinkArch) *Link {
|
func Linknew(arch *LinkArch) *Link {
|
||||||
ctxt := new(Link)
|
ctxt := new(Link)
|
||||||
ctxt.hash = make(map[SymVer]*LSym)
|
ctxt.hash = make(map[SymVer]*LSym)
|
||||||
ctxt.Arch = arch
|
ctxt.Arch = arch
|
||||||
ctxt.Pathname = WorkingDir()
|
ctxt.Pathname = objabi.WorkingDir()
|
||||||
|
|
||||||
ctxt.Headtype.Set(GOOS)
|
ctxt.Headtype.Set(objabi.GOOS)
|
||||||
if ctxt.Headtype < 0 {
|
if ctxt.Headtype < 0 {
|
||||||
log.Fatalf("unknown goos %s", GOOS)
|
log.Fatalf("unknown goos %s", objabi.GOOS)
|
||||||
}
|
}
|
||||||
|
|
||||||
ctxt.Flag_optimize = true
|
ctxt.Flag_optimize = true
|
||||||
ctxt.Framepointer_enabled = Framepointer_enabled(GOOS, arch.Name)
|
ctxt.Framepointer_enabled = objabi.Framepointer_enabled(objabi.GOOS, arch.Name)
|
||||||
return ctxt
|
return ctxt
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -6,58 +6,13 @@ package obj
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"bytes"
|
"bytes"
|
||||||
|
"cmd/internal/objabi"
|
||||||
"fmt"
|
"fmt"
|
||||||
"log"
|
|
||||||
"os"
|
|
||||||
"strings"
|
"strings"
|
||||||
"time"
|
|
||||||
)
|
)
|
||||||
|
|
||||||
const REG_NONE = 0
|
const REG_NONE = 0
|
||||||
|
|
||||||
var start time.Time
|
|
||||||
|
|
||||||
func Cputime() float64 {
|
|
||||||
if start.IsZero() {
|
|
||||||
start = time.Now()
|
|
||||||
}
|
|
||||||
return time.Since(start).Seconds()
|
|
||||||
}
|
|
||||||
|
|
||||||
func envOr(key, value string) string {
|
|
||||||
if x := os.Getenv(key); x != "" {
|
|
||||||
return x
|
|
||||||
}
|
|
||||||
return value
|
|
||||||
}
|
|
||||||
|
|
||||||
var (
|
|
||||||
GOROOT = envOr("GOROOT", defaultGOROOT)
|
|
||||||
GOARCH = envOr("GOARCH", defaultGOARCH)
|
|
||||||
GOOS = envOr("GOOS", defaultGOOS)
|
|
||||||
GO386 = envOr("GO386", defaultGO386)
|
|
||||||
GOARM = goarm()
|
|
||||||
Version = version
|
|
||||||
)
|
|
||||||
|
|
||||||
func goarm() int {
|
|
||||||
switch v := envOr("GOARM", defaultGOARM); v {
|
|
||||||
case "5":
|
|
||||||
return 5
|
|
||||||
case "6":
|
|
||||||
return 6
|
|
||||||
case "7":
|
|
||||||
return 7
|
|
||||||
}
|
|
||||||
// Fail here, rather than validate at multiple call sites.
|
|
||||||
log.Fatalf("Invalid GOARM value. Must be 5, 6, or 7.")
|
|
||||||
panic("unreachable")
|
|
||||||
}
|
|
||||||
|
|
||||||
func Getgoextlinkenabled() string {
|
|
||||||
return envOr("GO_EXTLINK_ENABLED", defaultGO_EXTLINK_ENABLED)
|
|
||||||
}
|
|
||||||
|
|
||||||
func (p *Prog) Line() string {
|
func (p *Prog) Line() string {
|
||||||
return p.Ctxt.OutermostPos(p.Pos).Format(false)
|
return p.Ctxt.OutermostPos(p.Pos).Format(false)
|
||||||
}
|
}
|
||||||
|
|
@ -240,7 +195,7 @@ func Dconv(p *Prog, a *Addr) string {
|
||||||
}
|
}
|
||||||
|
|
||||||
case TYPE_TEXTSIZE:
|
case TYPE_TEXTSIZE:
|
||||||
if a.Val.(int32) == ArgsSizeUnknown {
|
if a.Val.(int32) == objabi.ArgsSizeUnknown {
|
||||||
str = fmt.Sprintf("$%d", a.Offset)
|
str = fmt.Sprintf("$%d", a.Offset)
|
||||||
} else {
|
} else {
|
||||||
str = fmt.Sprintf("$%d-%d", a.Offset, a.Val.(int32))
|
str = fmt.Sprintf("$%d-%d", a.Offset, a.Val.(int32))
|
||||||
|
|
@ -263,7 +218,7 @@ func Dconv(p *Prog, a *Addr) string {
|
||||||
case TYPE_SHIFT:
|
case TYPE_SHIFT:
|
||||||
v := int(a.Offset)
|
v := int(a.Offset)
|
||||||
ops := "<<>>->@>"
|
ops := "<<>>->@>"
|
||||||
switch GOARCH {
|
switch objabi.GOARCH {
|
||||||
case "arm":
|
case "arm":
|
||||||
op := ops[((v>>5)&3)<<1:]
|
op := ops[((v>>5)&3)<<1:]
|
||||||
if v&(1<<4) != 0 {
|
if v&(1<<4) != 0 {
|
||||||
|
|
@ -278,7 +233,7 @@ func Dconv(p *Prog, a *Addr) string {
|
||||||
op := ops[((v>>22)&3)<<1:]
|
op := ops[((v>>22)&3)<<1:]
|
||||||
str = fmt.Sprintf("R%d%c%c%d", (v>>16)&31, op[0], op[1], (v>>10)&63)
|
str = fmt.Sprintf("R%d%c%c%d", (v>>16)&31, op[0], op[1], (v>>10)&63)
|
||||||
default:
|
default:
|
||||||
panic("TYPE_SHIFT is not supported on " + GOARCH)
|
panic("TYPE_SHIFT is not supported on " + objabi.GOARCH)
|
||||||
}
|
}
|
||||||
|
|
||||||
case TYPE_REGREG:
|
case TYPE_REGREG:
|
||||||
|
|
|
||||||
|
|
@ -32,6 +32,7 @@ package x86
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"cmd/internal/obj"
|
"cmd/internal/obj"
|
||||||
|
"cmd/internal/objabi"
|
||||||
"cmd/internal/sys"
|
"cmd/internal/sys"
|
||||||
"encoding/binary"
|
"encoding/binary"
|
||||||
"fmt"
|
"fmt"
|
||||||
|
|
@ -1844,7 +1845,7 @@ func span6(ctxt *obj.Link, s *obj.LSym, newprog obj.ProgAlloc) {
|
||||||
s.P = s.P[:0]
|
s.P = s.P[:0]
|
||||||
c = 0
|
c = 0
|
||||||
for p := s.Func.Text; p != nil; p = p.Link {
|
for p := s.Func.Text; p != nil; p = p.Link {
|
||||||
if ctxt.Headtype == obj.Hnacl && p.Isize > 0 {
|
if ctxt.Headtype == objabi.Hnacl && p.Isize > 0 {
|
||||||
|
|
||||||
// pad everything to avoid crossing 32-byte boundary
|
// pad everything to avoid crossing 32-byte boundary
|
||||||
if c>>5 != (c+int32(p.Isize)-1)>>5 {
|
if c>>5 != (c+int32(p.Isize)-1)>>5 {
|
||||||
|
|
@ -1939,7 +1940,7 @@ func span6(ctxt *obj.Link, s *obj.LSym, newprog obj.ProgAlloc) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if ctxt.Headtype == obj.Hnacl {
|
if ctxt.Headtype == objabi.Hnacl {
|
||||||
c = naclpad(ctxt, s, c, -c&31)
|
c = naclpad(ctxt, s, c, -c&31)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -1975,9 +1976,9 @@ func instinit(ctxt *obj.Link) {
|
||||||
}
|
}
|
||||||
|
|
||||||
switch ctxt.Headtype {
|
switch ctxt.Headtype {
|
||||||
case obj.Hplan9:
|
case objabi.Hplan9:
|
||||||
plan9privates = ctxt.Lookup("_privates", 0)
|
plan9privates = ctxt.Lookup("_privates", 0)
|
||||||
case obj.Hnacl:
|
case objabi.Hnacl:
|
||||||
deferreturn = ctxt.Lookup("runtime.deferreturn", 0)
|
deferreturn = ctxt.Lookup("runtime.deferreturn", 0)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -2121,7 +2122,7 @@ func instinit(ctxt *obj.Link) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
var isAndroid = (obj.GOOS == "android")
|
var isAndroid = (objabi.GOOS == "android")
|
||||||
|
|
||||||
func prefixof(ctxt *obj.Link, p *obj.Prog, a *obj.Addr) int {
|
func prefixof(ctxt *obj.Link, p *obj.Prog, a *obj.Addr) int {
|
||||||
if a.Reg < REG_CS && a.Index < REG_CS { // fast path
|
if a.Reg < REG_CS && a.Index < REG_CS { // fast path
|
||||||
|
|
@ -2159,11 +2160,11 @@ func prefixof(ctxt *obj.Link, p *obj.Prog, a *obj.Addr) int {
|
||||||
}
|
}
|
||||||
log.Fatalf("unknown TLS base register for %v", ctxt.Headtype)
|
log.Fatalf("unknown TLS base register for %v", ctxt.Headtype)
|
||||||
|
|
||||||
case obj.Hdarwin,
|
case objabi.Hdarwin,
|
||||||
obj.Hdragonfly,
|
objabi.Hdragonfly,
|
||||||
obj.Hfreebsd,
|
objabi.Hfreebsd,
|
||||||
obj.Hnetbsd,
|
objabi.Hnetbsd,
|
||||||
obj.Hopenbsd:
|
objabi.Hopenbsd:
|
||||||
return 0x65 // GS
|
return 0x65 // GS
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
@ -2172,7 +2173,7 @@ func prefixof(ctxt *obj.Link, p *obj.Prog, a *obj.Addr) int {
|
||||||
default:
|
default:
|
||||||
log.Fatalf("unknown TLS base register for %v", ctxt.Headtype)
|
log.Fatalf("unknown TLS base register for %v", ctxt.Headtype)
|
||||||
|
|
||||||
case obj.Hlinux:
|
case objabi.Hlinux:
|
||||||
if isAndroid {
|
if isAndroid {
|
||||||
return 0x64 // FS
|
return 0x64 // FS
|
||||||
}
|
}
|
||||||
|
|
@ -2183,14 +2184,14 @@ func prefixof(ctxt *obj.Link, p *obj.Prog, a *obj.Addr) int {
|
||||||
return 0x64 // FS
|
return 0x64 // FS
|
||||||
}
|
}
|
||||||
|
|
||||||
case obj.Hdragonfly,
|
case objabi.Hdragonfly,
|
||||||
obj.Hfreebsd,
|
objabi.Hfreebsd,
|
||||||
obj.Hnetbsd,
|
objabi.Hnetbsd,
|
||||||
obj.Hopenbsd,
|
objabi.Hopenbsd,
|
||||||
obj.Hsolaris:
|
objabi.Hsolaris:
|
||||||
return 0x64 // FS
|
return 0x64 // FS
|
||||||
|
|
||||||
case obj.Hdarwin:
|
case objabi.Hdarwin:
|
||||||
return 0x65 // GS
|
return 0x65 // GS
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
@ -2800,13 +2801,13 @@ func vaddr(ctxt *obj.Link, p *obj.Prog, a *obj.Addr, r *obj.Reloc) int64 {
|
||||||
|
|
||||||
if a.Name == obj.NAME_GOTREF {
|
if a.Name == obj.NAME_GOTREF {
|
||||||
r.Siz = 4
|
r.Siz = 4
|
||||||
r.Type = obj.R_GOTPCREL
|
r.Type = objabi.R_GOTPCREL
|
||||||
} else if isextern(s) || (ctxt.Arch.Family != sys.AMD64 && !ctxt.Flag_shared) {
|
} else if isextern(s) || (ctxt.Arch.Family != sys.AMD64 && !ctxt.Flag_shared) {
|
||||||
r.Siz = 4
|
r.Siz = 4
|
||||||
r.Type = obj.R_ADDR
|
r.Type = objabi.R_ADDR
|
||||||
} else {
|
} else {
|
||||||
r.Siz = 4
|
r.Siz = 4
|
||||||
r.Type = obj.R_PCREL
|
r.Type = objabi.R_PCREL
|
||||||
}
|
}
|
||||||
|
|
||||||
r.Off = -1 // caller must fill in
|
r.Off = -1 // caller must fill in
|
||||||
|
|
@ -2822,8 +2823,8 @@ func vaddr(ctxt *obj.Link, p *obj.Prog, a *obj.Addr, r *obj.Reloc) int64 {
|
||||||
log.Fatalf("reloc")
|
log.Fatalf("reloc")
|
||||||
}
|
}
|
||||||
|
|
||||||
if !ctxt.Flag_shared || isAndroid || ctxt.Headtype == obj.Hdarwin {
|
if !ctxt.Flag_shared || isAndroid || ctxt.Headtype == objabi.Hdarwin {
|
||||||
r.Type = obj.R_TLS_LE
|
r.Type = objabi.R_TLS_LE
|
||||||
r.Siz = 4
|
r.Siz = 4
|
||||||
r.Off = -1 // caller must fill in
|
r.Off = -1 // caller must fill in
|
||||||
r.Add = a.Offset
|
r.Add = a.Offset
|
||||||
|
|
@ -2992,7 +2993,7 @@ func (asmbuf *AsmBuf) asmandsz(ctxt *obj.Link, cursym *obj.LSym, p *obj.Prog, a
|
||||||
if REG_AX <= base && base <= REG_R15 {
|
if REG_AX <= base && base <= REG_R15 {
|
||||||
if a.Index == REG_TLS && !ctxt.Flag_shared {
|
if a.Index == REG_TLS && !ctxt.Flag_shared {
|
||||||
rel = obj.Reloc{}
|
rel = obj.Reloc{}
|
||||||
rel.Type = obj.R_TLS_LE
|
rel.Type = objabi.R_TLS_LE
|
||||||
rel.Siz = 4
|
rel.Siz = 4
|
||||||
rel.Sym = nil
|
rel.Sym = nil
|
||||||
rel.Add = int64(v)
|
rel.Add = int64(v)
|
||||||
|
|
@ -3625,7 +3626,7 @@ func (asmbuf *AsmBuf) doasm(ctxt *obj.Link, cursym *obj.LSym, p *obj.Prog) {
|
||||||
case Zcallindreg:
|
case Zcallindreg:
|
||||||
r = obj.Addrel(cursym)
|
r = obj.Addrel(cursym)
|
||||||
r.Off = int32(p.Pc)
|
r.Off = int32(p.Pc)
|
||||||
r.Type = obj.R_CALLIND
|
r.Type = objabi.R_CALLIND
|
||||||
r.Siz = 0
|
r.Siz = 0
|
||||||
fallthrough
|
fallthrough
|
||||||
|
|
||||||
|
|
@ -3786,7 +3787,7 @@ func (asmbuf *AsmBuf) doasm(ctxt *obj.Link, cursym *obj.LSym, p *obj.Prog) {
|
||||||
}
|
}
|
||||||
r = obj.Addrel(cursym)
|
r = obj.Addrel(cursym)
|
||||||
r.Off = int32(p.Pc + int64(asmbuf.Len()))
|
r.Off = int32(p.Pc + int64(asmbuf.Len()))
|
||||||
r.Type = obj.R_PCREL
|
r.Type = objabi.R_PCREL
|
||||||
r.Siz = 4
|
r.Siz = 4
|
||||||
r.Add = p.To.Offset
|
r.Add = p.To.Offset
|
||||||
asmbuf.PutInt32(0)
|
asmbuf.PutInt32(0)
|
||||||
|
|
@ -3796,9 +3797,9 @@ func (asmbuf *AsmBuf) doasm(ctxt *obj.Link, cursym *obj.LSym, p *obj.Prog) {
|
||||||
r = obj.Addrel(cursym)
|
r = obj.Addrel(cursym)
|
||||||
r.Off = int32(p.Pc + int64(asmbuf.Len()))
|
r.Off = int32(p.Pc + int64(asmbuf.Len()))
|
||||||
if ctxt.Arch.Family == sys.AMD64 {
|
if ctxt.Arch.Family == sys.AMD64 {
|
||||||
r.Type = obj.R_PCREL
|
r.Type = objabi.R_PCREL
|
||||||
} else {
|
} else {
|
||||||
r.Type = obj.R_ADDR
|
r.Type = objabi.R_ADDR
|
||||||
}
|
}
|
||||||
r.Siz = 4
|
r.Siz = 4
|
||||||
r.Add = p.To.Offset
|
r.Add = p.To.Offset
|
||||||
|
|
@ -3830,7 +3831,7 @@ func (asmbuf *AsmBuf) doasm(ctxt *obj.Link, cursym *obj.LSym, p *obj.Prog) {
|
||||||
r.Off = int32(p.Pc + int64(asmbuf.Len()))
|
r.Off = int32(p.Pc + int64(asmbuf.Len()))
|
||||||
r.Sym = p.To.Sym
|
r.Sym = p.To.Sym
|
||||||
r.Add = p.To.Offset
|
r.Add = p.To.Offset
|
||||||
r.Type = obj.R_CALL
|
r.Type = objabi.R_CALL
|
||||||
r.Siz = 4
|
r.Siz = 4
|
||||||
asmbuf.PutInt32(0)
|
asmbuf.PutInt32(0)
|
||||||
|
|
||||||
|
|
@ -3855,7 +3856,7 @@ func (asmbuf *AsmBuf) doasm(ctxt *obj.Link, cursym *obj.LSym, p *obj.Prog) {
|
||||||
r = obj.Addrel(cursym)
|
r = obj.Addrel(cursym)
|
||||||
r.Off = int32(p.Pc + int64(asmbuf.Len()))
|
r.Off = int32(p.Pc + int64(asmbuf.Len()))
|
||||||
r.Sym = p.To.Sym
|
r.Sym = p.To.Sym
|
||||||
r.Type = obj.R_PCREL
|
r.Type = objabi.R_PCREL
|
||||||
r.Siz = 4
|
r.Siz = 4
|
||||||
asmbuf.PutInt32(0)
|
asmbuf.PutInt32(0)
|
||||||
break
|
break
|
||||||
|
|
@ -4072,8 +4073,8 @@ func (asmbuf *AsmBuf) doasm(ctxt *obj.Link, cursym *obj.LSym, p *obj.Prog) {
|
||||||
default:
|
default:
|
||||||
log.Fatalf("unknown TLS base location for %v", ctxt.Headtype)
|
log.Fatalf("unknown TLS base location for %v", ctxt.Headtype)
|
||||||
|
|
||||||
case obj.Hlinux,
|
case objabi.Hlinux,
|
||||||
obj.Hnacl:
|
objabi.Hnacl:
|
||||||
if ctxt.Flag_shared {
|
if ctxt.Flag_shared {
|
||||||
// Note that this is not generating the same insns as the other cases.
|
// Note that this is not generating the same insns as the other cases.
|
||||||
// MOV TLS, dst
|
// MOV TLS, dst
|
||||||
|
|
@ -4090,7 +4091,7 @@ func (asmbuf *AsmBuf) doasm(ctxt *obj.Link, cursym *obj.LSym, p *obj.Prog) {
|
||||||
asmbuf.Put1(0xe8)
|
asmbuf.Put1(0xe8)
|
||||||
r = obj.Addrel(cursym)
|
r = obj.Addrel(cursym)
|
||||||
r.Off = int32(p.Pc + int64(asmbuf.Len()))
|
r.Off = int32(p.Pc + int64(asmbuf.Len()))
|
||||||
r.Type = obj.R_CALL
|
r.Type = objabi.R_CALL
|
||||||
r.Siz = 4
|
r.Siz = 4
|
||||||
r.Sym = ctxt.Lookup("__x86.get_pc_thunk."+strings.ToLower(rconv(int(dst))), 0)
|
r.Sym = ctxt.Lookup("__x86.get_pc_thunk."+strings.ToLower(rconv(int(dst))), 0)
|
||||||
asmbuf.PutInt32(0)
|
asmbuf.PutInt32(0)
|
||||||
|
|
@ -4098,7 +4099,7 @@ func (asmbuf *AsmBuf) doasm(ctxt *obj.Link, cursym *obj.LSym, p *obj.Prog) {
|
||||||
asmbuf.Put2(0x8B, byte(2<<6|reg[dst]|(reg[dst]<<3)))
|
asmbuf.Put2(0x8B, byte(2<<6|reg[dst]|(reg[dst]<<3)))
|
||||||
r = obj.Addrel(cursym)
|
r = obj.Addrel(cursym)
|
||||||
r.Off = int32(p.Pc + int64(asmbuf.Len()))
|
r.Off = int32(p.Pc + int64(asmbuf.Len()))
|
||||||
r.Type = obj.R_TLS_IE
|
r.Type = objabi.R_TLS_IE
|
||||||
r.Siz = 4
|
r.Siz = 4
|
||||||
r.Add = 2
|
r.Add = 2
|
||||||
asmbuf.PutInt32(0)
|
asmbuf.PutInt32(0)
|
||||||
|
|
@ -4115,7 +4116,7 @@ func (asmbuf *AsmBuf) doasm(ctxt *obj.Link, cursym *obj.LSym, p *obj.Prog) {
|
||||||
0x8B)
|
0x8B)
|
||||||
asmbuf.asmand(ctxt, cursym, p, &pp.From, &p.To)
|
asmbuf.asmand(ctxt, cursym, p, &pp.From, &p.To)
|
||||||
}
|
}
|
||||||
case obj.Hplan9:
|
case objabi.Hplan9:
|
||||||
pp.From = obj.Addr{}
|
pp.From = obj.Addr{}
|
||||||
pp.From.Type = obj.TYPE_MEM
|
pp.From.Type = obj.TYPE_MEM
|
||||||
pp.From.Name = obj.NAME_EXTERN
|
pp.From.Name = obj.NAME_EXTERN
|
||||||
|
|
@ -4125,7 +4126,7 @@ func (asmbuf *AsmBuf) doasm(ctxt *obj.Link, cursym *obj.LSym, p *obj.Prog) {
|
||||||
asmbuf.Put1(0x8B)
|
asmbuf.Put1(0x8B)
|
||||||
asmbuf.asmand(ctxt, cursym, p, &pp.From, &p.To)
|
asmbuf.asmand(ctxt, cursym, p, &pp.From, &p.To)
|
||||||
|
|
||||||
case obj.Hwindows:
|
case objabi.Hwindows:
|
||||||
// Windows TLS base is always 0x14(FS).
|
// Windows TLS base is always 0x14(FS).
|
||||||
pp.From = p.From
|
pp.From = p.From
|
||||||
|
|
||||||
|
|
@ -4145,7 +4146,7 @@ func (asmbuf *AsmBuf) doasm(ctxt *obj.Link, cursym *obj.LSym, p *obj.Prog) {
|
||||||
default:
|
default:
|
||||||
log.Fatalf("unknown TLS base location for %v", ctxt.Headtype)
|
log.Fatalf("unknown TLS base location for %v", ctxt.Headtype)
|
||||||
|
|
||||||
case obj.Hlinux:
|
case objabi.Hlinux:
|
||||||
if !ctxt.Flag_shared {
|
if !ctxt.Flag_shared {
|
||||||
log.Fatalf("unknown TLS base location for linux without -shared")
|
log.Fatalf("unknown TLS base location for linux without -shared")
|
||||||
}
|
}
|
||||||
|
|
@ -4163,12 +4164,12 @@ func (asmbuf *AsmBuf) doasm(ctxt *obj.Link, cursym *obj.LSym, p *obj.Prog) {
|
||||||
asmbuf.Put2(0x8B, byte(0x05|(reg[p.To.Reg]<<3)))
|
asmbuf.Put2(0x8B, byte(0x05|(reg[p.To.Reg]<<3)))
|
||||||
r = obj.Addrel(cursym)
|
r = obj.Addrel(cursym)
|
||||||
r.Off = int32(p.Pc + int64(asmbuf.Len()))
|
r.Off = int32(p.Pc + int64(asmbuf.Len()))
|
||||||
r.Type = obj.R_TLS_IE
|
r.Type = objabi.R_TLS_IE
|
||||||
r.Siz = 4
|
r.Siz = 4
|
||||||
r.Add = -4
|
r.Add = -4
|
||||||
asmbuf.PutInt32(0)
|
asmbuf.PutInt32(0)
|
||||||
|
|
||||||
case obj.Hplan9:
|
case objabi.Hplan9:
|
||||||
pp.From = obj.Addr{}
|
pp.From = obj.Addr{}
|
||||||
pp.From.Type = obj.TYPE_MEM
|
pp.From.Type = obj.TYPE_MEM
|
||||||
pp.From.Name = obj.NAME_EXTERN
|
pp.From.Name = obj.NAME_EXTERN
|
||||||
|
|
@ -4179,7 +4180,7 @@ func (asmbuf *AsmBuf) doasm(ctxt *obj.Link, cursym *obj.LSym, p *obj.Prog) {
|
||||||
asmbuf.Put1(0x8B)
|
asmbuf.Put1(0x8B)
|
||||||
asmbuf.asmand(ctxt, cursym, p, &pp.From, &p.To)
|
asmbuf.asmand(ctxt, cursym, p, &pp.From, &p.To)
|
||||||
|
|
||||||
case obj.Hsolaris: // TODO(rsc): Delete Hsolaris from list. Should not use this code. See progedit in obj6.c.
|
case objabi.Hsolaris: // TODO(rsc): Delete Hsolaris from list. Should not use this code. See progedit in obj6.c.
|
||||||
// TLS base is 0(FS).
|
// TLS base is 0(FS).
|
||||||
pp.From = p.From
|
pp.From = p.From
|
||||||
|
|
||||||
|
|
@ -4194,7 +4195,7 @@ func (asmbuf *AsmBuf) doasm(ctxt *obj.Link, cursym *obj.LSym, p *obj.Prog) {
|
||||||
0x8B)
|
0x8B)
|
||||||
asmbuf.asmand(ctxt, cursym, p, &pp.From, &p.To)
|
asmbuf.asmand(ctxt, cursym, p, &pp.From, &p.To)
|
||||||
|
|
||||||
case obj.Hwindows:
|
case objabi.Hwindows:
|
||||||
// Windows TLS base is always 0x28(GS).
|
// Windows TLS base is always 0x28(GS).
|
||||||
pp.From = p.From
|
pp.From = p.From
|
||||||
|
|
||||||
|
|
@ -4434,7 +4435,7 @@ func (asmbuf *AsmBuf) nacltrunc(ctxt *obj.Link, reg int) {
|
||||||
func (asmbuf *AsmBuf) asmins(ctxt *obj.Link, cursym *obj.LSym, p *obj.Prog) {
|
func (asmbuf *AsmBuf) asmins(ctxt *obj.Link, cursym *obj.LSym, p *obj.Prog) {
|
||||||
asmbuf.Reset()
|
asmbuf.Reset()
|
||||||
|
|
||||||
if ctxt.Headtype == obj.Hnacl && ctxt.Arch.Family == sys.I386 {
|
if ctxt.Headtype == objabi.Hnacl && ctxt.Arch.Family == sys.I386 {
|
||||||
switch p.As {
|
switch p.As {
|
||||||
case obj.ARET:
|
case obj.ARET:
|
||||||
asmbuf.Put(naclret8)
|
asmbuf.Put(naclret8)
|
||||||
|
|
@ -4452,7 +4453,7 @@ func (asmbuf *AsmBuf) asmins(ctxt *obj.Link, cursym *obj.LSym, p *obj.Prog) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if ctxt.Headtype == obj.Hnacl && ctxt.Arch.Family == sys.AMD64 {
|
if ctxt.Headtype == objabi.Hnacl && ctxt.Arch.Family == sys.AMD64 {
|
||||||
if p.As == AREP {
|
if p.As == AREP {
|
||||||
asmbuf.rep++
|
asmbuf.rep++
|
||||||
return
|
return
|
||||||
|
|
@ -4567,7 +4568,7 @@ func (asmbuf *AsmBuf) asmins(ctxt *obj.Link, cursym *obj.LSym, p *obj.Prog) {
|
||||||
if asmbuf.rexflag != 0 {
|
if asmbuf.rexflag != 0 {
|
||||||
r.Off++
|
r.Off++
|
||||||
}
|
}
|
||||||
if r.Type == obj.R_PCREL {
|
if r.Type == objabi.R_PCREL {
|
||||||
if ctxt.Arch.Family == sys.AMD64 || p.As == obj.AJMP || p.As == obj.ACALL {
|
if ctxt.Arch.Family == sys.AMD64 || p.As == obj.AJMP || p.As == obj.ACALL {
|
||||||
// PC-relative addressing is relative to the end of the instruction,
|
// PC-relative addressing is relative to the end of the instruction,
|
||||||
// but the relocations applied by the linker are relative to the end
|
// but the relocations applied by the linker are relative to the end
|
||||||
|
|
@ -4585,14 +4586,14 @@ func (asmbuf *AsmBuf) asmins(ctxt *obj.Link, cursym *obj.LSym, p *obj.Prog) {
|
||||||
r.Add += int64(r.Off) - p.Pc + int64(r.Siz)
|
r.Add += int64(r.Off) - p.Pc + int64(r.Siz)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if r.Type == obj.R_GOTPCREL && ctxt.Arch.Family == sys.I386 {
|
if r.Type == objabi.R_GOTPCREL && ctxt.Arch.Family == sys.I386 {
|
||||||
// On 386, R_GOTPCREL makes the same assumptions as R_PCREL.
|
// On 386, R_GOTPCREL makes the same assumptions as R_PCREL.
|
||||||
r.Add += int64(r.Off) - p.Pc + int64(r.Siz)
|
r.Add += int64(r.Off) - p.Pc + int64(r.Siz)
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
if ctxt.Arch.Family == sys.AMD64 && ctxt.Headtype == obj.Hnacl && p.As != ACMPL && p.As != ACMPQ && p.To.Type == obj.TYPE_REG {
|
if ctxt.Arch.Family == sys.AMD64 && ctxt.Headtype == objabi.Hnacl && p.As != ACMPL && p.As != ACMPQ && p.To.Type == obj.TYPE_REG {
|
||||||
switch p.To.Reg {
|
switch p.To.Reg {
|
||||||
case REG_SP:
|
case REG_SP:
|
||||||
asmbuf.Put(naclspfix)
|
asmbuf.Put(naclspfix)
|
||||||
|
|
|
||||||
|
|
@ -32,6 +32,7 @@ package x86
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"cmd/internal/obj"
|
"cmd/internal/obj"
|
||||||
|
"cmd/internal/objabi"
|
||||||
"cmd/internal/sys"
|
"cmd/internal/sys"
|
||||||
"math"
|
"math"
|
||||||
"strings"
|
"strings"
|
||||||
|
|
@ -50,10 +51,10 @@ func CanUse1InsnTLS(ctxt *obj.Link) bool {
|
||||||
|
|
||||||
if ctxt.Arch.Family == sys.I386 {
|
if ctxt.Arch.Family == sys.I386 {
|
||||||
switch ctxt.Headtype {
|
switch ctxt.Headtype {
|
||||||
case obj.Hlinux,
|
case objabi.Hlinux,
|
||||||
obj.Hnacl,
|
objabi.Hnacl,
|
||||||
obj.Hplan9,
|
objabi.Hplan9,
|
||||||
obj.Hwindows:
|
objabi.Hwindows:
|
||||||
return false
|
return false
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -61,9 +62,9 @@ func CanUse1InsnTLS(ctxt *obj.Link) bool {
|
||||||
}
|
}
|
||||||
|
|
||||||
switch ctxt.Headtype {
|
switch ctxt.Headtype {
|
||||||
case obj.Hplan9, obj.Hwindows:
|
case objabi.Hplan9, objabi.Hwindows:
|
||||||
return false
|
return false
|
||||||
case obj.Hlinux:
|
case objabi.Hlinux:
|
||||||
return !ctxt.Flag_shared
|
return !ctxt.Flag_shared
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -123,7 +124,7 @@ func progedit(ctxt *obj.Link, p *obj.Prog, newprog obj.ProgAlloc) {
|
||||||
// TODO(rsc): Remove the Hsolaris special case. It exists only to
|
// TODO(rsc): Remove the Hsolaris special case. It exists only to
|
||||||
// guarantee we are producing byte-identical binaries as before this code.
|
// guarantee we are producing byte-identical binaries as before this code.
|
||||||
// But it should be unnecessary.
|
// But it should be unnecessary.
|
||||||
if (p.As == AMOVQ || p.As == AMOVL) && p.From.Type == obj.TYPE_REG && p.From.Reg == REG_TLS && p.To.Type == obj.TYPE_REG && REG_AX <= p.To.Reg && p.To.Reg <= REG_R15 && ctxt.Headtype != obj.Hsolaris {
|
if (p.As == AMOVQ || p.As == AMOVL) && p.From.Type == obj.TYPE_REG && p.From.Reg == REG_TLS && p.To.Type == obj.TYPE_REG && REG_AX <= p.To.Reg && p.To.Reg <= REG_R15 && ctxt.Headtype != objabi.Hsolaris {
|
||||||
obj.Nopout(p)
|
obj.Nopout(p)
|
||||||
}
|
}
|
||||||
if p.From.Type == obj.TYPE_MEM && p.From.Index == REG_TLS && REG_AX <= p.From.Reg && p.From.Reg <= REG_R15 {
|
if p.From.Type == obj.TYPE_MEM && p.From.Index == REG_TLS && REG_AX <= p.From.Reg && p.From.Reg <= REG_R15 {
|
||||||
|
|
@ -161,7 +162,7 @@ func progedit(ctxt *obj.Link, p *obj.Prog, newprog obj.ProgAlloc) {
|
||||||
}
|
}
|
||||||
|
|
||||||
// TODO: Remove.
|
// TODO: Remove.
|
||||||
if ctxt.Headtype == obj.Hwindows && ctxt.Arch.Family == sys.AMD64 || ctxt.Headtype == obj.Hplan9 {
|
if ctxt.Headtype == objabi.Hwindows && ctxt.Arch.Family == sys.AMD64 || ctxt.Headtype == objabi.Hplan9 {
|
||||||
if p.From.Scale == 1 && p.From.Index == REG_TLS {
|
if p.From.Scale == 1 && p.From.Index == REG_TLS {
|
||||||
p.From.Scale = 2
|
p.From.Scale = 2
|
||||||
}
|
}
|
||||||
|
|
@ -199,7 +200,7 @@ func progedit(ctxt *obj.Link, p *obj.Prog, newprog obj.ProgAlloc) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if ctxt.Headtype == obj.Hnacl && ctxt.Arch.Family == sys.AMD64 {
|
if ctxt.Headtype == objabi.Hnacl && ctxt.Arch.Family == sys.AMD64 {
|
||||||
if p.From3 != nil {
|
if p.From3 != nil {
|
||||||
nacladdr(ctxt, p, p.From3)
|
nacladdr(ctxt, p, p.From3)
|
||||||
}
|
}
|
||||||
|
|
@ -496,7 +497,7 @@ func rewriteToPcrel(ctxt *obj.Link, p *obj.Prog, newprog obj.ProgAlloc) {
|
||||||
if a.Sym == nil || (a.Type != obj.TYPE_MEM && a.Type != obj.TYPE_ADDR) || a.Reg != 0 {
|
if a.Sym == nil || (a.Type != obj.TYPE_MEM && a.Type != obj.TYPE_ADDR) || a.Reg != 0 {
|
||||||
return false
|
return false
|
||||||
}
|
}
|
||||||
if a.Sym.Type == obj.STLSBSS {
|
if a.Sym.Type == objabi.STLSBSS {
|
||||||
return false
|
return false
|
||||||
}
|
}
|
||||||
return a.Name == obj.NAME_EXTERN || a.Name == obj.NAME_STATIC || a.Name == obj.NAME_GOTREF
|
return a.Name == obj.NAME_EXTERN || a.Name == obj.NAME_STATIC || a.Name == obj.NAME_GOTREF
|
||||||
|
|
@ -637,7 +638,7 @@ func preprocess(ctxt *obj.Link, cursym *obj.LSym, newprog obj.ProgAlloc) {
|
||||||
}
|
}
|
||||||
|
|
||||||
// TODO(rsc): Remove 'ctxt.Arch.Family == sys.AMD64 &&'.
|
// TODO(rsc): Remove 'ctxt.Arch.Family == sys.AMD64 &&'.
|
||||||
if ctxt.Arch.Family == sys.AMD64 && autoffset < obj.StackSmall && !p.From.Sym.NoSplit() {
|
if ctxt.Arch.Family == sys.AMD64 && autoffset < objabi.StackSmall && !p.From.Sym.NoSplit() {
|
||||||
leaf := true
|
leaf := true
|
||||||
LeafSearch:
|
LeafSearch:
|
||||||
for q := p; q != nil; q = q.Link {
|
for q := p; q != nil; q = q.Link {
|
||||||
|
|
@ -651,7 +652,7 @@ func preprocess(ctxt *obj.Link, cursym *obj.LSym, newprog obj.ProgAlloc) {
|
||||||
}
|
}
|
||||||
fallthrough
|
fallthrough
|
||||||
case obj.ADUFFCOPY, obj.ADUFFZERO:
|
case obj.ADUFFCOPY, obj.ADUFFZERO:
|
||||||
if autoffset >= obj.StackSmall-8 {
|
if autoffset >= objabi.StackSmall-8 {
|
||||||
leaf = false
|
leaf = false
|
||||||
break LeafSearch
|
break LeafSearch
|
||||||
}
|
}
|
||||||
|
|
@ -741,7 +742,7 @@ func preprocess(ctxt *obj.Link, cursym *obj.LSym, newprog obj.ProgAlloc) {
|
||||||
p.From.Offset = 4 * int64(ctxt.Arch.PtrSize) // g_panic
|
p.From.Offset = 4 * int64(ctxt.Arch.PtrSize) // g_panic
|
||||||
p.To.Type = obj.TYPE_REG
|
p.To.Type = obj.TYPE_REG
|
||||||
p.To.Reg = REG_BX
|
p.To.Reg = REG_BX
|
||||||
if ctxt.Headtype == obj.Hnacl && ctxt.Arch.Family == sys.AMD64 {
|
if ctxt.Headtype == objabi.Hnacl && ctxt.Arch.Family == sys.AMD64 {
|
||||||
p.As = AMOVL
|
p.As = AMOVL
|
||||||
p.From.Type = obj.TYPE_MEM
|
p.From.Type = obj.TYPE_MEM
|
||||||
p.From.Reg = REG_R15
|
p.From.Reg = REG_R15
|
||||||
|
|
@ -759,7 +760,7 @@ func preprocess(ctxt *obj.Link, cursym *obj.LSym, newprog obj.ProgAlloc) {
|
||||||
p.From.Reg = REG_BX
|
p.From.Reg = REG_BX
|
||||||
p.To.Type = obj.TYPE_REG
|
p.To.Type = obj.TYPE_REG
|
||||||
p.To.Reg = REG_BX
|
p.To.Reg = REG_BX
|
||||||
if ctxt.Headtype == obj.Hnacl || ctxt.Arch.Family == sys.I386 {
|
if ctxt.Headtype == objabi.Hnacl || ctxt.Arch.Family == sys.I386 {
|
||||||
p.As = ATESTL
|
p.As = ATESTL
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -786,7 +787,7 @@ func preprocess(ctxt *obj.Link, cursym *obj.LSym, newprog obj.ProgAlloc) {
|
||||||
p.From.Offset = int64(autoffset) + int64(ctxt.Arch.RegSize)
|
p.From.Offset = int64(autoffset) + int64(ctxt.Arch.RegSize)
|
||||||
p.To.Type = obj.TYPE_REG
|
p.To.Type = obj.TYPE_REG
|
||||||
p.To.Reg = REG_DI
|
p.To.Reg = REG_DI
|
||||||
if ctxt.Headtype == obj.Hnacl || ctxt.Arch.Family == sys.I386 {
|
if ctxt.Headtype == objabi.Hnacl || ctxt.Arch.Family == sys.I386 {
|
||||||
p.As = ALEAL
|
p.As = ALEAL
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -801,7 +802,7 @@ func preprocess(ctxt *obj.Link, cursym *obj.LSym, newprog obj.ProgAlloc) {
|
||||||
p.From.Offset = 0 // Panic.argp
|
p.From.Offset = 0 // Panic.argp
|
||||||
p.To.Type = obj.TYPE_REG
|
p.To.Type = obj.TYPE_REG
|
||||||
p.To.Reg = REG_DI
|
p.To.Reg = REG_DI
|
||||||
if ctxt.Headtype == obj.Hnacl && ctxt.Arch.Family == sys.AMD64 {
|
if ctxt.Headtype == objabi.Hnacl && ctxt.Arch.Family == sys.AMD64 {
|
||||||
p.As = ACMPL
|
p.As = ACMPL
|
||||||
p.From.Type = obj.TYPE_MEM
|
p.From.Type = obj.TYPE_MEM
|
||||||
p.From.Reg = REG_R15
|
p.From.Reg = REG_R15
|
||||||
|
|
@ -826,7 +827,7 @@ func preprocess(ctxt *obj.Link, cursym *obj.LSym, newprog obj.ProgAlloc) {
|
||||||
p.To.Type = obj.TYPE_MEM
|
p.To.Type = obj.TYPE_MEM
|
||||||
p.To.Reg = REG_BX
|
p.To.Reg = REG_BX
|
||||||
p.To.Offset = 0 // Panic.argp
|
p.To.Offset = 0 // Panic.argp
|
||||||
if ctxt.Headtype == obj.Hnacl && ctxt.Arch.Family == sys.AMD64 {
|
if ctxt.Headtype == objabi.Hnacl && ctxt.Arch.Family == sys.AMD64 {
|
||||||
p.As = AMOVL
|
p.As = AMOVL
|
||||||
p.To.Type = obj.TYPE_MEM
|
p.To.Type = obj.TYPE_MEM
|
||||||
p.To.Reg = REG_R15
|
p.To.Reg = REG_R15
|
||||||
|
|
@ -958,7 +959,7 @@ func isZeroArgRuntimeCall(s *obj.LSym) bool {
|
||||||
}
|
}
|
||||||
|
|
||||||
func indir_cx(ctxt *obj.Link, p *obj.Prog, a *obj.Addr) {
|
func indir_cx(ctxt *obj.Link, p *obj.Prog, a *obj.Addr) {
|
||||||
if ctxt.Headtype == obj.Hnacl && ctxt.Arch.Family == sys.AMD64 {
|
if ctxt.Headtype == objabi.Hnacl && ctxt.Arch.Family == sys.AMD64 {
|
||||||
a.Type = obj.TYPE_MEM
|
a.Type = obj.TYPE_MEM
|
||||||
a.Reg = REG_R15
|
a.Reg = REG_R15
|
||||||
a.Index = REG_CX
|
a.Index = REG_CX
|
||||||
|
|
@ -1009,7 +1010,7 @@ func stacksplit(ctxt *obj.Link, cursym *obj.LSym, p *obj.Prog, newprog obj.ProgA
|
||||||
mov := AMOVQ
|
mov := AMOVQ
|
||||||
sub := ASUBQ
|
sub := ASUBQ
|
||||||
|
|
||||||
if ctxt.Headtype == obj.Hnacl || ctxt.Arch.Family == sys.I386 {
|
if ctxt.Headtype == objabi.Hnacl || ctxt.Arch.Family == sys.I386 {
|
||||||
cmp = ACMPL
|
cmp = ACMPL
|
||||||
lea = ALEAL
|
lea = ALEAL
|
||||||
mov = AMOVL
|
mov = AMOVL
|
||||||
|
|
@ -1017,7 +1018,7 @@ func stacksplit(ctxt *obj.Link, cursym *obj.LSym, p *obj.Prog, newprog obj.ProgA
|
||||||
}
|
}
|
||||||
|
|
||||||
var q1 *obj.Prog
|
var q1 *obj.Prog
|
||||||
if framesize <= obj.StackSmall {
|
if framesize <= objabi.StackSmall {
|
||||||
// small stack: SP <= stackguard
|
// small stack: SP <= stackguard
|
||||||
// CMPQ SP, stackguard
|
// CMPQ SP, stackguard
|
||||||
p = obj.Appendp(p, newprog)
|
p = obj.Appendp(p, newprog)
|
||||||
|
|
@ -1030,7 +1031,7 @@ func stacksplit(ctxt *obj.Link, cursym *obj.LSym, p *obj.Prog, newprog obj.ProgA
|
||||||
if cursym.CFunc() {
|
if cursym.CFunc() {
|
||||||
p.To.Offset = 3 * int64(ctxt.Arch.PtrSize) // G.stackguard1
|
p.To.Offset = 3 * int64(ctxt.Arch.PtrSize) // G.stackguard1
|
||||||
}
|
}
|
||||||
} else if framesize <= obj.StackBig {
|
} else if framesize <= objabi.StackBig {
|
||||||
// large stack: SP-framesize <= stackguard-StackSmall
|
// large stack: SP-framesize <= stackguard-StackSmall
|
||||||
// LEAQ -xxx(SP), AX
|
// LEAQ -xxx(SP), AX
|
||||||
// CMPQ AX, stackguard
|
// CMPQ AX, stackguard
|
||||||
|
|
@ -1039,7 +1040,7 @@ func stacksplit(ctxt *obj.Link, cursym *obj.LSym, p *obj.Prog, newprog obj.ProgA
|
||||||
p.As = lea
|
p.As = lea
|
||||||
p.From.Type = obj.TYPE_MEM
|
p.From.Type = obj.TYPE_MEM
|
||||||
p.From.Reg = REG_SP
|
p.From.Reg = REG_SP
|
||||||
p.From.Offset = -(int64(framesize) - obj.StackSmall)
|
p.From.Offset = -(int64(framesize) - objabi.StackSmall)
|
||||||
p.To.Type = obj.TYPE_REG
|
p.To.Type = obj.TYPE_REG
|
||||||
p.To.Reg = REG_AX
|
p.To.Reg = REG_AX
|
||||||
|
|
||||||
|
|
@ -1084,9 +1085,9 @@ func stacksplit(ctxt *obj.Link, cursym *obj.LSym, p *obj.Prog, newprog obj.ProgA
|
||||||
p.From.Type = obj.TYPE_REG
|
p.From.Type = obj.TYPE_REG
|
||||||
p.From.Reg = REG_SI
|
p.From.Reg = REG_SI
|
||||||
p.To.Type = obj.TYPE_CONST
|
p.To.Type = obj.TYPE_CONST
|
||||||
p.To.Offset = obj.StackPreempt
|
p.To.Offset = objabi.StackPreempt
|
||||||
if ctxt.Arch.Family == sys.I386 {
|
if ctxt.Arch.Family == sys.I386 {
|
||||||
p.To.Offset = int64(uint32(obj.StackPreempt & (1<<32 - 1)))
|
p.To.Offset = int64(uint32(objabi.StackPreempt & (1<<32 - 1)))
|
||||||
}
|
}
|
||||||
|
|
||||||
p = obj.Appendp(p, newprog)
|
p = obj.Appendp(p, newprog)
|
||||||
|
|
@ -1098,7 +1099,7 @@ func stacksplit(ctxt *obj.Link, cursym *obj.LSym, p *obj.Prog, newprog obj.ProgA
|
||||||
p.As = lea
|
p.As = lea
|
||||||
p.From.Type = obj.TYPE_MEM
|
p.From.Type = obj.TYPE_MEM
|
||||||
p.From.Reg = REG_SP
|
p.From.Reg = REG_SP
|
||||||
p.From.Offset = obj.StackGuard
|
p.From.Offset = objabi.StackGuard
|
||||||
p.To.Type = obj.TYPE_REG
|
p.To.Type = obj.TYPE_REG
|
||||||
p.To.Reg = REG_AX
|
p.To.Reg = REG_AX
|
||||||
|
|
||||||
|
|
@ -1114,7 +1115,7 @@ func stacksplit(ctxt *obj.Link, cursym *obj.LSym, p *obj.Prog, newprog obj.ProgA
|
||||||
p.From.Type = obj.TYPE_REG
|
p.From.Type = obj.TYPE_REG
|
||||||
p.From.Reg = REG_AX
|
p.From.Reg = REG_AX
|
||||||
p.To.Type = obj.TYPE_CONST
|
p.To.Type = obj.TYPE_CONST
|
||||||
p.To.Offset = int64(framesize) + (obj.StackGuard - obj.StackSmall)
|
p.To.Offset = int64(framesize) + (objabi.StackGuard - objabi.StackSmall)
|
||||||
}
|
}
|
||||||
|
|
||||||
// common
|
// common
|
||||||
|
|
@ -1137,7 +1138,7 @@ func stacksplit(ctxt *obj.Link, cursym *obj.LSym, p *obj.Prog, newprog obj.ProgA
|
||||||
pcdata.Pos = cursym.Func.Text.Pos
|
pcdata.Pos = cursym.Func.Text.Pos
|
||||||
pcdata.As = obj.APCDATA
|
pcdata.As = obj.APCDATA
|
||||||
pcdata.From.Type = obj.TYPE_CONST
|
pcdata.From.Type = obj.TYPE_CONST
|
||||||
pcdata.From.Offset = obj.PCDATA_StackMapIndex
|
pcdata.From.Offset = objabi.PCDATA_StackMapIndex
|
||||||
pcdata.To.Type = obj.TYPE_CONST
|
pcdata.To.Type = obj.TYPE_CONST
|
||||||
pcdata.To.Offset = -1 // pcdata starts at -1 at function entry
|
pcdata.To.Offset = -1 // pcdata starts at -1 at function entry
|
||||||
|
|
||||||
|
|
|
||||||
37
src/cmd/internal/objabi/autotype.go
Normal file
37
src/cmd/internal/objabi/autotype.go
Normal file
|
|
@ -0,0 +1,37 @@
|
||||||
|
// Derived from Inferno utils/6l/l.h and related files.
|
||||||
|
// https://bitbucket.org/inferno-os/inferno-os/src/default/utils/6l/l.h
|
||||||
|
//
|
||||||
|
// Copyright © 1994-1999 Lucent Technologies Inc. All rights reserved.
|
||||||
|
// Portions Copyright © 1995-1997 C H Forsyth (forsyth@terzarima.net)
|
||||||
|
// Portions Copyright © 1997-1999 Vita Nuova Limited
|
||||||
|
// Portions Copyright © 2000-2007 Vita Nuova Holdings Limited (www.vitanuova.com)
|
||||||
|
// Portions Copyright © 2004,2006 Bruce Ellis
|
||||||
|
// Portions Copyright © 2005-2007 C H Forsyth (forsyth@terzarima.net)
|
||||||
|
// Revisions Copyright © 2000-2007 Lucent Technologies Inc. and others
|
||||||
|
// Portions Copyright © 2009 The Go Authors. All rights reserved.
|
||||||
|
//
|
||||||
|
// Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||||
|
// of this software and associated documentation files (the "Software"), to deal
|
||||||
|
// in the Software without restriction, including without limitation the rights
|
||||||
|
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||||
|
// copies of the Software, and to permit persons to whom the Software is
|
||||||
|
// furnished to do so, subject to the following conditions:
|
||||||
|
//
|
||||||
|
// The above copyright notice and this permission notice shall be included in
|
||||||
|
// all copies or substantial portions of the Software.
|
||||||
|
//
|
||||||
|
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||||
|
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||||
|
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||||
|
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||||
|
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||||
|
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||||
|
// THE SOFTWARE.
|
||||||
|
|
||||||
|
package objabi
|
||||||
|
|
||||||
|
// Auto.name
|
||||||
|
const (
|
||||||
|
A_AUTO = 1 + iota
|
||||||
|
A_PARAM
|
||||||
|
)
|
||||||
119
src/cmd/internal/objabi/doc.go
Normal file
119
src/cmd/internal/objabi/doc.go
Normal file
|
|
@ -0,0 +1,119 @@
|
||||||
|
// Copyright 2013 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.
|
||||||
|
|
||||||
|
// NOTE: There are *three* independent implementations of this object
|
||||||
|
// file format in the Go source tree:
|
||||||
|
//
|
||||||
|
// - cmd/internal/goobj/read.go (used by cmd/addr2line, cmd/nm, cmd/objdump, cmd/pprof)
|
||||||
|
// - cmd/internal/obj/objfile.go (used by cmd/asm and cmd/compile)
|
||||||
|
// - cmd/link/internal/objfile.go (used by cmd/link)
|
||||||
|
//
|
||||||
|
// When changing the object file format, remember to change all three.
|
||||||
|
|
||||||
|
// Originally, Go object files were Plan 9 object files, but no longer.
|
||||||
|
// Now they are more like standard object files, in that each symbol is defined
|
||||||
|
// by an associated memory image (bytes) and a list of relocations to apply
|
||||||
|
// during linking. We do not (yet?) use a standard file format, however.
|
||||||
|
// For now, the format is chosen to be as simple as possible to read and write.
|
||||||
|
// It may change for reasons of efficiency, or we may even switch to a
|
||||||
|
// standard file format if there are compelling benefits to doing so.
|
||||||
|
// See golang.org/s/go13linker for more background.
|
||||||
|
//
|
||||||
|
// The file format is:
|
||||||
|
//
|
||||||
|
// - magic header: "\x00\x00go19ld"
|
||||||
|
// - byte 1 - version number
|
||||||
|
// - sequence of strings giving dependencies (imported packages)
|
||||||
|
// - empty string (marks end of sequence)
|
||||||
|
// - sequence of symbol references used by the defined symbols
|
||||||
|
// - byte 0xff (marks end of sequence)
|
||||||
|
// - sequence of integer lengths:
|
||||||
|
// - total data length
|
||||||
|
// - total number of relocations
|
||||||
|
// - total number of pcdata
|
||||||
|
// - total number of automatics
|
||||||
|
// - total number of funcdata
|
||||||
|
// - total number of files
|
||||||
|
// - data, the content of the defined symbols
|
||||||
|
// - sequence of defined symbols
|
||||||
|
// - byte 0xff (marks end of sequence)
|
||||||
|
// - magic footer: "\xff\xffgo19ld"
|
||||||
|
//
|
||||||
|
// All integers are stored in a zigzag varint format.
|
||||||
|
// See golang.org/s/go12symtab for a definition.
|
||||||
|
//
|
||||||
|
// Data blocks and strings are both stored as an integer
|
||||||
|
// followed by that many bytes.
|
||||||
|
//
|
||||||
|
// A symbol reference is a string name followed by a version.
|
||||||
|
//
|
||||||
|
// A symbol points to other symbols using an index into the symbol
|
||||||
|
// reference sequence. Index 0 corresponds to a nil symbol pointer.
|
||||||
|
// In the symbol layout described below "symref index" stands for this
|
||||||
|
// index.
|
||||||
|
//
|
||||||
|
// Each symbol is laid out as the following fields:
|
||||||
|
//
|
||||||
|
// - byte 0xfe (sanity check for synchronization)
|
||||||
|
// - type [int]
|
||||||
|
// - name & version [symref index]
|
||||||
|
// - flags [int]
|
||||||
|
// 1<<0 dupok
|
||||||
|
// 1<<1 local
|
||||||
|
// 1<<2 add to typelink table
|
||||||
|
// - size [int]
|
||||||
|
// - gotype [symref index]
|
||||||
|
// - p [data block]
|
||||||
|
// - nr [int]
|
||||||
|
// - r [nr relocations, sorted by off]
|
||||||
|
//
|
||||||
|
// If type == STEXT, there are a few more fields:
|
||||||
|
//
|
||||||
|
// - args [int]
|
||||||
|
// - locals [int]
|
||||||
|
// - nosplit [int]
|
||||||
|
// - flags [int]
|
||||||
|
// 1<<0 leaf
|
||||||
|
// 1<<1 C function
|
||||||
|
// 1<<2 function may call reflect.Type.Method
|
||||||
|
// - nlocal [int]
|
||||||
|
// - local [nlocal automatics]
|
||||||
|
// - pcln [pcln table]
|
||||||
|
//
|
||||||
|
// Each relocation has the encoding:
|
||||||
|
//
|
||||||
|
// - off [int]
|
||||||
|
// - siz [int]
|
||||||
|
// - type [int]
|
||||||
|
// - add [int]
|
||||||
|
// - sym [symref index]
|
||||||
|
//
|
||||||
|
// Each local has the encoding:
|
||||||
|
//
|
||||||
|
// - asym [symref index]
|
||||||
|
// - offset [int]
|
||||||
|
// - type [int]
|
||||||
|
// - gotype [symref index]
|
||||||
|
//
|
||||||
|
// The pcln table has the encoding:
|
||||||
|
//
|
||||||
|
// - pcsp [data block]
|
||||||
|
// - pcfile [data block]
|
||||||
|
// - pcline [data block]
|
||||||
|
// - pcinline [data block]
|
||||||
|
// - npcdata [int]
|
||||||
|
// - pcdata [npcdata data blocks]
|
||||||
|
// - nfuncdata [int]
|
||||||
|
// - funcdata [nfuncdata symref index]
|
||||||
|
// - funcdatasym [nfuncdata ints]
|
||||||
|
// - nfile [int]
|
||||||
|
// - file [nfile symref index]
|
||||||
|
// - ninlinedcall [int]
|
||||||
|
// - inlinedcall [ninlinedcall int symref int symref]
|
||||||
|
//
|
||||||
|
// The file layout and meaning of type integers are architecture-independent.
|
||||||
|
//
|
||||||
|
// TODO(rsc): The file format is good for a first pass but needs work.
|
||||||
|
// - There are SymID in the object file that should really just be strings.
|
||||||
|
package objabi
|
||||||
|
|
@ -2,7 +2,7 @@
|
||||||
// Use of this source code is governed by a BSD-style
|
// Use of this source code is governed by a BSD-style
|
||||||
// license that can be found in the LICENSE file.
|
// license that can be found in the LICENSE file.
|
||||||
|
|
||||||
package obj
|
package objabi
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"flag"
|
"flag"
|
||||||
|
|
@ -2,7 +2,7 @@
|
||||||
// Use of this source code is governed by a BSD-style
|
// Use of this source code is governed by a BSD-style
|
||||||
// license that can be found in the LICENSE file.
|
// license that can be found in the LICENSE file.
|
||||||
|
|
||||||
package obj
|
package objabi
|
||||||
|
|
||||||
// This file defines the IDs for PCDATA and FUNCDATA instructions
|
// This file defines the IDs for PCDATA and FUNCDATA instructions
|
||||||
// in Go binaries.
|
// in Go binaries.
|
||||||
104
src/cmd/internal/objabi/head.go
Normal file
104
src/cmd/internal/objabi/head.go
Normal file
|
|
@ -0,0 +1,104 @@
|
||||||
|
// Derived from Inferno utils/6l/l.h and related files.
|
||||||
|
// https://bitbucket.org/inferno-os/inferno-os/src/default/utils/6l/l.h
|
||||||
|
//
|
||||||
|
// Copyright © 1994-1999 Lucent Technologies Inc. All rights reserved.
|
||||||
|
// Portions Copyright © 1995-1997 C H Forsyth (forsyth@terzarima.net)
|
||||||
|
// Portions Copyright © 1997-1999 Vita Nuova Limited
|
||||||
|
// Portions Copyright © 2000-2007 Vita Nuova Holdings Limited (www.vitanuova.com)
|
||||||
|
// Portions Copyright © 2004,2006 Bruce Ellis
|
||||||
|
// Portions Copyright © 2005-2007 C H Forsyth (forsyth@terzarima.net)
|
||||||
|
// Revisions Copyright © 2000-2007 Lucent Technologies Inc. and others
|
||||||
|
// Portions Copyright © 2009 The Go Authors. All rights reserved.
|
||||||
|
//
|
||||||
|
// Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||||
|
// of this software and associated documentation files (the "Software"), to deal
|
||||||
|
// in the Software without restriction, including without limitation the rights
|
||||||
|
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||||
|
// copies of the Software, and to permit persons to whom the Software is
|
||||||
|
// furnished to do so, subject to the following conditions:
|
||||||
|
//
|
||||||
|
// The above copyright notice and this permission notice shall be included in
|
||||||
|
// all copies or substantial portions of the Software.
|
||||||
|
//
|
||||||
|
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||||
|
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||||
|
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||||
|
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||||
|
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||||
|
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||||
|
// THE SOFTWARE.
|
||||||
|
|
||||||
|
package objabi
|
||||||
|
|
||||||
|
import "fmt"
|
||||||
|
|
||||||
|
// HeadType is the executable header type.
|
||||||
|
type HeadType uint8
|
||||||
|
|
||||||
|
const (
|
||||||
|
Hunknown HeadType = iota
|
||||||
|
Hdarwin
|
||||||
|
Hdragonfly
|
||||||
|
Hfreebsd
|
||||||
|
Hlinux
|
||||||
|
Hnacl
|
||||||
|
Hnetbsd
|
||||||
|
Hopenbsd
|
||||||
|
Hplan9
|
||||||
|
Hsolaris
|
||||||
|
Hwindows
|
||||||
|
)
|
||||||
|
|
||||||
|
func (h *HeadType) Set(s string) error {
|
||||||
|
switch s {
|
||||||
|
case "darwin":
|
||||||
|
*h = Hdarwin
|
||||||
|
case "dragonfly":
|
||||||
|
*h = Hdragonfly
|
||||||
|
case "freebsd":
|
||||||
|
*h = Hfreebsd
|
||||||
|
case "linux", "android":
|
||||||
|
*h = Hlinux
|
||||||
|
case "nacl":
|
||||||
|
*h = Hnacl
|
||||||
|
case "netbsd":
|
||||||
|
*h = Hnetbsd
|
||||||
|
case "openbsd":
|
||||||
|
*h = Hopenbsd
|
||||||
|
case "plan9":
|
||||||
|
*h = Hplan9
|
||||||
|
case "solaris":
|
||||||
|
*h = Hsolaris
|
||||||
|
case "windows":
|
||||||
|
*h = Hwindows
|
||||||
|
default:
|
||||||
|
return fmt.Errorf("invalid headtype: %q", s)
|
||||||
|
}
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
|
func (h *HeadType) String() string {
|
||||||
|
switch *h {
|
||||||
|
case Hdarwin:
|
||||||
|
return "darwin"
|
||||||
|
case Hdragonfly:
|
||||||
|
return "dragonfly"
|
||||||
|
case Hfreebsd:
|
||||||
|
return "freebsd"
|
||||||
|
case Hlinux:
|
||||||
|
return "linux"
|
||||||
|
case Hnacl:
|
||||||
|
return "nacl"
|
||||||
|
case Hnetbsd:
|
||||||
|
return "netbsd"
|
||||||
|
case Hopenbsd:
|
||||||
|
return "openbsd"
|
||||||
|
case Hplan9:
|
||||||
|
return "plan9"
|
||||||
|
case Hsolaris:
|
||||||
|
return "solaris"
|
||||||
|
case Hwindows:
|
||||||
|
return "windows"
|
||||||
|
}
|
||||||
|
return fmt.Sprintf("HeadType(%d)", *h)
|
||||||
|
}
|
||||||
82
src/cmd/internal/objabi/line.go
Normal file
82
src/cmd/internal/objabi/line.go
Normal file
|
|
@ -0,0 +1,82 @@
|
||||||
|
// Copyright 2009 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 objabi
|
||||||
|
|
||||||
|
import (
|
||||||
|
"os"
|
||||||
|
"path/filepath"
|
||||||
|
)
|
||||||
|
|
||||||
|
// WorkingDir returns the current working directory
|
||||||
|
// (or "/???" if the directory cannot be identified),
|
||||||
|
// with "/" as separator.
|
||||||
|
func WorkingDir() string {
|
||||||
|
var path string
|
||||||
|
path, _ = os.Getwd()
|
||||||
|
if path == "" {
|
||||||
|
path = "/???"
|
||||||
|
}
|
||||||
|
return filepath.ToSlash(path)
|
||||||
|
}
|
||||||
|
|
||||||
|
// AbsFile returns the absolute filename for file in the given directory.
|
||||||
|
// It also removes a leading pathPrefix, or else rewrites a leading $GOROOT
|
||||||
|
// prefix to the literal "$GOROOT".
|
||||||
|
// If the resulting path is the empty string, the result is "??".
|
||||||
|
func AbsFile(dir, file, pathPrefix string) string {
|
||||||
|
abs := file
|
||||||
|
if dir != "" && !filepath.IsAbs(file) {
|
||||||
|
abs = filepath.Join(dir, file)
|
||||||
|
}
|
||||||
|
|
||||||
|
if pathPrefix != "" && hasPathPrefix(abs, pathPrefix) {
|
||||||
|
if abs == pathPrefix {
|
||||||
|
abs = ""
|
||||||
|
} else {
|
||||||
|
abs = abs[len(pathPrefix)+1:]
|
||||||
|
}
|
||||||
|
} else if hasPathPrefix(abs, GOROOT) {
|
||||||
|
abs = "$GOROOT" + abs[len(GOROOT):]
|
||||||
|
}
|
||||||
|
if abs == "" {
|
||||||
|
abs = "??"
|
||||||
|
}
|
||||||
|
|
||||||
|
return filepath.Clean(abs)
|
||||||
|
}
|
||||||
|
|
||||||
|
// Does s have t as a path prefix?
|
||||||
|
// That is, does s == t or does s begin with t followed by a slash?
|
||||||
|
// For portability, we allow ASCII case folding, so that hasPathPrefix("a/b/c", "A/B") is true.
|
||||||
|
// Similarly, we allow slash folding, so that hasPathPrefix("a/b/c", "a\\b") is true.
|
||||||
|
// We do not allow full Unicode case folding, for fear of causing more confusion
|
||||||
|
// or harm than good. (For an example of the kinds of things that can go wrong,
|
||||||
|
// see http://article.gmane.org/gmane.linux.kernel/1853266.)
|
||||||
|
func hasPathPrefix(s string, t string) bool {
|
||||||
|
if len(t) > len(s) {
|
||||||
|
return false
|
||||||
|
}
|
||||||
|
var i int
|
||||||
|
for i = 0; i < len(t); i++ {
|
||||||
|
cs := int(s[i])
|
||||||
|
ct := int(t[i])
|
||||||
|
if 'A' <= cs && cs <= 'Z' {
|
||||||
|
cs += 'a' - 'A'
|
||||||
|
}
|
||||||
|
if 'A' <= ct && ct <= 'Z' {
|
||||||
|
ct += 'a' - 'A'
|
||||||
|
}
|
||||||
|
if cs == '\\' {
|
||||||
|
cs = '/'
|
||||||
|
}
|
||||||
|
if ct == '\\' {
|
||||||
|
ct = '/'
|
||||||
|
}
|
||||||
|
if cs != ct {
|
||||||
|
return false
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return i >= len(s) || s[i] == '/' || s[i] == '\\'
|
||||||
|
}
|
||||||
200
src/cmd/internal/objabi/reloctype.go
Normal file
200
src/cmd/internal/objabi/reloctype.go
Normal file
|
|
@ -0,0 +1,200 @@
|
||||||
|
// Derived from Inferno utils/6l/l.h and related files.
|
||||||
|
// https://bitbucket.org/inferno-os/inferno-os/src/default/utils/6l/l.h
|
||||||
|
//
|
||||||
|
// Copyright © 1994-1999 Lucent Technologies Inc. All rights reserved.
|
||||||
|
// Portions Copyright © 1995-1997 C H Forsyth (forsyth@terzarima.net)
|
||||||
|
// Portions Copyright © 1997-1999 Vita Nuova Limited
|
||||||
|
// Portions Copyright © 2000-2007 Vita Nuova Holdings Limited (www.vitanuova.com)
|
||||||
|
// Portions Copyright © 2004,2006 Bruce Ellis
|
||||||
|
// Portions Copyright © 2005-2007 C H Forsyth (forsyth@terzarima.net)
|
||||||
|
// Revisions Copyright © 2000-2007 Lucent Technologies Inc. and others
|
||||||
|
// Portions Copyright © 2009 The Go Authors. All rights reserved.
|
||||||
|
//
|
||||||
|
// Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||||
|
// of this software and associated documentation files (the "Software"), to deal
|
||||||
|
// in the Software without restriction, including without limitation the rights
|
||||||
|
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||||
|
// copies of the Software, and to permit persons to whom the Software is
|
||||||
|
// furnished to do so, subject to the following conditions:
|
||||||
|
//
|
||||||
|
// The above copyright notice and this permission notice shall be included in
|
||||||
|
// all copies or substantial portions of the Software.
|
||||||
|
//
|
||||||
|
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||||
|
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||||
|
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||||
|
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||||
|
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||||
|
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||||
|
// THE SOFTWARE.
|
||||||
|
|
||||||
|
package objabi
|
||||||
|
|
||||||
|
type RelocType int32
|
||||||
|
|
||||||
|
//go:generate stringer -type=RelocType
|
||||||
|
const (
|
||||||
|
R_ADDR RelocType = 1 + iota
|
||||||
|
// R_ADDRPOWER relocates a pair of "D-form" instructions (instructions with 16-bit
|
||||||
|
// immediates in the low half of the instruction word), usually addis followed by
|
||||||
|
// another add or a load, inserting the "high adjusted" 16 bits of the address of
|
||||||
|
// the referenced symbol into the immediate field of the first instruction and the
|
||||||
|
// low 16 bits into that of the second instruction.
|
||||||
|
R_ADDRPOWER
|
||||||
|
// R_ADDRARM64 relocates an adrp, add pair to compute the address of the
|
||||||
|
// referenced symbol.
|
||||||
|
R_ADDRARM64
|
||||||
|
// R_ADDRMIPS (only used on mips/mips64) resolves to the low 16 bits of an external
|
||||||
|
// address, by encoding it into the instruction.
|
||||||
|
R_ADDRMIPS
|
||||||
|
// R_ADDROFF resolves to a 32-bit offset from the beginning of the section
|
||||||
|
// holding the data being relocated to the referenced symbol.
|
||||||
|
R_ADDROFF
|
||||||
|
// R_WEAKADDROFF resolves just like R_ADDROFF but is a weak relocation.
|
||||||
|
// A weak relocation does not make the symbol it refers to reachable,
|
||||||
|
// and is only honored by the linker if the symbol is in some other way
|
||||||
|
// reachable.
|
||||||
|
R_WEAKADDROFF
|
||||||
|
R_SIZE
|
||||||
|
R_CALL
|
||||||
|
R_CALLARM
|
||||||
|
R_CALLARM64
|
||||||
|
R_CALLIND
|
||||||
|
R_CALLPOWER
|
||||||
|
// R_CALLMIPS (only used on mips64) resolves to non-PC-relative target address
|
||||||
|
// of a CALL (JAL) instruction, by encoding the address into the instruction.
|
||||||
|
R_CALLMIPS
|
||||||
|
R_CONST
|
||||||
|
R_PCREL
|
||||||
|
// R_TLS_LE, used on 386, amd64, and ARM, resolves to the offset of the
|
||||||
|
// thread-local symbol from the thread local base and is used to implement the
|
||||||
|
// "local exec" model for tls access (r.Sym is not set on intel platforms but is
|
||||||
|
// set to a TLS symbol -- runtime.tlsg -- in the linker when externally linking).
|
||||||
|
R_TLS_LE
|
||||||
|
// R_TLS_IE, used 386, amd64, and ARM resolves to the PC-relative offset to a GOT
|
||||||
|
// slot containing the offset from the thread-local symbol from the thread local
|
||||||
|
// base and is used to implemented the "initial exec" model for tls access (r.Sym
|
||||||
|
// is not set on intel platforms but is set to a TLS symbol -- runtime.tlsg -- in
|
||||||
|
// the linker when externally linking).
|
||||||
|
R_TLS_IE
|
||||||
|
R_GOTOFF
|
||||||
|
R_PLT0
|
||||||
|
R_PLT1
|
||||||
|
R_PLT2
|
||||||
|
R_USEFIELD
|
||||||
|
// R_USETYPE resolves to an *rtype, but no relocation is created. The
|
||||||
|
// linker uses this as a signal that the pointed-to type information
|
||||||
|
// should be linked into the final binary, even if there are no other
|
||||||
|
// direct references. (This is used for types reachable by reflection.)
|
||||||
|
R_USETYPE
|
||||||
|
// R_METHODOFF resolves to a 32-bit offset from the beginning of the section
|
||||||
|
// holding the data being relocated to the referenced symbol.
|
||||||
|
// It is a variant of R_ADDROFF used when linking from the uncommonType of a
|
||||||
|
// *rtype, and may be set to zero by the linker if it determines the method
|
||||||
|
// text is unreachable by the linked program.
|
||||||
|
R_METHODOFF
|
||||||
|
R_POWER_TOC
|
||||||
|
R_GOTPCREL
|
||||||
|
// R_JMPMIPS (only used on mips64) resolves to non-PC-relative target address
|
||||||
|
// of a JMP instruction, by encoding the address into the instruction.
|
||||||
|
// The stack nosplit check ignores this since it is not a function call.
|
||||||
|
R_JMPMIPS
|
||||||
|
// R_DWARFREF resolves to the offset of the symbol from its section.
|
||||||
|
R_DWARFREF
|
||||||
|
|
||||||
|
// Platform dependent relocations. Architectures with fixed width instructions
|
||||||
|
// have the inherent issue that a 32-bit (or 64-bit!) displacement cannot be
|
||||||
|
// stuffed into a 32-bit instruction, so an address needs to be spread across
|
||||||
|
// several instructions, and in turn this requires a sequence of relocations, each
|
||||||
|
// updating a part of an instruction. This leads to relocation codes that are
|
||||||
|
// inherently processor specific.
|
||||||
|
|
||||||
|
// Arm64.
|
||||||
|
|
||||||
|
// Set a MOV[NZ] immediate field to bits [15:0] of the offset from the thread
|
||||||
|
// local base to the thread local variable defined by the referenced (thread
|
||||||
|
// local) symbol. Error if the offset does not fit into 16 bits.
|
||||||
|
R_ARM64_TLS_LE
|
||||||
|
|
||||||
|
// Relocates an ADRP; LD64 instruction sequence to load the offset between
|
||||||
|
// the thread local base and the thread local variable defined by the
|
||||||
|
// referenced (thread local) symbol from the GOT.
|
||||||
|
R_ARM64_TLS_IE
|
||||||
|
|
||||||
|
// R_ARM64_GOTPCREL relocates an adrp, ld64 pair to compute the address of the GOT
|
||||||
|
// slot of the referenced symbol.
|
||||||
|
R_ARM64_GOTPCREL
|
||||||
|
|
||||||
|
// PPC64.
|
||||||
|
|
||||||
|
// R_POWER_TLS_LE is used to implement the "local exec" model for tls
|
||||||
|
// access. It resolves to the offset of the thread-local symbol from the
|
||||||
|
// thread pointer (R13) and inserts this value into the low 16 bits of an
|
||||||
|
// instruction word.
|
||||||
|
R_POWER_TLS_LE
|
||||||
|
|
||||||
|
// R_POWER_TLS_IE is used to implement the "initial exec" model for tls access. It
|
||||||
|
// relocates a D-form, DS-form instruction sequence like R_ADDRPOWER_DS. It
|
||||||
|
// inserts to the offset of GOT slot for the thread-local symbol from the TOC (the
|
||||||
|
// GOT slot is filled by the dynamic linker with the offset of the thread-local
|
||||||
|
// symbol from the thread pointer (R13)).
|
||||||
|
R_POWER_TLS_IE
|
||||||
|
|
||||||
|
// R_POWER_TLS marks an X-form instruction such as "MOVD 0(R13)(R31*1), g" as
|
||||||
|
// accessing a particular thread-local symbol. It does not affect code generation
|
||||||
|
// but is used by the system linker when relaxing "initial exec" model code to
|
||||||
|
// "local exec" model code.
|
||||||
|
R_POWER_TLS
|
||||||
|
|
||||||
|
// R_ADDRPOWER_DS is similar to R_ADDRPOWER above, but assumes the second
|
||||||
|
// instruction is a "DS-form" instruction, which has an immediate field occupying
|
||||||
|
// bits [15:2] of the instruction word. Bits [15:2] of the address of the
|
||||||
|
// relocated symbol are inserted into this field; it is an error if the last two
|
||||||
|
// bits of the address are not 0.
|
||||||
|
R_ADDRPOWER_DS
|
||||||
|
|
||||||
|
// R_ADDRPOWER_PCREL relocates a D-form, DS-form instruction sequence like
|
||||||
|
// R_ADDRPOWER_DS but inserts the offset of the GOT slot for the referenced symbol
|
||||||
|
// from the TOC rather than the symbol's address.
|
||||||
|
R_ADDRPOWER_GOT
|
||||||
|
|
||||||
|
// R_ADDRPOWER_PCREL relocates two D-form instructions like R_ADDRPOWER, but
|
||||||
|
// inserts the displacement from the place being relocated to the address of the
|
||||||
|
// the relocated symbol instead of just its address.
|
||||||
|
R_ADDRPOWER_PCREL
|
||||||
|
|
||||||
|
// R_ADDRPOWER_TOCREL relocates two D-form instructions like R_ADDRPOWER, but
|
||||||
|
// inserts the offset from the TOC to the address of the relocated symbol
|
||||||
|
// rather than the symbol's address.
|
||||||
|
R_ADDRPOWER_TOCREL
|
||||||
|
|
||||||
|
// R_ADDRPOWER_TOCREL relocates a D-form, DS-form instruction sequence like
|
||||||
|
// R_ADDRPOWER_DS but inserts the offset from the TOC to the address of the the
|
||||||
|
// relocated symbol rather than the symbol's address.
|
||||||
|
R_ADDRPOWER_TOCREL_DS
|
||||||
|
|
||||||
|
// R_PCRELDBL relocates s390x 2-byte aligned PC-relative addresses.
|
||||||
|
// TODO(mundaym): remove once variants can be serialized - see issue 14218.
|
||||||
|
R_PCRELDBL
|
||||||
|
|
||||||
|
// R_ADDRMIPSU (only used on mips/mips64) resolves to the sign-adjusted "upper" 16
|
||||||
|
// bits (bit 16-31) of an external address, by encoding it into the instruction.
|
||||||
|
R_ADDRMIPSU
|
||||||
|
// R_ADDRMIPSTLS (only used on mips64) resolves to the low 16 bits of a TLS
|
||||||
|
// address (offset from thread pointer), by encoding it into the instruction.
|
||||||
|
R_ADDRMIPSTLS
|
||||||
|
)
|
||||||
|
|
||||||
|
// IsDirectJump returns whether r is a relocation for a direct jump.
|
||||||
|
// A direct jump is a CALL or JMP instruction that takes the target address
|
||||||
|
// as immediate. The address is embedded into the instruction, possibly
|
||||||
|
// with limited width.
|
||||||
|
// An indirect jump is a CALL or JMP instruction that takes the target address
|
||||||
|
// in register or memory.
|
||||||
|
func (r RelocType) IsDirectJump() bool {
|
||||||
|
switch r {
|
||||||
|
case R_CALL, R_CALLARM, R_CALLARM64, R_CALLPOWER, R_CALLMIPS, R_JMPMIPS:
|
||||||
|
return true
|
||||||
|
}
|
||||||
|
return false
|
||||||
|
}
|
||||||
|
|
@ -1,6 +1,6 @@
|
||||||
// Code generated by "stringer -type=RelocType"; DO NOT EDIT
|
// Code generated by "stringer -type=RelocType"; DO NOT EDIT.
|
||||||
|
|
||||||
package obj
|
package objabi
|
||||||
|
|
||||||
import "fmt"
|
import "fmt"
|
||||||
|
|
||||||
|
|
@ -2,10 +2,9 @@
|
||||||
// Use of this source code is governed by a BSD-style
|
// Use of this source code is governed by a BSD-style
|
||||||
// license that can be found in the LICENSE file.
|
// license that can be found in the LICENSE file.
|
||||||
|
|
||||||
package obj
|
package objabi
|
||||||
|
|
||||||
// For the linkers. Must match Go definitions.
|
// For the linkers. Must match Go definitions.
|
||||||
// TODO(rsc): Share Go definitions with linkers directly.
|
|
||||||
|
|
||||||
const (
|
const (
|
||||||
STACKSYSTEM = 0
|
STACKSYSTEM = 0
|
||||||
137
src/cmd/internal/objabi/symkind.go
Normal file
137
src/cmd/internal/objabi/symkind.go
Normal file
|
|
@ -0,0 +1,137 @@
|
||||||
|
// Derived from Inferno utils/6l/l.h and related files.
|
||||||
|
// https://bitbucket.org/inferno-os/inferno-os/src/default/utils/6l/l.h
|
||||||
|
//
|
||||||
|
// Copyright © 1994-1999 Lucent Technologies Inc. All rights reserved.
|
||||||
|
// Portions Copyright © 1995-1997 C H Forsyth (forsyth@terzarima.net)
|
||||||
|
// Portions Copyright © 1997-1999 Vita Nuova Limited
|
||||||
|
// Portions Copyright © 2000-2007 Vita Nuova Holdings Limited (www.vitanuova.com)
|
||||||
|
// Portions Copyright © 2004,2006 Bruce Ellis
|
||||||
|
// Portions Copyright © 2005-2007 C H Forsyth (forsyth@terzarima.net)
|
||||||
|
// Revisions Copyright © 2000-2007 Lucent Technologies Inc. and others
|
||||||
|
// Portions Copyright © 2009 The Go Authors. All rights reserved.
|
||||||
|
//
|
||||||
|
// Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||||
|
// of this software and associated documentation files (the "Software"), to deal
|
||||||
|
// in the Software without restriction, including without limitation the rights
|
||||||
|
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||||
|
// copies of the Software, and to permit persons to whom the Software is
|
||||||
|
// furnished to do so, subject to the following conditions:
|
||||||
|
//
|
||||||
|
// The above copyright notice and this permission notice shall be included in
|
||||||
|
// all copies or substantial portions of the Software.
|
||||||
|
//
|
||||||
|
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||||
|
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||||
|
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||||
|
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||||
|
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||||
|
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||||
|
// THE SOFTWARE.
|
||||||
|
|
||||||
|
package objabi
|
||||||
|
|
||||||
|
// A SymKind describes the kind of memory represented by a symbol.
|
||||||
|
type SymKind int16
|
||||||
|
|
||||||
|
// Defined SymKind values.
|
||||||
|
//
|
||||||
|
// TODO(rsc): Give idiomatic Go names.
|
||||||
|
// TODO(rsc): Reduce the number of symbol types in the object files.
|
||||||
|
//go:generate stringer -type=SymKind
|
||||||
|
const (
|
||||||
|
Sxxx SymKind = iota
|
||||||
|
STEXT
|
||||||
|
SELFRXSECT
|
||||||
|
|
||||||
|
// Read-only sections.
|
||||||
|
STYPE
|
||||||
|
SSTRING
|
||||||
|
SGOSTRING
|
||||||
|
SGOFUNC
|
||||||
|
SGCBITS
|
||||||
|
SRODATA
|
||||||
|
SFUNCTAB
|
||||||
|
|
||||||
|
SELFROSECT
|
||||||
|
SMACHOPLT
|
||||||
|
|
||||||
|
// Read-only sections with relocations.
|
||||||
|
//
|
||||||
|
// Types STYPE-SFUNCTAB above are written to the .rodata section by default.
|
||||||
|
// When linking a shared object, some conceptually "read only" types need to
|
||||||
|
// be written to by relocations and putting them in a section called
|
||||||
|
// ".rodata" interacts poorly with the system linkers. The GNU linkers
|
||||||
|
// support this situation by arranging for sections of the name
|
||||||
|
// ".data.rel.ro.XXX" to be mprotected read only by the dynamic linker after
|
||||||
|
// relocations have applied, so when the Go linker is creating a shared
|
||||||
|
// object it checks all objects of the above types and bumps any object that
|
||||||
|
// has a relocation to it to the corresponding type below, which are then
|
||||||
|
// written to sections with appropriate magic names.
|
||||||
|
STYPERELRO
|
||||||
|
SSTRINGRELRO
|
||||||
|
SGOSTRINGRELRO
|
||||||
|
SGOFUNCRELRO
|
||||||
|
SGCBITSRELRO
|
||||||
|
SRODATARELRO
|
||||||
|
SFUNCTABRELRO
|
||||||
|
|
||||||
|
// Part of .data.rel.ro if it exists, otherwise part of .rodata.
|
||||||
|
STYPELINK
|
||||||
|
SITABLINK
|
||||||
|
SSYMTAB
|
||||||
|
SPCLNTAB
|
||||||
|
|
||||||
|
// Writable sections.
|
||||||
|
SELFSECT
|
||||||
|
SMACHO
|
||||||
|
SMACHOGOT
|
||||||
|
SWINDOWS
|
||||||
|
SELFGOT
|
||||||
|
SNOPTRDATA
|
||||||
|
SINITARR
|
||||||
|
SDATA
|
||||||
|
SBSS
|
||||||
|
SNOPTRBSS
|
||||||
|
STLSBSS
|
||||||
|
SXREF
|
||||||
|
SMACHOSYMSTR
|
||||||
|
SMACHOSYMTAB
|
||||||
|
SMACHOINDIRECTPLT
|
||||||
|
SMACHOINDIRECTGOT
|
||||||
|
SFILE
|
||||||
|
SFILEPATH
|
||||||
|
SCONST
|
||||||
|
SDYNIMPORT
|
||||||
|
SHOSTOBJ
|
||||||
|
SDWARFSECT
|
||||||
|
SDWARFINFO
|
||||||
|
SSUB = SymKind(1 << 8)
|
||||||
|
SMASK = SymKind(SSUB - 1)
|
||||||
|
SHIDDEN = SymKind(1 << 9)
|
||||||
|
SCONTAINER = SymKind(1 << 10) // has a sub-symbol
|
||||||
|
)
|
||||||
|
|
||||||
|
// ReadOnly are the symbol kinds that form read-only sections. In some
|
||||||
|
// cases, if they will require relocations, they are transformed into
|
||||||
|
// rel-ro sections using RelROMap.
|
||||||
|
var ReadOnly = []SymKind{
|
||||||
|
STYPE,
|
||||||
|
SSTRING,
|
||||||
|
SGOSTRING,
|
||||||
|
SGOFUNC,
|
||||||
|
SGCBITS,
|
||||||
|
SRODATA,
|
||||||
|
SFUNCTAB,
|
||||||
|
}
|
||||||
|
|
||||||
|
// RelROMap describes the transformation of read-only symbols to rel-ro
|
||||||
|
// symbols.
|
||||||
|
var RelROMap = map[SymKind]SymKind{
|
||||||
|
STYPE: STYPERELRO,
|
||||||
|
SSTRING: SSTRINGRELRO,
|
||||||
|
SGOSTRING: SGOSTRINGRELRO,
|
||||||
|
SGOFUNC: SGOFUNCRELRO,
|
||||||
|
SGCBITS: SGCBITSRELRO,
|
||||||
|
SRODATA: SRODATARELRO,
|
||||||
|
SFUNCTAB: SFUNCTABRELRO,
|
||||||
|
}
|
||||||
|
|
@ -1,6 +1,6 @@
|
||||||
// Code generated by "stringer -type=SymKind"; DO NOT EDIT
|
// Code generated by "stringer -type=SymKind"; DO NOT EDIT.
|
||||||
|
|
||||||
package obj
|
package objabi
|
||||||
|
|
||||||
import "fmt"
|
import "fmt"
|
||||||
|
|
||||||
|
|
@ -2,7 +2,7 @@
|
||||||
// Use of this source code is governed by a BSD-style
|
// Use of this source code is governed by a BSD-style
|
||||||
// license that can be found in the LICENSE file.
|
// license that can be found in the LICENSE file.
|
||||||
|
|
||||||
package obj
|
package objabi
|
||||||
|
|
||||||
// Must match runtime and reflect.
|
// Must match runtime and reflect.
|
||||||
// Included by cmd/gc.
|
// Included by cmd/gc.
|
||||||
112
src/cmd/internal/objabi/util.go
Normal file
112
src/cmd/internal/objabi/util.go
Normal file
|
|
@ -0,0 +1,112 @@
|
||||||
|
// Copyright 2015 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 objabi
|
||||||
|
|
||||||
|
import (
|
||||||
|
"fmt"
|
||||||
|
"log"
|
||||||
|
"os"
|
||||||
|
"strings"
|
||||||
|
)
|
||||||
|
|
||||||
|
func envOr(key, value string) string {
|
||||||
|
if x := os.Getenv(key); x != "" {
|
||||||
|
return x
|
||||||
|
}
|
||||||
|
return value
|
||||||
|
}
|
||||||
|
|
||||||
|
var (
|
||||||
|
GOROOT = envOr("GOROOT", defaultGOROOT)
|
||||||
|
GOARCH = envOr("GOARCH", defaultGOARCH)
|
||||||
|
GOOS = envOr("GOOS", defaultGOOS)
|
||||||
|
GO386 = envOr("GO386", defaultGO386)
|
||||||
|
GOARM = goarm()
|
||||||
|
Version = version
|
||||||
|
)
|
||||||
|
|
||||||
|
func goarm() int {
|
||||||
|
switch v := envOr("GOARM", defaultGOARM); v {
|
||||||
|
case "5":
|
||||||
|
return 5
|
||||||
|
case "6":
|
||||||
|
return 6
|
||||||
|
case "7":
|
||||||
|
return 7
|
||||||
|
}
|
||||||
|
// Fail here, rather than validate at multiple call sites.
|
||||||
|
log.Fatalf("Invalid GOARM value. Must be 5, 6, or 7.")
|
||||||
|
panic("unreachable")
|
||||||
|
}
|
||||||
|
|
||||||
|
func Getgoextlinkenabled() string {
|
||||||
|
return envOr("GO_EXTLINK_ENABLED", defaultGO_EXTLINK_ENABLED)
|
||||||
|
}
|
||||||
|
|
||||||
|
func init() {
|
||||||
|
framepointer_enabled = 1 // default
|
||||||
|
for _, f := range strings.Split(goexperiment, ",") {
|
||||||
|
if f != "" {
|
||||||
|
addexp(f)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func Framepointer_enabled(goos, goarch string) bool {
|
||||||
|
return framepointer_enabled != 0 && goarch == "amd64" && goos != "nacl"
|
||||||
|
}
|
||||||
|
|
||||||
|
func addexp(s string) {
|
||||||
|
// Could do general integer parsing here, but the runtime copy doesn't yet.
|
||||||
|
v := 1
|
||||||
|
name := s
|
||||||
|
if len(name) > 2 && name[:2] == "no" {
|
||||||
|
v = 0
|
||||||
|
name = name[2:]
|
||||||
|
}
|
||||||
|
for i := 0; i < len(exper); i++ {
|
||||||
|
if exper[i].name == name {
|
||||||
|
if exper[i].val != nil {
|
||||||
|
*exper[i].val = v
|
||||||
|
}
|
||||||
|
return
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
fmt.Printf("unknown experiment %s\n", s)
|
||||||
|
os.Exit(2)
|
||||||
|
}
|
||||||
|
|
||||||
|
var (
|
||||||
|
framepointer_enabled int
|
||||||
|
Fieldtrack_enabled int
|
||||||
|
Preemptibleloops_enabled int
|
||||||
|
)
|
||||||
|
|
||||||
|
// Toolchain experiments.
|
||||||
|
// These are controlled by the GOEXPERIMENT environment
|
||||||
|
// variable recorded when the toolchain is built.
|
||||||
|
// This list is also known to cmd/gc.
|
||||||
|
var exper = []struct {
|
||||||
|
name string
|
||||||
|
val *int
|
||||||
|
}{
|
||||||
|
{"fieldtrack", &Fieldtrack_enabled},
|
||||||
|
{"framepointer", &framepointer_enabled},
|
||||||
|
{"preemptibleloops", &Preemptibleloops_enabled},
|
||||||
|
}
|
||||||
|
|
||||||
|
func Expstring() string {
|
||||||
|
buf := "X"
|
||||||
|
for i := range exper {
|
||||||
|
if *exper[i].val != 0 {
|
||||||
|
buf += "," + exper[i].name
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if buf == "X" {
|
||||||
|
buf += ",none"
|
||||||
|
}
|
||||||
|
return "X:" + buf[2:]
|
||||||
|
}
|
||||||
|
|
@ -8,6 +8,7 @@ package objfile
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"cmd/internal/goobj"
|
"cmd/internal/goobj"
|
||||||
|
"cmd/internal/objabi"
|
||||||
"cmd/internal/sys"
|
"cmd/internal/sys"
|
||||||
"debug/dwarf"
|
"debug/dwarf"
|
||||||
"debug/gosym"
|
"debug/gosym"
|
||||||
|
|
@ -44,15 +45,15 @@ func (f *goobjFile) symbols() ([]Sym, error) {
|
||||||
seen[s.SymID] = true
|
seen[s.SymID] = true
|
||||||
sym := Sym{Addr: uint64(s.Data.Offset), Name: goobjName(s.SymID), Size: int64(s.Size), Type: s.Type.Name, Code: '?'}
|
sym := Sym{Addr: uint64(s.Data.Offset), Name: goobjName(s.SymID), Size: int64(s.Size), Type: s.Type.Name, Code: '?'}
|
||||||
switch s.Kind {
|
switch s.Kind {
|
||||||
case goobj.STEXT, goobj.SELFRXSECT:
|
case objabi.STEXT, objabi.SELFRXSECT:
|
||||||
sym.Code = 'T'
|
sym.Code = 'T'
|
||||||
case goobj.STYPE, goobj.SSTRING, goobj.SGOSTRING, goobj.SGOFUNC, goobj.SRODATA, goobj.SFUNCTAB, goobj.STYPELINK, goobj.SITABLINK, goobj.SSYMTAB, goobj.SPCLNTAB, goobj.SELFROSECT:
|
case objabi.STYPE, objabi.SSTRING, objabi.SGOSTRING, objabi.SGOFUNC, objabi.SRODATA, objabi.SFUNCTAB, objabi.STYPELINK, objabi.SITABLINK, objabi.SSYMTAB, objabi.SPCLNTAB, objabi.SELFROSECT:
|
||||||
sym.Code = 'R'
|
sym.Code = 'R'
|
||||||
case goobj.SMACHOPLT, goobj.SELFSECT, goobj.SMACHO, goobj.SMACHOGOT, goobj.SNOPTRDATA, goobj.SINITARR, goobj.SDATA, goobj.SWINDOWS:
|
case objabi.SMACHOPLT, objabi.SELFSECT, objabi.SMACHO, objabi.SMACHOGOT, objabi.SNOPTRDATA, objabi.SINITARR, objabi.SDATA, objabi.SWINDOWS:
|
||||||
sym.Code = 'D'
|
sym.Code = 'D'
|
||||||
case goobj.SBSS, goobj.SNOPTRBSS, goobj.STLSBSS:
|
case objabi.SBSS, objabi.SNOPTRBSS, objabi.STLSBSS:
|
||||||
sym.Code = 'B'
|
sym.Code = 'B'
|
||||||
case goobj.SXREF, goobj.SMACHOSYMSTR, goobj.SMACHOSYMTAB, goobj.SMACHOINDIRECTPLT, goobj.SMACHOINDIRECTGOT, goobj.SFILE, goobj.SFILEPATH, goobj.SCONST, goobj.SDYNIMPORT, goobj.SHOSTOBJ:
|
case objabi.SXREF, objabi.SMACHOSYMSTR, objabi.SMACHOSYMTAB, objabi.SMACHOINDIRECTPLT, objabi.SMACHOINDIRECTGOT, objabi.SFILE, objabi.SFILEPATH, objabi.SCONST, objabi.SDYNIMPORT, objabi.SHOSTOBJ:
|
||||||
sym.Code = 'X' // should not see
|
sym.Code = 'X' // should not see
|
||||||
}
|
}
|
||||||
if s.Version != 0 {
|
if s.Version != 0 {
|
||||||
|
|
|
||||||
|
|
@ -31,7 +31,7 @@
|
||||||
package amd64
|
package amd64
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"cmd/internal/obj"
|
"cmd/internal/objabi"
|
||||||
"cmd/link/internal/ld"
|
"cmd/link/internal/ld"
|
||||||
"debug/elf"
|
"debug/elf"
|
||||||
"log"
|
"log"
|
||||||
|
|
@ -49,7 +49,7 @@ func Addcall(ctxt *ld.Link, s *ld.Symbol, t *ld.Symbol) int64 {
|
||||||
r := ld.Addrel(s)
|
r := ld.Addrel(s)
|
||||||
r.Sym = t
|
r.Sym = t
|
||||||
r.Off = int32(i)
|
r.Off = int32(i)
|
||||||
r.Type = obj.R_CALL
|
r.Type = objabi.R_CALL
|
||||||
r.Siz = 4
|
r.Siz = 4
|
||||||
return i + int64(r.Siz)
|
return i + int64(r.Siz)
|
||||||
}
|
}
|
||||||
|
|
@ -59,14 +59,14 @@ func gentext(ctxt *ld.Link) {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
addmoduledata := ctxt.Syms.Lookup("runtime.addmoduledata", 0)
|
addmoduledata := ctxt.Syms.Lookup("runtime.addmoduledata", 0)
|
||||||
if addmoduledata.Type == obj.STEXT && ld.Buildmode != ld.BuildmodePlugin {
|
if addmoduledata.Type == objabi.STEXT && ld.Buildmode != ld.BuildmodePlugin {
|
||||||
// we're linking a module containing the runtime -> no need for
|
// we're linking a module containing the runtime -> no need for
|
||||||
// an init function
|
// an init function
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
addmoduledata.Attr |= ld.AttrReachable
|
addmoduledata.Attr |= ld.AttrReachable
|
||||||
initfunc := ctxt.Syms.Lookup("go.link.addmoduledata", 0)
|
initfunc := ctxt.Syms.Lookup("go.link.addmoduledata", 0)
|
||||||
initfunc.Type = obj.STEXT
|
initfunc.Type = objabi.STEXT
|
||||||
initfunc.Attr |= ld.AttrLocal
|
initfunc.Attr |= ld.AttrLocal
|
||||||
initfunc.Attr |= ld.AttrReachable
|
initfunc.Attr |= ld.AttrReachable
|
||||||
o := func(op ...uint8) {
|
o := func(op ...uint8) {
|
||||||
|
|
@ -92,7 +92,7 @@ func gentext(ctxt *ld.Link) {
|
||||||
initarray_entry := ctxt.Syms.Lookup("go.link.addmoduledatainit", 0)
|
initarray_entry := ctxt.Syms.Lookup("go.link.addmoduledatainit", 0)
|
||||||
initarray_entry.Attr |= ld.AttrReachable
|
initarray_entry.Attr |= ld.AttrReachable
|
||||||
initarray_entry.Attr |= ld.AttrLocal
|
initarray_entry.Attr |= ld.AttrLocal
|
||||||
initarray_entry.Type = obj.SINITARR
|
initarray_entry.Type = objabi.SINITARR
|
||||||
ld.Addaddr(ctxt, initarray_entry, initfunc)
|
ld.Addaddr(ctxt, initarray_entry, initfunc)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -108,20 +108,20 @@ func adddynrel(ctxt *ld.Link, s *ld.Symbol, r *ld.Reloc) bool {
|
||||||
|
|
||||||
// Handle relocations found in ELF object files.
|
// Handle relocations found in ELF object files.
|
||||||
case 256 + ld.R_X86_64_PC32:
|
case 256 + ld.R_X86_64_PC32:
|
||||||
if targ.Type == obj.SDYNIMPORT {
|
if targ.Type == objabi.SDYNIMPORT {
|
||||||
ld.Errorf(s, "unexpected R_X86_64_PC32 relocation for dynamic symbol %s", targ.Name)
|
ld.Errorf(s, "unexpected R_X86_64_PC32 relocation for dynamic symbol %s", targ.Name)
|
||||||
}
|
}
|
||||||
if targ.Type == 0 || targ.Type == obj.SXREF {
|
if targ.Type == 0 || targ.Type == objabi.SXREF {
|
||||||
ld.Errorf(s, "unknown symbol %s in pcrel", targ.Name)
|
ld.Errorf(s, "unknown symbol %s in pcrel", targ.Name)
|
||||||
}
|
}
|
||||||
r.Type = obj.R_PCREL
|
r.Type = objabi.R_PCREL
|
||||||
r.Add += 4
|
r.Add += 4
|
||||||
return true
|
return true
|
||||||
|
|
||||||
case 256 + ld.R_X86_64_PLT32:
|
case 256 + ld.R_X86_64_PLT32:
|
||||||
r.Type = obj.R_PCREL
|
r.Type = objabi.R_PCREL
|
||||||
r.Add += 4
|
r.Add += 4
|
||||||
if targ.Type == obj.SDYNIMPORT {
|
if targ.Type == objabi.SDYNIMPORT {
|
||||||
addpltsym(ctxt, targ)
|
addpltsym(ctxt, targ)
|
||||||
r.Sym = ctxt.Syms.Lookup(".plt", 0)
|
r.Sym = ctxt.Syms.Lookup(".plt", 0)
|
||||||
r.Add += int64(targ.Plt)
|
r.Add += int64(targ.Plt)
|
||||||
|
|
@ -130,13 +130,13 @@ func adddynrel(ctxt *ld.Link, s *ld.Symbol, r *ld.Reloc) bool {
|
||||||
return true
|
return true
|
||||||
|
|
||||||
case 256 + ld.R_X86_64_GOTPCREL, 256 + ld.R_X86_64_GOTPCRELX, 256 + ld.R_X86_64_REX_GOTPCRELX:
|
case 256 + ld.R_X86_64_GOTPCREL, 256 + ld.R_X86_64_GOTPCRELX, 256 + ld.R_X86_64_REX_GOTPCRELX:
|
||||||
if targ.Type != obj.SDYNIMPORT {
|
if targ.Type != objabi.SDYNIMPORT {
|
||||||
// have symbol
|
// have symbol
|
||||||
if r.Off >= 2 && s.P[r.Off-2] == 0x8b {
|
if r.Off >= 2 && s.P[r.Off-2] == 0x8b {
|
||||||
// turn MOVQ of GOT entry into LEAQ of symbol itself
|
// turn MOVQ of GOT entry into LEAQ of symbol itself
|
||||||
s.P[r.Off-2] = 0x8d
|
s.P[r.Off-2] = 0x8d
|
||||||
|
|
||||||
r.Type = obj.R_PCREL
|
r.Type = objabi.R_PCREL
|
||||||
r.Add += 4
|
r.Add += 4
|
||||||
return true
|
return true
|
||||||
}
|
}
|
||||||
|
|
@ -146,17 +146,17 @@ func adddynrel(ctxt *ld.Link, s *ld.Symbol, r *ld.Reloc) bool {
|
||||||
// TODO: just needs relocation, no need to put in .dynsym
|
// TODO: just needs relocation, no need to put in .dynsym
|
||||||
addgotsym(ctxt, targ)
|
addgotsym(ctxt, targ)
|
||||||
|
|
||||||
r.Type = obj.R_PCREL
|
r.Type = objabi.R_PCREL
|
||||||
r.Sym = ctxt.Syms.Lookup(".got", 0)
|
r.Sym = ctxt.Syms.Lookup(".got", 0)
|
||||||
r.Add += 4
|
r.Add += 4
|
||||||
r.Add += int64(targ.Got)
|
r.Add += int64(targ.Got)
|
||||||
return true
|
return true
|
||||||
|
|
||||||
case 256 + ld.R_X86_64_64:
|
case 256 + ld.R_X86_64_64:
|
||||||
if targ.Type == obj.SDYNIMPORT {
|
if targ.Type == objabi.SDYNIMPORT {
|
||||||
ld.Errorf(s, "unexpected R_X86_64_64 relocation for dynamic symbol %s", targ.Name)
|
ld.Errorf(s, "unexpected R_X86_64_64 relocation for dynamic symbol %s", targ.Name)
|
||||||
}
|
}
|
||||||
r.Type = obj.R_ADDR
|
r.Type = objabi.R_ADDR
|
||||||
return true
|
return true
|
||||||
|
|
||||||
// Handle relocations found in Mach-O object files.
|
// Handle relocations found in Mach-O object files.
|
||||||
|
|
@ -164,19 +164,19 @@ func adddynrel(ctxt *ld.Link, s *ld.Symbol, r *ld.Reloc) bool {
|
||||||
512 + ld.MACHO_X86_64_RELOC_SIGNED*2 + 0,
|
512 + ld.MACHO_X86_64_RELOC_SIGNED*2 + 0,
|
||||||
512 + ld.MACHO_X86_64_RELOC_BRANCH*2 + 0:
|
512 + ld.MACHO_X86_64_RELOC_BRANCH*2 + 0:
|
||||||
// TODO: What is the difference between all these?
|
// TODO: What is the difference between all these?
|
||||||
r.Type = obj.R_ADDR
|
r.Type = objabi.R_ADDR
|
||||||
|
|
||||||
if targ.Type == obj.SDYNIMPORT {
|
if targ.Type == objabi.SDYNIMPORT {
|
||||||
ld.Errorf(s, "unexpected reloc for dynamic symbol %s", targ.Name)
|
ld.Errorf(s, "unexpected reloc for dynamic symbol %s", targ.Name)
|
||||||
}
|
}
|
||||||
return true
|
return true
|
||||||
|
|
||||||
case 512 + ld.MACHO_X86_64_RELOC_BRANCH*2 + 1:
|
case 512 + ld.MACHO_X86_64_RELOC_BRANCH*2 + 1:
|
||||||
if targ.Type == obj.SDYNIMPORT {
|
if targ.Type == objabi.SDYNIMPORT {
|
||||||
addpltsym(ctxt, targ)
|
addpltsym(ctxt, targ)
|
||||||
r.Sym = ctxt.Syms.Lookup(".plt", 0)
|
r.Sym = ctxt.Syms.Lookup(".plt", 0)
|
||||||
r.Add = int64(targ.Plt)
|
r.Add = int64(targ.Plt)
|
||||||
r.Type = obj.R_PCREL
|
r.Type = objabi.R_PCREL
|
||||||
return true
|
return true
|
||||||
}
|
}
|
||||||
fallthrough
|
fallthrough
|
||||||
|
|
@ -187,15 +187,15 @@ func adddynrel(ctxt *ld.Link, s *ld.Symbol, r *ld.Reloc) bool {
|
||||||
512 + ld.MACHO_X86_64_RELOC_SIGNED_1*2 + 1,
|
512 + ld.MACHO_X86_64_RELOC_SIGNED_1*2 + 1,
|
||||||
512 + ld.MACHO_X86_64_RELOC_SIGNED_2*2 + 1,
|
512 + ld.MACHO_X86_64_RELOC_SIGNED_2*2 + 1,
|
||||||
512 + ld.MACHO_X86_64_RELOC_SIGNED_4*2 + 1:
|
512 + ld.MACHO_X86_64_RELOC_SIGNED_4*2 + 1:
|
||||||
r.Type = obj.R_PCREL
|
r.Type = objabi.R_PCREL
|
||||||
|
|
||||||
if targ.Type == obj.SDYNIMPORT {
|
if targ.Type == objabi.SDYNIMPORT {
|
||||||
ld.Errorf(s, "unexpected pc-relative reloc for dynamic symbol %s", targ.Name)
|
ld.Errorf(s, "unexpected pc-relative reloc for dynamic symbol %s", targ.Name)
|
||||||
}
|
}
|
||||||
return true
|
return true
|
||||||
|
|
||||||
case 512 + ld.MACHO_X86_64_RELOC_GOT_LOAD*2 + 1:
|
case 512 + ld.MACHO_X86_64_RELOC_GOT_LOAD*2 + 1:
|
||||||
if targ.Type != obj.SDYNIMPORT {
|
if targ.Type != objabi.SDYNIMPORT {
|
||||||
// have symbol
|
// have symbol
|
||||||
// turn MOVQ of GOT entry into LEAQ of symbol itself
|
// turn MOVQ of GOT entry into LEAQ of symbol itself
|
||||||
if r.Off < 2 || s.P[r.Off-2] != 0x8b {
|
if r.Off < 2 || s.P[r.Off-2] != 0x8b {
|
||||||
|
|
@ -204,31 +204,31 @@ func adddynrel(ctxt *ld.Link, s *ld.Symbol, r *ld.Reloc) bool {
|
||||||
}
|
}
|
||||||
|
|
||||||
s.P[r.Off-2] = 0x8d
|
s.P[r.Off-2] = 0x8d
|
||||||
r.Type = obj.R_PCREL
|
r.Type = objabi.R_PCREL
|
||||||
return true
|
return true
|
||||||
}
|
}
|
||||||
fallthrough
|
fallthrough
|
||||||
|
|
||||||
// fall through
|
// fall through
|
||||||
case 512 + ld.MACHO_X86_64_RELOC_GOT*2 + 1:
|
case 512 + ld.MACHO_X86_64_RELOC_GOT*2 + 1:
|
||||||
if targ.Type != obj.SDYNIMPORT {
|
if targ.Type != objabi.SDYNIMPORT {
|
||||||
ld.Errorf(s, "unexpected GOT reloc for non-dynamic symbol %s", targ.Name)
|
ld.Errorf(s, "unexpected GOT reloc for non-dynamic symbol %s", targ.Name)
|
||||||
}
|
}
|
||||||
addgotsym(ctxt, targ)
|
addgotsym(ctxt, targ)
|
||||||
r.Type = obj.R_PCREL
|
r.Type = objabi.R_PCREL
|
||||||
r.Sym = ctxt.Syms.Lookup(".got", 0)
|
r.Sym = ctxt.Syms.Lookup(".got", 0)
|
||||||
r.Add += int64(targ.Got)
|
r.Add += int64(targ.Got)
|
||||||
return true
|
return true
|
||||||
}
|
}
|
||||||
|
|
||||||
switch r.Type {
|
switch r.Type {
|
||||||
case obj.R_CALL,
|
case objabi.R_CALL,
|
||||||
obj.R_PCREL:
|
objabi.R_PCREL:
|
||||||
if targ.Type != obj.SDYNIMPORT {
|
if targ.Type != objabi.SDYNIMPORT {
|
||||||
// nothing to do, the relocation will be laid out in reloc
|
// nothing to do, the relocation will be laid out in reloc
|
||||||
return true
|
return true
|
||||||
}
|
}
|
||||||
if ld.Headtype == obj.Hwindows {
|
if ld.Headtype == objabi.Hwindows {
|
||||||
// nothing to do, the relocation will be laid out in pereloc1
|
// nothing to do, the relocation will be laid out in pereloc1
|
||||||
return true
|
return true
|
||||||
} else {
|
} else {
|
||||||
|
|
@ -239,9 +239,9 @@ func adddynrel(ctxt *ld.Link, s *ld.Symbol, r *ld.Reloc) bool {
|
||||||
return true
|
return true
|
||||||
}
|
}
|
||||||
|
|
||||||
case obj.R_ADDR:
|
case objabi.R_ADDR:
|
||||||
if s.Type == obj.STEXT && ld.Iself {
|
if s.Type == objabi.STEXT && ld.Iself {
|
||||||
if ld.Headtype == obj.Hsolaris {
|
if ld.Headtype == objabi.Hsolaris {
|
||||||
addpltsym(ctxt, targ)
|
addpltsym(ctxt, targ)
|
||||||
r.Sym = ctxt.Syms.Lookup(".plt", 0)
|
r.Sym = ctxt.Syms.Lookup(".plt", 0)
|
||||||
r.Add += int64(targ.Plt)
|
r.Add += int64(targ.Plt)
|
||||||
|
|
@ -294,7 +294,7 @@ func adddynrel(ctxt *ld.Link, s *ld.Symbol, r *ld.Reloc) bool {
|
||||||
// linking, in which case the relocation will be
|
// linking, in which case the relocation will be
|
||||||
// prepared in the 'reloc' phase and passed to the
|
// prepared in the 'reloc' phase and passed to the
|
||||||
// external linker in the 'asmb' phase.
|
// external linker in the 'asmb' phase.
|
||||||
if s.Type != obj.SDATA && s.Type != obj.SRODATA {
|
if s.Type != objabi.SDATA && s.Type != objabi.SRODATA {
|
||||||
break
|
break
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
@ -317,7 +317,7 @@ func adddynrel(ctxt *ld.Link, s *ld.Symbol, r *ld.Reloc) bool {
|
||||||
return true
|
return true
|
||||||
}
|
}
|
||||||
|
|
||||||
if ld.Headtype == obj.Hdarwin && s.Size == int64(ld.SysArch.PtrSize) && r.Off == 0 {
|
if ld.Headtype == objabi.Hdarwin && s.Size == int64(ld.SysArch.PtrSize) && r.Off == 0 {
|
||||||
// Mach-O relocations are a royal pain to lay out.
|
// Mach-O relocations are a royal pain to lay out.
|
||||||
// They use a compact stateful bytecode representation
|
// They use a compact stateful bytecode representation
|
||||||
// that is too much bother to deal with.
|
// that is too much bother to deal with.
|
||||||
|
|
@ -331,7 +331,7 @@ func adddynrel(ctxt *ld.Link, s *ld.Symbol, r *ld.Reloc) bool {
|
||||||
ld.Adddynsym(ctxt, targ)
|
ld.Adddynsym(ctxt, targ)
|
||||||
|
|
||||||
got := ctxt.Syms.Lookup(".got", 0)
|
got := ctxt.Syms.Lookup(".got", 0)
|
||||||
s.Type = got.Type | obj.SSUB
|
s.Type = got.Type | objabi.SSUB
|
||||||
s.Outer = got
|
s.Outer = got
|
||||||
s.Sub = got.Sub
|
s.Sub = got.Sub
|
||||||
got.Sub = s
|
got.Sub = s
|
||||||
|
|
@ -342,7 +342,7 @@ func adddynrel(ctxt *ld.Link, s *ld.Symbol, r *ld.Reloc) bool {
|
||||||
return true
|
return true
|
||||||
}
|
}
|
||||||
|
|
||||||
if ld.Headtype == obj.Hwindows {
|
if ld.Headtype == objabi.Hwindows {
|
||||||
// nothing to do, the relocation will be laid out in pereloc1
|
// nothing to do, the relocation will be laid out in pereloc1
|
||||||
return true
|
return true
|
||||||
}
|
}
|
||||||
|
|
@ -359,7 +359,7 @@ func elfreloc1(ctxt *ld.Link, r *ld.Reloc, sectoff int64) int {
|
||||||
default:
|
default:
|
||||||
return -1
|
return -1
|
||||||
|
|
||||||
case obj.R_ADDR:
|
case objabi.R_ADDR:
|
||||||
if r.Siz == 4 {
|
if r.Siz == 4 {
|
||||||
ld.Thearch.Vput(ld.R_X86_64_32 | uint64(elfsym)<<32)
|
ld.Thearch.Vput(ld.R_X86_64_32 | uint64(elfsym)<<32)
|
||||||
} else if r.Siz == 8 {
|
} else if r.Siz == 8 {
|
||||||
|
|
@ -368,23 +368,23 @@ func elfreloc1(ctxt *ld.Link, r *ld.Reloc, sectoff int64) int {
|
||||||
return -1
|
return -1
|
||||||
}
|
}
|
||||||
|
|
||||||
case obj.R_TLS_LE:
|
case objabi.R_TLS_LE:
|
||||||
if r.Siz == 4 {
|
if r.Siz == 4 {
|
||||||
ld.Thearch.Vput(ld.R_X86_64_TPOFF32 | uint64(elfsym)<<32)
|
ld.Thearch.Vput(ld.R_X86_64_TPOFF32 | uint64(elfsym)<<32)
|
||||||
} else {
|
} else {
|
||||||
return -1
|
return -1
|
||||||
}
|
}
|
||||||
|
|
||||||
case obj.R_TLS_IE:
|
case objabi.R_TLS_IE:
|
||||||
if r.Siz == 4 {
|
if r.Siz == 4 {
|
||||||
ld.Thearch.Vput(ld.R_X86_64_GOTTPOFF | uint64(elfsym)<<32)
|
ld.Thearch.Vput(ld.R_X86_64_GOTTPOFF | uint64(elfsym)<<32)
|
||||||
} else {
|
} else {
|
||||||
return -1
|
return -1
|
||||||
}
|
}
|
||||||
|
|
||||||
case obj.R_CALL:
|
case objabi.R_CALL:
|
||||||
if r.Siz == 4 {
|
if r.Siz == 4 {
|
||||||
if r.Xsym.Type == obj.SDYNIMPORT {
|
if r.Xsym.Type == objabi.SDYNIMPORT {
|
||||||
if ctxt.DynlinkingGo() {
|
if ctxt.DynlinkingGo() {
|
||||||
ld.Thearch.Vput(ld.R_X86_64_PLT32 | uint64(elfsym)<<32)
|
ld.Thearch.Vput(ld.R_X86_64_PLT32 | uint64(elfsym)<<32)
|
||||||
} else {
|
} else {
|
||||||
|
|
@ -397,9 +397,9 @@ func elfreloc1(ctxt *ld.Link, r *ld.Reloc, sectoff int64) int {
|
||||||
return -1
|
return -1
|
||||||
}
|
}
|
||||||
|
|
||||||
case obj.R_PCREL:
|
case objabi.R_PCREL:
|
||||||
if r.Siz == 4 {
|
if r.Siz == 4 {
|
||||||
if r.Xsym.Type == obj.SDYNIMPORT && r.Xsym.ElfType == elf.STT_FUNC {
|
if r.Xsym.Type == objabi.SDYNIMPORT && r.Xsym.ElfType == elf.STT_FUNC {
|
||||||
ld.Thearch.Vput(ld.R_X86_64_PLT32 | uint64(elfsym)<<32)
|
ld.Thearch.Vput(ld.R_X86_64_PLT32 | uint64(elfsym)<<32)
|
||||||
} else {
|
} else {
|
||||||
ld.Thearch.Vput(ld.R_X86_64_PC32 | uint64(elfsym)<<32)
|
ld.Thearch.Vput(ld.R_X86_64_PC32 | uint64(elfsym)<<32)
|
||||||
|
|
@ -408,7 +408,7 @@ func elfreloc1(ctxt *ld.Link, r *ld.Reloc, sectoff int64) int {
|
||||||
return -1
|
return -1
|
||||||
}
|
}
|
||||||
|
|
||||||
case obj.R_GOTPCREL:
|
case objabi.R_GOTPCREL:
|
||||||
if r.Siz == 4 {
|
if r.Siz == 4 {
|
||||||
ld.Thearch.Vput(ld.R_X86_64_GOTPCREL | uint64(elfsym)<<32)
|
ld.Thearch.Vput(ld.R_X86_64_GOTPCREL | uint64(elfsym)<<32)
|
||||||
} else {
|
} else {
|
||||||
|
|
@ -425,7 +425,7 @@ func machoreloc1(s *ld.Symbol, r *ld.Reloc, sectoff int64) int {
|
||||||
|
|
||||||
rs := r.Xsym
|
rs := r.Xsym
|
||||||
|
|
||||||
if rs.Type == obj.SHOSTOBJ || r.Type == obj.R_PCREL || r.Type == obj.R_GOTPCREL {
|
if rs.Type == objabi.SHOSTOBJ || r.Type == objabi.R_PCREL || r.Type == objabi.R_GOTPCREL {
|
||||||
if rs.Dynid < 0 {
|
if rs.Dynid < 0 {
|
||||||
ld.Errorf(s, "reloc %d to non-macho symbol %s type=%d", r.Type, rs.Name, rs.Type)
|
ld.Errorf(s, "reloc %d to non-macho symbol %s type=%d", r.Type, rs.Name, rs.Type)
|
||||||
return -1
|
return -1
|
||||||
|
|
@ -445,18 +445,18 @@ func machoreloc1(s *ld.Symbol, r *ld.Reloc, sectoff int64) int {
|
||||||
default:
|
default:
|
||||||
return -1
|
return -1
|
||||||
|
|
||||||
case obj.R_ADDR:
|
case objabi.R_ADDR:
|
||||||
v |= ld.MACHO_X86_64_RELOC_UNSIGNED << 28
|
v |= ld.MACHO_X86_64_RELOC_UNSIGNED << 28
|
||||||
|
|
||||||
case obj.R_CALL:
|
case objabi.R_CALL:
|
||||||
v |= 1 << 24 // pc-relative bit
|
v |= 1 << 24 // pc-relative bit
|
||||||
v |= ld.MACHO_X86_64_RELOC_BRANCH << 28
|
v |= ld.MACHO_X86_64_RELOC_BRANCH << 28
|
||||||
|
|
||||||
// NOTE: Only works with 'external' relocation. Forced above.
|
// NOTE: Only works with 'external' relocation. Forced above.
|
||||||
case obj.R_PCREL:
|
case objabi.R_PCREL:
|
||||||
v |= 1 << 24 // pc-relative bit
|
v |= 1 << 24 // pc-relative bit
|
||||||
v |= ld.MACHO_X86_64_RELOC_SIGNED << 28
|
v |= ld.MACHO_X86_64_RELOC_SIGNED << 28
|
||||||
case obj.R_GOTPCREL:
|
case objabi.R_GOTPCREL:
|
||||||
v |= 1 << 24 // pc-relative bit
|
v |= 1 << 24 // pc-relative bit
|
||||||
v |= ld.MACHO_X86_64_RELOC_GOT_LOAD << 28
|
v |= ld.MACHO_X86_64_RELOC_GOT_LOAD << 28
|
||||||
}
|
}
|
||||||
|
|
@ -500,18 +500,18 @@ func pereloc1(s *ld.Symbol, r *ld.Reloc, sectoff int64) bool {
|
||||||
default:
|
default:
|
||||||
return false
|
return false
|
||||||
|
|
||||||
case obj.R_DWARFREF:
|
case objabi.R_DWARFREF:
|
||||||
v = ld.IMAGE_REL_AMD64_SECREL
|
v = ld.IMAGE_REL_AMD64_SECREL
|
||||||
|
|
||||||
case obj.R_ADDR:
|
case objabi.R_ADDR:
|
||||||
if r.Siz == 8 {
|
if r.Siz == 8 {
|
||||||
v = ld.IMAGE_REL_AMD64_ADDR64
|
v = ld.IMAGE_REL_AMD64_ADDR64
|
||||||
} else {
|
} else {
|
||||||
v = ld.IMAGE_REL_AMD64_ADDR32
|
v = ld.IMAGE_REL_AMD64_ADDR32
|
||||||
}
|
}
|
||||||
|
|
||||||
case obj.R_CALL,
|
case objabi.R_CALL,
|
||||||
obj.R_PCREL:
|
objabi.R_PCREL:
|
||||||
v = ld.IMAGE_REL_AMD64_REL32
|
v = ld.IMAGE_REL_AMD64_REL32
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -597,7 +597,7 @@ func addpltsym(ctxt *ld.Link, s *ld.Symbol) {
|
||||||
ld.Adduint64(ctxt, rela, 0)
|
ld.Adduint64(ctxt, rela, 0)
|
||||||
|
|
||||||
s.Plt = int32(plt.Size - 16)
|
s.Plt = int32(plt.Size - 16)
|
||||||
} else if ld.Headtype == obj.Hdarwin {
|
} else if ld.Headtype == objabi.Hdarwin {
|
||||||
// To do lazy symbol lookup right, we're supposed
|
// To do lazy symbol lookup right, we're supposed
|
||||||
// to tell the dynamic loader which library each
|
// to tell the dynamic loader which library each
|
||||||
// symbol comes from and format the link info
|
// symbol comes from and format the link info
|
||||||
|
|
@ -639,7 +639,7 @@ func addgotsym(ctxt *ld.Link, s *ld.Symbol) {
|
||||||
ld.Addaddrplus(ctxt, rela, got, int64(s.Got))
|
ld.Addaddrplus(ctxt, rela, got, int64(s.Got))
|
||||||
ld.Adduint64(ctxt, rela, ld.ELF64_R_INFO(uint32(s.Dynid), ld.R_X86_64_GLOB_DAT))
|
ld.Adduint64(ctxt, rela, ld.ELF64_R_INFO(uint32(s.Dynid), ld.R_X86_64_GLOB_DAT))
|
||||||
ld.Adduint64(ctxt, rela, 0)
|
ld.Adduint64(ctxt, rela, 0)
|
||||||
} else if ld.Headtype == obj.Hdarwin {
|
} else if ld.Headtype == objabi.Hdarwin {
|
||||||
ld.Adduint32(ctxt, ctxt.Syms.Lookup(".linkedit.got", 0), uint32(s.Dynid))
|
ld.Adduint32(ctxt, ctxt.Syms.Lookup(".linkedit.got", 0), uint32(s.Dynid))
|
||||||
} else {
|
} else {
|
||||||
ld.Errorf(s, "addgotsym: unsupported binary format")
|
ld.Errorf(s, "addgotsym: unsupported binary format")
|
||||||
|
|
@ -648,11 +648,11 @@ func addgotsym(ctxt *ld.Link, s *ld.Symbol) {
|
||||||
|
|
||||||
func asmb(ctxt *ld.Link) {
|
func asmb(ctxt *ld.Link) {
|
||||||
if ctxt.Debugvlog != 0 {
|
if ctxt.Debugvlog != 0 {
|
||||||
ctxt.Logf("%5.2f asmb\n", obj.Cputime())
|
ctxt.Logf("%5.2f asmb\n", ld.Cputime())
|
||||||
}
|
}
|
||||||
|
|
||||||
if ctxt.Debugvlog != 0 {
|
if ctxt.Debugvlog != 0 {
|
||||||
ctxt.Logf("%5.2f codeblk\n", obj.Cputime())
|
ctxt.Logf("%5.2f codeblk\n", ld.Cputime())
|
||||||
}
|
}
|
||||||
|
|
||||||
if ld.Iself {
|
if ld.Iself {
|
||||||
|
|
@ -670,21 +670,21 @@ func asmb(ctxt *ld.Link) {
|
||||||
|
|
||||||
if ld.Segrodata.Filelen > 0 {
|
if ld.Segrodata.Filelen > 0 {
|
||||||
if ctxt.Debugvlog != 0 {
|
if ctxt.Debugvlog != 0 {
|
||||||
ctxt.Logf("%5.2f rodatblk\n", obj.Cputime())
|
ctxt.Logf("%5.2f rodatblk\n", ld.Cputime())
|
||||||
}
|
}
|
||||||
ld.Cseek(int64(ld.Segrodata.Fileoff))
|
ld.Cseek(int64(ld.Segrodata.Fileoff))
|
||||||
ld.Datblk(ctxt, int64(ld.Segrodata.Vaddr), int64(ld.Segrodata.Filelen))
|
ld.Datblk(ctxt, int64(ld.Segrodata.Vaddr), int64(ld.Segrodata.Filelen))
|
||||||
}
|
}
|
||||||
if ld.Segrelrodata.Filelen > 0 {
|
if ld.Segrelrodata.Filelen > 0 {
|
||||||
if ctxt.Debugvlog != 0 {
|
if ctxt.Debugvlog != 0 {
|
||||||
ctxt.Logf("%5.2f relrodatblk\n", obj.Cputime())
|
ctxt.Logf("%5.2f relrodatblk\n", ld.Cputime())
|
||||||
}
|
}
|
||||||
ld.Cseek(int64(ld.Segrelrodata.Fileoff))
|
ld.Cseek(int64(ld.Segrelrodata.Fileoff))
|
||||||
ld.Datblk(ctxt, int64(ld.Segrelrodata.Vaddr), int64(ld.Segrelrodata.Filelen))
|
ld.Datblk(ctxt, int64(ld.Segrelrodata.Vaddr), int64(ld.Segrelrodata.Filelen))
|
||||||
}
|
}
|
||||||
|
|
||||||
if ctxt.Debugvlog != 0 {
|
if ctxt.Debugvlog != 0 {
|
||||||
ctxt.Logf("%5.2f datblk\n", obj.Cputime())
|
ctxt.Logf("%5.2f datblk\n", ld.Cputime())
|
||||||
}
|
}
|
||||||
|
|
||||||
ld.Cseek(int64(ld.Segdata.Fileoff))
|
ld.Cseek(int64(ld.Segdata.Fileoff))
|
||||||
|
|
@ -694,7 +694,7 @@ func asmb(ctxt *ld.Link) {
|
||||||
ld.Dwarfblk(ctxt, int64(ld.Segdwarf.Vaddr), int64(ld.Segdwarf.Filelen))
|
ld.Dwarfblk(ctxt, int64(ld.Segdwarf.Vaddr), int64(ld.Segdwarf.Filelen))
|
||||||
|
|
||||||
machlink := int64(0)
|
machlink := int64(0)
|
||||||
if ld.Headtype == obj.Hdarwin {
|
if ld.Headtype == objabi.Hdarwin {
|
||||||
machlink = ld.Domacholink(ctxt)
|
machlink = ld.Domacholink(ctxt)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -703,22 +703,22 @@ func asmb(ctxt *ld.Link) {
|
||||||
ld.Errorf(nil, "unknown header type %v", ld.Headtype)
|
ld.Errorf(nil, "unknown header type %v", ld.Headtype)
|
||||||
fallthrough
|
fallthrough
|
||||||
|
|
||||||
case obj.Hplan9:
|
case objabi.Hplan9:
|
||||||
break
|
break
|
||||||
|
|
||||||
case obj.Hdarwin:
|
case objabi.Hdarwin:
|
||||||
ld.Flag8 = true /* 64-bit addresses */
|
ld.Flag8 = true /* 64-bit addresses */
|
||||||
|
|
||||||
case obj.Hlinux,
|
case objabi.Hlinux,
|
||||||
obj.Hfreebsd,
|
objabi.Hfreebsd,
|
||||||
obj.Hnetbsd,
|
objabi.Hnetbsd,
|
||||||
obj.Hopenbsd,
|
objabi.Hopenbsd,
|
||||||
obj.Hdragonfly,
|
objabi.Hdragonfly,
|
||||||
obj.Hsolaris:
|
objabi.Hsolaris:
|
||||||
ld.Flag8 = true /* 64-bit addresses */
|
ld.Flag8 = true /* 64-bit addresses */
|
||||||
|
|
||||||
case obj.Hnacl,
|
case objabi.Hnacl,
|
||||||
obj.Hwindows:
|
objabi.Hwindows:
|
||||||
break
|
break
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -728,28 +728,28 @@ func asmb(ctxt *ld.Link) {
|
||||||
symo := int64(0)
|
symo := int64(0)
|
||||||
if !*ld.FlagS {
|
if !*ld.FlagS {
|
||||||
if ctxt.Debugvlog != 0 {
|
if ctxt.Debugvlog != 0 {
|
||||||
ctxt.Logf("%5.2f sym\n", obj.Cputime())
|
ctxt.Logf("%5.2f sym\n", ld.Cputime())
|
||||||
}
|
}
|
||||||
switch ld.Headtype {
|
switch ld.Headtype {
|
||||||
default:
|
default:
|
||||||
case obj.Hplan9:
|
case objabi.Hplan9:
|
||||||
*ld.FlagS = true
|
*ld.FlagS = true
|
||||||
symo = int64(ld.Segdata.Fileoff + ld.Segdata.Filelen)
|
symo = int64(ld.Segdata.Fileoff + ld.Segdata.Filelen)
|
||||||
|
|
||||||
case obj.Hdarwin:
|
case objabi.Hdarwin:
|
||||||
symo = int64(ld.Segdwarf.Fileoff + uint64(ld.Rnd(int64(ld.Segdwarf.Filelen), int64(*ld.FlagRound))) + uint64(machlink))
|
symo = int64(ld.Segdwarf.Fileoff + uint64(ld.Rnd(int64(ld.Segdwarf.Filelen), int64(*ld.FlagRound))) + uint64(machlink))
|
||||||
|
|
||||||
case obj.Hlinux,
|
case objabi.Hlinux,
|
||||||
obj.Hfreebsd,
|
objabi.Hfreebsd,
|
||||||
obj.Hnetbsd,
|
objabi.Hnetbsd,
|
||||||
obj.Hopenbsd,
|
objabi.Hopenbsd,
|
||||||
obj.Hdragonfly,
|
objabi.Hdragonfly,
|
||||||
obj.Hsolaris,
|
objabi.Hsolaris,
|
||||||
obj.Hnacl:
|
objabi.Hnacl:
|
||||||
symo = int64(ld.Segdwarf.Fileoff + ld.Segdwarf.Filelen)
|
symo = int64(ld.Segdwarf.Fileoff + ld.Segdwarf.Filelen)
|
||||||
symo = ld.Rnd(symo, int64(*ld.FlagRound))
|
symo = ld.Rnd(symo, int64(*ld.FlagRound))
|
||||||
|
|
||||||
case obj.Hwindows:
|
case objabi.Hwindows:
|
||||||
symo = int64(ld.Segdwarf.Fileoff + ld.Segdwarf.Filelen)
|
symo = int64(ld.Segdwarf.Fileoff + ld.Segdwarf.Filelen)
|
||||||
symo = ld.Rnd(symo, ld.PEFILEALIGN)
|
symo = ld.Rnd(symo, ld.PEFILEALIGN)
|
||||||
}
|
}
|
||||||
|
|
@ -764,7 +764,7 @@ func asmb(ctxt *ld.Link) {
|
||||||
ld.Cwrite(ld.Elfstrdat)
|
ld.Cwrite(ld.Elfstrdat)
|
||||||
|
|
||||||
if ctxt.Debugvlog != 0 {
|
if ctxt.Debugvlog != 0 {
|
||||||
ctxt.Logf("%5.2f dwarf\n", obj.Cputime())
|
ctxt.Logf("%5.2f dwarf\n", ld.Cputime())
|
||||||
}
|
}
|
||||||
|
|
||||||
if ld.Linkmode == ld.LinkExternal {
|
if ld.Linkmode == ld.LinkExternal {
|
||||||
|
|
@ -772,7 +772,7 @@ func asmb(ctxt *ld.Link) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
case obj.Hplan9:
|
case objabi.Hplan9:
|
||||||
ld.Asmplan9sym(ctxt)
|
ld.Asmplan9sym(ctxt)
|
||||||
ld.Cflush()
|
ld.Cflush()
|
||||||
|
|
||||||
|
|
@ -786,12 +786,12 @@ func asmb(ctxt *ld.Link) {
|
||||||
ld.Cflush()
|
ld.Cflush()
|
||||||
}
|
}
|
||||||
|
|
||||||
case obj.Hwindows:
|
case objabi.Hwindows:
|
||||||
if ctxt.Debugvlog != 0 {
|
if ctxt.Debugvlog != 0 {
|
||||||
ctxt.Logf("%5.2f dwarf\n", obj.Cputime())
|
ctxt.Logf("%5.2f dwarf\n", ld.Cputime())
|
||||||
}
|
}
|
||||||
|
|
||||||
case obj.Hdarwin:
|
case objabi.Hdarwin:
|
||||||
if ld.Linkmode == ld.LinkExternal {
|
if ld.Linkmode == ld.LinkExternal {
|
||||||
ld.Machoemitreloc(ctxt)
|
ld.Machoemitreloc(ctxt)
|
||||||
}
|
}
|
||||||
|
|
@ -799,12 +799,12 @@ func asmb(ctxt *ld.Link) {
|
||||||
}
|
}
|
||||||
|
|
||||||
if ctxt.Debugvlog != 0 {
|
if ctxt.Debugvlog != 0 {
|
||||||
ctxt.Logf("%5.2f headr\n", obj.Cputime())
|
ctxt.Logf("%5.2f headr\n", ld.Cputime())
|
||||||
}
|
}
|
||||||
ld.Cseek(0)
|
ld.Cseek(0)
|
||||||
switch ld.Headtype {
|
switch ld.Headtype {
|
||||||
default:
|
default:
|
||||||
case obj.Hplan9: /* plan9 */
|
case objabi.Hplan9: /* plan9 */
|
||||||
magic := int32(4*26*26 + 7)
|
magic := int32(4*26*26 + 7)
|
||||||
|
|
||||||
magic |= 0x00008000 /* fat header */
|
magic |= 0x00008000 /* fat header */
|
||||||
|
|
@ -819,19 +819,19 @@ func asmb(ctxt *ld.Link) {
|
||||||
ld.Lputb(uint32(ld.Lcsize)) /* line offsets */
|
ld.Lputb(uint32(ld.Lcsize)) /* line offsets */
|
||||||
ld.Vputb(uint64(vl)) /* va of entry */
|
ld.Vputb(uint64(vl)) /* va of entry */
|
||||||
|
|
||||||
case obj.Hdarwin:
|
case objabi.Hdarwin:
|
||||||
ld.Asmbmacho(ctxt)
|
ld.Asmbmacho(ctxt)
|
||||||
|
|
||||||
case obj.Hlinux,
|
case objabi.Hlinux,
|
||||||
obj.Hfreebsd,
|
objabi.Hfreebsd,
|
||||||
obj.Hnetbsd,
|
objabi.Hnetbsd,
|
||||||
obj.Hopenbsd,
|
objabi.Hopenbsd,
|
||||||
obj.Hdragonfly,
|
objabi.Hdragonfly,
|
||||||
obj.Hsolaris,
|
objabi.Hsolaris,
|
||||||
obj.Hnacl:
|
objabi.Hnacl:
|
||||||
ld.Asmbelf(ctxt, symo)
|
ld.Asmbelf(ctxt, symo)
|
||||||
|
|
||||||
case obj.Hwindows:
|
case objabi.Hwindows:
|
||||||
ld.Asmbpe(ctxt)
|
ld.Asmbpe(ctxt)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -31,7 +31,7 @@
|
||||||
package amd64
|
package amd64
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"cmd/internal/obj"
|
"cmd/internal/objabi"
|
||||||
"cmd/internal/sys"
|
"cmd/internal/sys"
|
||||||
"cmd/link/internal/ld"
|
"cmd/link/internal/ld"
|
||||||
"fmt"
|
"fmt"
|
||||||
|
|
@ -39,7 +39,7 @@ import (
|
||||||
|
|
||||||
func Init() {
|
func Init() {
|
||||||
ld.SysArch = sys.ArchAMD64
|
ld.SysArch = sys.ArchAMD64
|
||||||
if obj.GOARCH == "amd64p32" {
|
if objabi.GOARCH == "amd64p32" {
|
||||||
ld.SysArch = sys.ArchAMD64P32
|
ld.SysArch = sys.ArchAMD64P32
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -80,7 +80,7 @@ func archinit(ctxt *ld.Link) {
|
||||||
default:
|
default:
|
||||||
ld.Exitf("unknown -H option: %v", ld.Headtype)
|
ld.Exitf("unknown -H option: %v", ld.Headtype)
|
||||||
|
|
||||||
case obj.Hplan9: /* plan 9 */
|
case objabi.Hplan9: /* plan 9 */
|
||||||
ld.HEADR = 32 + 8
|
ld.HEADR = 32 + 8
|
||||||
|
|
||||||
if *ld.FlagTextAddr == -1 {
|
if *ld.FlagTextAddr == -1 {
|
||||||
|
|
@ -93,7 +93,7 @@ func archinit(ctxt *ld.Link) {
|
||||||
*ld.FlagRound = 0x200000
|
*ld.FlagRound = 0x200000
|
||||||
}
|
}
|
||||||
|
|
||||||
case obj.Hdarwin: /* apple MACH */
|
case objabi.Hdarwin: /* apple MACH */
|
||||||
ld.Machoinit()
|
ld.Machoinit()
|
||||||
|
|
||||||
ld.HEADR = ld.INITIAL_MACHO_HEADR
|
ld.HEADR = ld.INITIAL_MACHO_HEADR
|
||||||
|
|
@ -107,12 +107,12 @@ func archinit(ctxt *ld.Link) {
|
||||||
*ld.FlagDataAddr = 0
|
*ld.FlagDataAddr = 0
|
||||||
}
|
}
|
||||||
|
|
||||||
case obj.Hlinux, /* elf64 executable */
|
case objabi.Hlinux, /* elf64 executable */
|
||||||
obj.Hfreebsd, /* freebsd */
|
objabi.Hfreebsd, /* freebsd */
|
||||||
obj.Hnetbsd, /* netbsd */
|
objabi.Hnetbsd, /* netbsd */
|
||||||
obj.Hopenbsd, /* openbsd */
|
objabi.Hopenbsd, /* openbsd */
|
||||||
obj.Hdragonfly, /* dragonfly */
|
objabi.Hdragonfly, /* dragonfly */
|
||||||
obj.Hsolaris: /* solaris */
|
objabi.Hsolaris: /* solaris */
|
||||||
ld.Elfinit(ctxt)
|
ld.Elfinit(ctxt)
|
||||||
|
|
||||||
ld.HEADR = ld.ELFRESERVE
|
ld.HEADR = ld.ELFRESERVE
|
||||||
|
|
@ -126,7 +126,7 @@ func archinit(ctxt *ld.Link) {
|
||||||
*ld.FlagRound = 4096
|
*ld.FlagRound = 4096
|
||||||
}
|
}
|
||||||
|
|
||||||
case obj.Hnacl:
|
case objabi.Hnacl:
|
||||||
ld.Elfinit(ctxt)
|
ld.Elfinit(ctxt)
|
||||||
*ld.FlagW = true // disable dwarf, which gets confused and is useless anyway
|
*ld.FlagW = true // disable dwarf, which gets confused and is useless anyway
|
||||||
ld.HEADR = 0x10000
|
ld.HEADR = 0x10000
|
||||||
|
|
@ -141,7 +141,7 @@ func archinit(ctxt *ld.Link) {
|
||||||
*ld.FlagRound = 0x10000
|
*ld.FlagRound = 0x10000
|
||||||
}
|
}
|
||||||
|
|
||||||
case obj.Hwindows: /* PE executable */
|
case objabi.Hwindows: /* PE executable */
|
||||||
// ld.HEADR, ld.FlagTextAddr, ld.FlagDataAddr and ld.FlagRound are set in ld.Peinit
|
// ld.HEADR, ld.FlagTextAddr, ld.FlagDataAddr and ld.FlagRound are set in ld.Peinit
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -31,7 +31,7 @@
|
||||||
package arm
|
package arm
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"cmd/internal/obj"
|
"cmd/internal/objabi"
|
||||||
"cmd/link/internal/ld"
|
"cmd/link/internal/ld"
|
||||||
"fmt"
|
"fmt"
|
||||||
"log"
|
"log"
|
||||||
|
|
@ -63,14 +63,14 @@ func gentext(ctxt *ld.Link) {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
addmoduledata := ctxt.Syms.Lookup("runtime.addmoduledata", 0)
|
addmoduledata := ctxt.Syms.Lookup("runtime.addmoduledata", 0)
|
||||||
if addmoduledata.Type == obj.STEXT && ld.Buildmode != ld.BuildmodePlugin {
|
if addmoduledata.Type == objabi.STEXT && ld.Buildmode != ld.BuildmodePlugin {
|
||||||
// we're linking a module containing the runtime -> no need for
|
// we're linking a module containing the runtime -> no need for
|
||||||
// an init function
|
// an init function
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
addmoduledata.Attr |= ld.AttrReachable
|
addmoduledata.Attr |= ld.AttrReachable
|
||||||
initfunc := ctxt.Syms.Lookup("go.link.addmoduledata", 0)
|
initfunc := ctxt.Syms.Lookup("go.link.addmoduledata", 0)
|
||||||
initfunc.Type = obj.STEXT
|
initfunc.Type = objabi.STEXT
|
||||||
initfunc.Attr |= ld.AttrLocal
|
initfunc.Attr |= ld.AttrLocal
|
||||||
initfunc.Attr |= ld.AttrReachable
|
initfunc.Attr |= ld.AttrReachable
|
||||||
o := func(op uint32) {
|
o := func(op uint32) {
|
||||||
|
|
@ -84,7 +84,7 @@ func gentext(ctxt *ld.Link) {
|
||||||
rel.Off = 8
|
rel.Off = 8
|
||||||
rel.Siz = 4
|
rel.Siz = 4
|
||||||
rel.Sym = ctxt.Syms.Lookup("runtime.addmoduledata", 0)
|
rel.Sym = ctxt.Syms.Lookup("runtime.addmoduledata", 0)
|
||||||
rel.Type = obj.R_CALLARM
|
rel.Type = objabi.R_CALLARM
|
||||||
rel.Add = 0xeafffffe // vomit
|
rel.Add = 0xeafffffe // vomit
|
||||||
|
|
||||||
o(0x00000000)
|
o(0x00000000)
|
||||||
|
|
@ -92,7 +92,7 @@ func gentext(ctxt *ld.Link) {
|
||||||
rel.Off = 12
|
rel.Off = 12
|
||||||
rel.Siz = 4
|
rel.Siz = 4
|
||||||
rel.Sym = ctxt.Moduledata
|
rel.Sym = ctxt.Moduledata
|
||||||
rel.Type = obj.R_PCREL
|
rel.Type = objabi.R_PCREL
|
||||||
rel.Add = 4
|
rel.Add = 4
|
||||||
|
|
||||||
if ld.Buildmode == ld.BuildmodePlugin {
|
if ld.Buildmode == ld.BuildmodePlugin {
|
||||||
|
|
@ -102,7 +102,7 @@ func gentext(ctxt *ld.Link) {
|
||||||
initarray_entry := ctxt.Syms.Lookup("go.link.addmoduledatainit", 0)
|
initarray_entry := ctxt.Syms.Lookup("go.link.addmoduledatainit", 0)
|
||||||
initarray_entry.Attr |= ld.AttrReachable
|
initarray_entry.Attr |= ld.AttrReachable
|
||||||
initarray_entry.Attr |= ld.AttrLocal
|
initarray_entry.Attr |= ld.AttrLocal
|
||||||
initarray_entry.Type = obj.SINITARR
|
initarray_entry.Type = objabi.SINITARR
|
||||||
ld.Addaddr(ctxt, initarray_entry, initfunc)
|
ld.Addaddr(ctxt, initarray_entry, initfunc)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -124,9 +124,9 @@ func adddynrel(ctxt *ld.Link, s *ld.Symbol, r *ld.Reloc) bool {
|
||||||
|
|
||||||
// Handle relocations found in ELF object files.
|
// Handle relocations found in ELF object files.
|
||||||
case 256 + ld.R_ARM_PLT32:
|
case 256 + ld.R_ARM_PLT32:
|
||||||
r.Type = obj.R_CALLARM
|
r.Type = objabi.R_CALLARM
|
||||||
|
|
||||||
if targ.Type == obj.SDYNIMPORT {
|
if targ.Type == objabi.SDYNIMPORT {
|
||||||
addpltsym(ctxt, targ)
|
addpltsym(ctxt, targ)
|
||||||
r.Sym = ctxt.Syms.Lookup(".plt", 0)
|
r.Sym = ctxt.Syms.Lookup(".plt", 0)
|
||||||
r.Add = int64(braddoff(int32(r.Add), targ.Plt/4))
|
r.Add = int64(braddoff(int32(r.Add), targ.Plt/4))
|
||||||
|
|
@ -139,44 +139,44 @@ func adddynrel(ctxt *ld.Link, s *ld.Symbol, r *ld.Reloc) bool {
|
||||||
return false
|
return false
|
||||||
|
|
||||||
case 256 + ld.R_ARM_GOT32: // R_ARM_GOT_BREL
|
case 256 + ld.R_ARM_GOT32: // R_ARM_GOT_BREL
|
||||||
if targ.Type != obj.SDYNIMPORT {
|
if targ.Type != objabi.SDYNIMPORT {
|
||||||
addgotsyminternal(ctxt, targ)
|
addgotsyminternal(ctxt, targ)
|
||||||
} else {
|
} else {
|
||||||
addgotsym(ctxt, targ)
|
addgotsym(ctxt, targ)
|
||||||
}
|
}
|
||||||
|
|
||||||
r.Type = obj.R_CONST // write r->add during relocsym
|
r.Type = objabi.R_CONST // write r->add during relocsym
|
||||||
r.Sym = nil
|
r.Sym = nil
|
||||||
r.Add += int64(targ.Got)
|
r.Add += int64(targ.Got)
|
||||||
return true
|
return true
|
||||||
|
|
||||||
case 256 + ld.R_ARM_GOT_PREL: // GOT(nil) + A - nil
|
case 256 + ld.R_ARM_GOT_PREL: // GOT(nil) + A - nil
|
||||||
if targ.Type != obj.SDYNIMPORT {
|
if targ.Type != objabi.SDYNIMPORT {
|
||||||
addgotsyminternal(ctxt, targ)
|
addgotsyminternal(ctxt, targ)
|
||||||
} else {
|
} else {
|
||||||
addgotsym(ctxt, targ)
|
addgotsym(ctxt, targ)
|
||||||
}
|
}
|
||||||
|
|
||||||
r.Type = obj.R_PCREL
|
r.Type = objabi.R_PCREL
|
||||||
r.Sym = ctxt.Syms.Lookup(".got", 0)
|
r.Sym = ctxt.Syms.Lookup(".got", 0)
|
||||||
r.Add += int64(targ.Got) + 4
|
r.Add += int64(targ.Got) + 4
|
||||||
return true
|
return true
|
||||||
|
|
||||||
case 256 + ld.R_ARM_GOTOFF: // R_ARM_GOTOFF32
|
case 256 + ld.R_ARM_GOTOFF: // R_ARM_GOTOFF32
|
||||||
r.Type = obj.R_GOTOFF
|
r.Type = objabi.R_GOTOFF
|
||||||
|
|
||||||
return true
|
return true
|
||||||
|
|
||||||
case 256 + ld.R_ARM_GOTPC: // R_ARM_BASE_PREL
|
case 256 + ld.R_ARM_GOTPC: // R_ARM_BASE_PREL
|
||||||
r.Type = obj.R_PCREL
|
r.Type = objabi.R_PCREL
|
||||||
|
|
||||||
r.Sym = ctxt.Syms.Lookup(".got", 0)
|
r.Sym = ctxt.Syms.Lookup(".got", 0)
|
||||||
r.Add += 4
|
r.Add += 4
|
||||||
return true
|
return true
|
||||||
|
|
||||||
case 256 + ld.R_ARM_CALL:
|
case 256 + ld.R_ARM_CALL:
|
||||||
r.Type = obj.R_CALLARM
|
r.Type = objabi.R_CALLARM
|
||||||
if targ.Type == obj.SDYNIMPORT {
|
if targ.Type == objabi.SDYNIMPORT {
|
||||||
addpltsym(ctxt, targ)
|
addpltsym(ctxt, targ)
|
||||||
r.Sym = ctxt.Syms.Lookup(".plt", 0)
|
r.Sym = ctxt.Syms.Lookup(".plt", 0)
|
||||||
r.Add = int64(braddoff(int32(r.Add), targ.Plt/4))
|
r.Add = int64(braddoff(int32(r.Add), targ.Plt/4))
|
||||||
|
|
@ -185,16 +185,16 @@ func adddynrel(ctxt *ld.Link, s *ld.Symbol, r *ld.Reloc) bool {
|
||||||
return true
|
return true
|
||||||
|
|
||||||
case 256 + ld.R_ARM_REL32: // R_ARM_REL32
|
case 256 + ld.R_ARM_REL32: // R_ARM_REL32
|
||||||
r.Type = obj.R_PCREL
|
r.Type = objabi.R_PCREL
|
||||||
|
|
||||||
r.Add += 4
|
r.Add += 4
|
||||||
return true
|
return true
|
||||||
|
|
||||||
case 256 + ld.R_ARM_ABS32:
|
case 256 + ld.R_ARM_ABS32:
|
||||||
if targ.Type == obj.SDYNIMPORT {
|
if targ.Type == objabi.SDYNIMPORT {
|
||||||
ld.Errorf(s, "unexpected R_ARM_ABS32 relocation for dynamic symbol %s", targ.Name)
|
ld.Errorf(s, "unexpected R_ARM_ABS32 relocation for dynamic symbol %s", targ.Name)
|
||||||
}
|
}
|
||||||
r.Type = obj.R_ADDR
|
r.Type = objabi.R_ADDR
|
||||||
return true
|
return true
|
||||||
|
|
||||||
// we can just ignore this, because we are targeting ARM V5+ anyway
|
// we can just ignore this, because we are targeting ARM V5+ anyway
|
||||||
|
|
@ -209,8 +209,8 @@ func adddynrel(ctxt *ld.Link, s *ld.Symbol, r *ld.Reloc) bool {
|
||||||
|
|
||||||
case 256 + ld.R_ARM_PC24,
|
case 256 + ld.R_ARM_PC24,
|
||||||
256 + ld.R_ARM_JUMP24:
|
256 + ld.R_ARM_JUMP24:
|
||||||
r.Type = obj.R_CALLARM
|
r.Type = objabi.R_CALLARM
|
||||||
if targ.Type == obj.SDYNIMPORT {
|
if targ.Type == objabi.SDYNIMPORT {
|
||||||
addpltsym(ctxt, targ)
|
addpltsym(ctxt, targ)
|
||||||
r.Sym = ctxt.Syms.Lookup(".plt", 0)
|
r.Sym = ctxt.Syms.Lookup(".plt", 0)
|
||||||
r.Add = int64(braddoff(int32(r.Add), targ.Plt/4))
|
r.Add = int64(braddoff(int32(r.Add), targ.Plt/4))
|
||||||
|
|
@ -220,19 +220,19 @@ func adddynrel(ctxt *ld.Link, s *ld.Symbol, r *ld.Reloc) bool {
|
||||||
}
|
}
|
||||||
|
|
||||||
// Handle references to ELF symbols from our own object files.
|
// Handle references to ELF symbols from our own object files.
|
||||||
if targ.Type != obj.SDYNIMPORT {
|
if targ.Type != objabi.SDYNIMPORT {
|
||||||
return true
|
return true
|
||||||
}
|
}
|
||||||
|
|
||||||
switch r.Type {
|
switch r.Type {
|
||||||
case obj.R_CALLARM:
|
case objabi.R_CALLARM:
|
||||||
addpltsym(ctxt, targ)
|
addpltsym(ctxt, targ)
|
||||||
r.Sym = ctxt.Syms.Lookup(".plt", 0)
|
r.Sym = ctxt.Syms.Lookup(".plt", 0)
|
||||||
r.Add = int64(targ.Plt)
|
r.Add = int64(targ.Plt)
|
||||||
return true
|
return true
|
||||||
|
|
||||||
case obj.R_ADDR:
|
case objabi.R_ADDR:
|
||||||
if s.Type != obj.SDATA {
|
if s.Type != objabi.SDATA {
|
||||||
break
|
break
|
||||||
}
|
}
|
||||||
if ld.Iself {
|
if ld.Iself {
|
||||||
|
|
@ -240,7 +240,7 @@ func adddynrel(ctxt *ld.Link, s *ld.Symbol, r *ld.Reloc) bool {
|
||||||
rel := ctxt.Syms.Lookup(".rel", 0)
|
rel := ctxt.Syms.Lookup(".rel", 0)
|
||||||
ld.Addaddrplus(ctxt, rel, s, int64(r.Off))
|
ld.Addaddrplus(ctxt, rel, s, int64(r.Off))
|
||||||
ld.Adduint32(ctxt, rel, ld.ELF32_R_INFO(uint32(targ.Dynid), ld.R_ARM_GLOB_DAT)) // we need a nil + A dynamic reloc
|
ld.Adduint32(ctxt, rel, ld.ELF32_R_INFO(uint32(targ.Dynid), ld.R_ARM_GLOB_DAT)) // we need a nil + A dynamic reloc
|
||||||
r.Type = obj.R_CONST // write r->add during relocsym
|
r.Type = objabi.R_CONST // write r->add during relocsym
|
||||||
r.Sym = nil
|
r.Sym = nil
|
||||||
return true
|
return true
|
||||||
}
|
}
|
||||||
|
|
@ -257,21 +257,21 @@ func elfreloc1(ctxt *ld.Link, r *ld.Reloc, sectoff int64) int {
|
||||||
default:
|
default:
|
||||||
return -1
|
return -1
|
||||||
|
|
||||||
case obj.R_ADDR:
|
case objabi.R_ADDR:
|
||||||
if r.Siz == 4 {
|
if r.Siz == 4 {
|
||||||
ld.Thearch.Lput(ld.R_ARM_ABS32 | uint32(elfsym)<<8)
|
ld.Thearch.Lput(ld.R_ARM_ABS32 | uint32(elfsym)<<8)
|
||||||
} else {
|
} else {
|
||||||
return -1
|
return -1
|
||||||
}
|
}
|
||||||
|
|
||||||
case obj.R_PCREL:
|
case objabi.R_PCREL:
|
||||||
if r.Siz == 4 {
|
if r.Siz == 4 {
|
||||||
ld.Thearch.Lput(ld.R_ARM_REL32 | uint32(elfsym)<<8)
|
ld.Thearch.Lput(ld.R_ARM_REL32 | uint32(elfsym)<<8)
|
||||||
} else {
|
} else {
|
||||||
return -1
|
return -1
|
||||||
}
|
}
|
||||||
|
|
||||||
case obj.R_CALLARM:
|
case objabi.R_CALLARM:
|
||||||
if r.Siz == 4 {
|
if r.Siz == 4 {
|
||||||
if r.Add&0xff000000 == 0xeb000000 { // BL
|
if r.Add&0xff000000 == 0xeb000000 { // BL
|
||||||
ld.Thearch.Lput(ld.R_ARM_CALL | uint32(elfsym)<<8)
|
ld.Thearch.Lput(ld.R_ARM_CALL | uint32(elfsym)<<8)
|
||||||
|
|
@ -282,13 +282,13 @@ func elfreloc1(ctxt *ld.Link, r *ld.Reloc, sectoff int64) int {
|
||||||
return -1
|
return -1
|
||||||
}
|
}
|
||||||
|
|
||||||
case obj.R_TLS_LE:
|
case objabi.R_TLS_LE:
|
||||||
ld.Thearch.Lput(ld.R_ARM_TLS_LE32 | uint32(elfsym)<<8)
|
ld.Thearch.Lput(ld.R_ARM_TLS_LE32 | uint32(elfsym)<<8)
|
||||||
|
|
||||||
case obj.R_TLS_IE:
|
case objabi.R_TLS_IE:
|
||||||
ld.Thearch.Lput(ld.R_ARM_TLS_IE32 | uint32(elfsym)<<8)
|
ld.Thearch.Lput(ld.R_ARM_TLS_IE32 | uint32(elfsym)<<8)
|
||||||
|
|
||||||
case obj.R_GOTPCREL:
|
case objabi.R_GOTPCREL:
|
||||||
if r.Siz == 4 {
|
if r.Siz == 4 {
|
||||||
ld.Thearch.Lput(ld.R_ARM_GOT_PREL | uint32(elfsym)<<8)
|
ld.Thearch.Lput(ld.R_ARM_GOT_PREL | uint32(elfsym)<<8)
|
||||||
} else {
|
} else {
|
||||||
|
|
@ -331,8 +331,8 @@ func machoreloc1(s *ld.Symbol, r *ld.Reloc, sectoff int64) int {
|
||||||
|
|
||||||
rs := r.Xsym
|
rs := r.Xsym
|
||||||
|
|
||||||
if r.Type == obj.R_PCREL {
|
if r.Type == objabi.R_PCREL {
|
||||||
if rs.Type == obj.SHOSTOBJ {
|
if rs.Type == objabi.SHOSTOBJ {
|
||||||
ld.Errorf(s, "pc-relative relocation of external symbol is not supported")
|
ld.Errorf(s, "pc-relative relocation of external symbol is not supported")
|
||||||
return -1
|
return -1
|
||||||
}
|
}
|
||||||
|
|
@ -361,7 +361,7 @@ func machoreloc1(s *ld.Symbol, r *ld.Reloc, sectoff int64) int {
|
||||||
return 0
|
return 0
|
||||||
}
|
}
|
||||||
|
|
||||||
if rs.Type == obj.SHOSTOBJ || r.Type == obj.R_CALLARM {
|
if rs.Type == objabi.SHOSTOBJ || r.Type == objabi.R_CALLARM {
|
||||||
if rs.Dynid < 0 {
|
if rs.Dynid < 0 {
|
||||||
ld.Errorf(s, "reloc %d to non-macho symbol %s type=%d", r.Type, rs.Name, rs.Type)
|
ld.Errorf(s, "reloc %d to non-macho symbol %s type=%d", r.Type, rs.Name, rs.Type)
|
||||||
return -1
|
return -1
|
||||||
|
|
@ -381,10 +381,10 @@ func machoreloc1(s *ld.Symbol, r *ld.Reloc, sectoff int64) int {
|
||||||
default:
|
default:
|
||||||
return -1
|
return -1
|
||||||
|
|
||||||
case obj.R_ADDR:
|
case objabi.R_ADDR:
|
||||||
v |= ld.MACHO_GENERIC_RELOC_VANILLA << 28
|
v |= ld.MACHO_GENERIC_RELOC_VANILLA << 28
|
||||||
|
|
||||||
case obj.R_CALLARM:
|
case objabi.R_CALLARM:
|
||||||
v |= 1 << 24 // pc-relative bit
|
v |= 1 << 24 // pc-relative bit
|
||||||
v |= ld.MACHO_ARM_RELOC_BR24 << 28
|
v |= ld.MACHO_ARM_RELOC_BR24 << 28
|
||||||
}
|
}
|
||||||
|
|
@ -430,7 +430,7 @@ func immrot(v uint32) uint32 {
|
||||||
// Convert the direct jump relocation r to refer to a trampoline if the target is too far
|
// Convert the direct jump relocation r to refer to a trampoline if the target is too far
|
||||||
func trampoline(ctxt *ld.Link, r *ld.Reloc, s *ld.Symbol) {
|
func trampoline(ctxt *ld.Link, r *ld.Reloc, s *ld.Symbol) {
|
||||||
switch r.Type {
|
switch r.Type {
|
||||||
case obj.R_CALLARM:
|
case objabi.R_CALLARM:
|
||||||
// r.Add is the instruction
|
// r.Add is the instruction
|
||||||
// low 24-bit encodes the target address
|
// low 24-bit encodes the target address
|
||||||
t := (ld.Symaddr(r.Sym) + int64(signext24(r.Add&0xffffff)*4) - (s.Value + int64(r.Off))) / 4
|
t := (ld.Symaddr(r.Sym) + int64(signext24(r.Add&0xffffff)*4) - (s.Value + int64(r.Off))) / 4
|
||||||
|
|
@ -443,7 +443,7 @@ func trampoline(ctxt *ld.Link, r *ld.Reloc, s *ld.Symbol) {
|
||||||
for i := 0; ; i++ {
|
for i := 0; ; i++ {
|
||||||
name := r.Sym.Name + fmt.Sprintf("%+d-tramp%d", offset, i)
|
name := r.Sym.Name + fmt.Sprintf("%+d-tramp%d", offset, i)
|
||||||
tramp = ctxt.Syms.Lookup(name, int(r.Sym.Version))
|
tramp = ctxt.Syms.Lookup(name, int(r.Sym.Version))
|
||||||
if tramp.Type == obj.SDYNIMPORT {
|
if tramp.Type == objabi.SDYNIMPORT {
|
||||||
// don't reuse trampoline defined in other module
|
// don't reuse trampoline defined in other module
|
||||||
continue
|
continue
|
||||||
}
|
}
|
||||||
|
|
@ -500,7 +500,7 @@ func gentramp(tramp, target *ld.Symbol, offset int64) {
|
||||||
if ld.Linkmode == ld.LinkExternal {
|
if ld.Linkmode == ld.LinkExternal {
|
||||||
r := ld.Addrel(tramp)
|
r := ld.Addrel(tramp)
|
||||||
r.Off = 8
|
r.Off = 8
|
||||||
r.Type = obj.R_ADDR
|
r.Type = objabi.R_ADDR
|
||||||
r.Siz = 4
|
r.Siz = 4
|
||||||
r.Sym = target
|
r.Sym = target
|
||||||
r.Add = offset
|
r.Add = offset
|
||||||
|
|
@ -522,7 +522,7 @@ func gentramppic(tramp, target *ld.Symbol, offset int64) {
|
||||||
|
|
||||||
r := ld.Addrel(tramp)
|
r := ld.Addrel(tramp)
|
||||||
r.Off = 12
|
r.Off = 12
|
||||||
r.Type = obj.R_PCREL
|
r.Type = objabi.R_PCREL
|
||||||
r.Siz = 4
|
r.Siz = 4
|
||||||
r.Sym = target
|
r.Sym = target
|
||||||
r.Add = offset + 4
|
r.Add = offset + 4
|
||||||
|
|
@ -557,7 +557,7 @@ func gentrampdyn(tramp, target *ld.Symbol, offset int64) {
|
||||||
|
|
||||||
r := ld.Addrel(tramp)
|
r := ld.Addrel(tramp)
|
||||||
r.Off = 16
|
r.Off = 16
|
||||||
r.Type = obj.R_GOTPCREL
|
r.Type = objabi.R_GOTPCREL
|
||||||
r.Siz = 4
|
r.Siz = 4
|
||||||
r.Sym = target
|
r.Sym = target
|
||||||
r.Add = 8
|
r.Add = 8
|
||||||
|
|
@ -571,7 +571,7 @@ func gentrampdyn(tramp, target *ld.Symbol, offset int64) {
|
||||||
func archreloc(ctxt *ld.Link, r *ld.Reloc, s *ld.Symbol, val *int64) int {
|
func archreloc(ctxt *ld.Link, r *ld.Reloc, s *ld.Symbol, val *int64) int {
|
||||||
if ld.Linkmode == ld.LinkExternal {
|
if ld.Linkmode == ld.LinkExternal {
|
||||||
switch r.Type {
|
switch r.Type {
|
||||||
case obj.R_CALLARM:
|
case objabi.R_CALLARM:
|
||||||
r.Done = 0
|
r.Done = 0
|
||||||
|
|
||||||
// set up addend for eventual relocation via outer symbol.
|
// set up addend for eventual relocation via outer symbol.
|
||||||
|
|
@ -584,7 +584,7 @@ func archreloc(ctxt *ld.Link, r *ld.Reloc, s *ld.Symbol, val *int64) int {
|
||||||
rs = rs.Outer
|
rs = rs.Outer
|
||||||
}
|
}
|
||||||
|
|
||||||
if rs.Type != obj.SHOSTOBJ && rs.Type != obj.SDYNIMPORT && rs.Sect == nil {
|
if rs.Type != objabi.SHOSTOBJ && rs.Type != objabi.SDYNIMPORT && rs.Sect == nil {
|
||||||
ld.Errorf(s, "missing section for %s", rs.Name)
|
ld.Errorf(s, "missing section for %s", rs.Name)
|
||||||
}
|
}
|
||||||
r.Xsym = rs
|
r.Xsym = rs
|
||||||
|
|
@ -594,7 +594,7 @@ func archreloc(ctxt *ld.Link, r *ld.Reloc, s *ld.Symbol, val *int64) int {
|
||||||
// the section load address.
|
// the section load address.
|
||||||
// we need to compensate that by removing the instruction's address
|
// we need to compensate that by removing the instruction's address
|
||||||
// from addend.
|
// from addend.
|
||||||
if ld.Headtype == obj.Hdarwin {
|
if ld.Headtype == objabi.Hdarwin {
|
||||||
r.Xadd -= ld.Symaddr(s) + int64(r.Off)
|
r.Xadd -= ld.Symaddr(s) + int64(r.Off)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -610,34 +610,34 @@ func archreloc(ctxt *ld.Link, r *ld.Reloc, s *ld.Symbol, val *int64) int {
|
||||||
}
|
}
|
||||||
|
|
||||||
switch r.Type {
|
switch r.Type {
|
||||||
case obj.R_CONST:
|
case objabi.R_CONST:
|
||||||
*val = r.Add
|
*val = r.Add
|
||||||
return 0
|
return 0
|
||||||
|
|
||||||
case obj.R_GOTOFF:
|
case objabi.R_GOTOFF:
|
||||||
*val = ld.Symaddr(r.Sym) + r.Add - ld.Symaddr(ctxt.Syms.Lookup(".got", 0))
|
*val = ld.Symaddr(r.Sym) + r.Add - ld.Symaddr(ctxt.Syms.Lookup(".got", 0))
|
||||||
return 0
|
return 0
|
||||||
|
|
||||||
// The following three arch specific relocations are only for generation of
|
// The following three arch specific relocations are only for generation of
|
||||||
// Linux/ARM ELF's PLT entry (3 assembler instruction)
|
// Linux/ARM ELF's PLT entry (3 assembler instruction)
|
||||||
case obj.R_PLT0: // add ip, pc, #0xXX00000
|
case objabi.R_PLT0: // add ip, pc, #0xXX00000
|
||||||
if ld.Symaddr(ctxt.Syms.Lookup(".got.plt", 0)) < ld.Symaddr(ctxt.Syms.Lookup(".plt", 0)) {
|
if ld.Symaddr(ctxt.Syms.Lookup(".got.plt", 0)) < ld.Symaddr(ctxt.Syms.Lookup(".plt", 0)) {
|
||||||
ld.Errorf(s, ".got.plt should be placed after .plt section.")
|
ld.Errorf(s, ".got.plt should be placed after .plt section.")
|
||||||
}
|
}
|
||||||
*val = 0xe28fc600 + (0xff & (int64(uint32(ld.Symaddr(r.Sym)-(ld.Symaddr(ctxt.Syms.Lookup(".plt", 0))+int64(r.Off))+r.Add)) >> 20))
|
*val = 0xe28fc600 + (0xff & (int64(uint32(ld.Symaddr(r.Sym)-(ld.Symaddr(ctxt.Syms.Lookup(".plt", 0))+int64(r.Off))+r.Add)) >> 20))
|
||||||
return 0
|
return 0
|
||||||
|
|
||||||
case obj.R_PLT1: // add ip, ip, #0xYY000
|
case objabi.R_PLT1: // add ip, ip, #0xYY000
|
||||||
*val = 0xe28cca00 + (0xff & (int64(uint32(ld.Symaddr(r.Sym)-(ld.Symaddr(ctxt.Syms.Lookup(".plt", 0))+int64(r.Off))+r.Add+4)) >> 12))
|
*val = 0xe28cca00 + (0xff & (int64(uint32(ld.Symaddr(r.Sym)-(ld.Symaddr(ctxt.Syms.Lookup(".plt", 0))+int64(r.Off))+r.Add+4)) >> 12))
|
||||||
|
|
||||||
return 0
|
return 0
|
||||||
|
|
||||||
case obj.R_PLT2: // ldr pc, [ip, #0xZZZ]!
|
case objabi.R_PLT2: // ldr pc, [ip, #0xZZZ]!
|
||||||
*val = 0xe5bcf000 + (0xfff & int64(uint32(ld.Symaddr(r.Sym)-(ld.Symaddr(ctxt.Syms.Lookup(".plt", 0))+int64(r.Off))+r.Add+8)))
|
*val = 0xe5bcf000 + (0xfff & int64(uint32(ld.Symaddr(r.Sym)-(ld.Symaddr(ctxt.Syms.Lookup(".plt", 0))+int64(r.Off))+r.Add+8)))
|
||||||
|
|
||||||
return 0
|
return 0
|
||||||
|
|
||||||
case obj.R_CALLARM: // bl XXXXXX or b YYYYYY
|
case objabi.R_CALLARM: // bl XXXXXX or b YYYYYY
|
||||||
// r.Add is the instruction
|
// r.Add is the instruction
|
||||||
// low 24-bit encodes the target address
|
// low 24-bit encodes the target address
|
||||||
t := (ld.Symaddr(r.Sym) + int64(signext24(r.Add&0xffffff)*4) - (s.Value + int64(r.Off))) / 4
|
t := (ld.Symaddr(r.Sym) + int64(signext24(r.Add&0xffffff)*4) - (s.Value + int64(r.Off))) / 4
|
||||||
|
|
@ -657,7 +657,7 @@ func archrelocvariant(ctxt *ld.Link, r *ld.Reloc, s *ld.Symbol, t int64) int64 {
|
||||||
return t
|
return t
|
||||||
}
|
}
|
||||||
|
|
||||||
func addpltreloc(ctxt *ld.Link, plt *ld.Symbol, got *ld.Symbol, sym *ld.Symbol, typ obj.RelocType) *ld.Reloc {
|
func addpltreloc(ctxt *ld.Link, plt *ld.Symbol, got *ld.Symbol, sym *ld.Symbol, typ objabi.RelocType) *ld.Reloc {
|
||||||
r := ld.Addrel(plt)
|
r := ld.Addrel(plt)
|
||||||
r.Sym = got
|
r.Sym = got
|
||||||
r.Off = int32(plt.Size)
|
r.Off = int32(plt.Size)
|
||||||
|
|
@ -698,9 +698,9 @@ func addpltsym(ctxt *ld.Link, s *ld.Symbol) {
|
||||||
// .plt entry, this depends on the .got entry
|
// .plt entry, this depends on the .got entry
|
||||||
s.Plt = int32(plt.Size)
|
s.Plt = int32(plt.Size)
|
||||||
|
|
||||||
addpltreloc(ctxt, plt, got, s, obj.R_PLT0) // add lr, pc, #0xXX00000
|
addpltreloc(ctxt, plt, got, s, objabi.R_PLT0) // add lr, pc, #0xXX00000
|
||||||
addpltreloc(ctxt, plt, got, s, obj.R_PLT1) // add lr, lr, #0xYY000
|
addpltreloc(ctxt, plt, got, s, objabi.R_PLT1) // add lr, lr, #0xYY000
|
||||||
addpltreloc(ctxt, plt, got, s, obj.R_PLT2) // ldr pc, [lr, #0xZZZ]!
|
addpltreloc(ctxt, plt, got, s, objabi.R_PLT2) // ldr pc, [lr, #0xZZZ]!
|
||||||
|
|
||||||
// rel
|
// rel
|
||||||
ld.Addaddrplus(ctxt, rel, got, int64(s.Got))
|
ld.Addaddrplus(ctxt, rel, got, int64(s.Got))
|
||||||
|
|
@ -748,7 +748,7 @@ func addgotsym(ctxt *ld.Link, s *ld.Symbol) {
|
||||||
|
|
||||||
func asmb(ctxt *ld.Link) {
|
func asmb(ctxt *ld.Link) {
|
||||||
if ctxt.Debugvlog != 0 {
|
if ctxt.Debugvlog != 0 {
|
||||||
ctxt.Logf("%5.2f asmb\n", obj.Cputime())
|
ctxt.Logf("%5.2f asmb\n", ld.Cputime())
|
||||||
}
|
}
|
||||||
|
|
||||||
if ld.Iself {
|
if ld.Iself {
|
||||||
|
|
@ -765,21 +765,21 @@ func asmb(ctxt *ld.Link) {
|
||||||
|
|
||||||
if ld.Segrodata.Filelen > 0 {
|
if ld.Segrodata.Filelen > 0 {
|
||||||
if ctxt.Debugvlog != 0 {
|
if ctxt.Debugvlog != 0 {
|
||||||
ctxt.Logf("%5.2f rodatblk\n", obj.Cputime())
|
ctxt.Logf("%5.2f rodatblk\n", ld.Cputime())
|
||||||
}
|
}
|
||||||
ld.Cseek(int64(ld.Segrodata.Fileoff))
|
ld.Cseek(int64(ld.Segrodata.Fileoff))
|
||||||
ld.Datblk(ctxt, int64(ld.Segrodata.Vaddr), int64(ld.Segrodata.Filelen))
|
ld.Datblk(ctxt, int64(ld.Segrodata.Vaddr), int64(ld.Segrodata.Filelen))
|
||||||
}
|
}
|
||||||
if ld.Segrelrodata.Filelen > 0 {
|
if ld.Segrelrodata.Filelen > 0 {
|
||||||
if ctxt.Debugvlog != 0 {
|
if ctxt.Debugvlog != 0 {
|
||||||
ctxt.Logf("%5.2f relrodatblk\n", obj.Cputime())
|
ctxt.Logf("%5.2f relrodatblk\n", ld.Cputime())
|
||||||
}
|
}
|
||||||
ld.Cseek(int64(ld.Segrelrodata.Fileoff))
|
ld.Cseek(int64(ld.Segrelrodata.Fileoff))
|
||||||
ld.Datblk(ctxt, int64(ld.Segrelrodata.Vaddr), int64(ld.Segrelrodata.Filelen))
|
ld.Datblk(ctxt, int64(ld.Segrelrodata.Vaddr), int64(ld.Segrelrodata.Filelen))
|
||||||
}
|
}
|
||||||
|
|
||||||
if ctxt.Debugvlog != 0 {
|
if ctxt.Debugvlog != 0 {
|
||||||
ctxt.Logf("%5.2f datblk\n", obj.Cputime())
|
ctxt.Logf("%5.2f datblk\n", ld.Cputime())
|
||||||
}
|
}
|
||||||
|
|
||||||
ld.Cseek(int64(ld.Segdata.Fileoff))
|
ld.Cseek(int64(ld.Segdata.Fileoff))
|
||||||
|
|
@ -789,7 +789,7 @@ func asmb(ctxt *ld.Link) {
|
||||||
ld.Dwarfblk(ctxt, int64(ld.Segdwarf.Vaddr), int64(ld.Segdwarf.Filelen))
|
ld.Dwarfblk(ctxt, int64(ld.Segdwarf.Vaddr), int64(ld.Segdwarf.Filelen))
|
||||||
|
|
||||||
machlink := uint32(0)
|
machlink := uint32(0)
|
||||||
if ld.Headtype == obj.Hdarwin {
|
if ld.Headtype == objabi.Hdarwin {
|
||||||
machlink = uint32(ld.Domacholink(ctxt))
|
machlink = uint32(ld.Domacholink(ctxt))
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -801,7 +801,7 @@ func asmb(ctxt *ld.Link) {
|
||||||
if !*ld.FlagS {
|
if !*ld.FlagS {
|
||||||
// TODO: rationalize
|
// TODO: rationalize
|
||||||
if ctxt.Debugvlog != 0 {
|
if ctxt.Debugvlog != 0 {
|
||||||
ctxt.Logf("%5.2f sym\n", obj.Cputime())
|
ctxt.Logf("%5.2f sym\n", ld.Cputime())
|
||||||
}
|
}
|
||||||
switch ld.Headtype {
|
switch ld.Headtype {
|
||||||
default:
|
default:
|
||||||
|
|
@ -810,10 +810,10 @@ func asmb(ctxt *ld.Link) {
|
||||||
symo = uint32(ld.Rnd(int64(symo), int64(*ld.FlagRound)))
|
symo = uint32(ld.Rnd(int64(symo), int64(*ld.FlagRound)))
|
||||||
}
|
}
|
||||||
|
|
||||||
case obj.Hplan9:
|
case objabi.Hplan9:
|
||||||
symo = uint32(ld.Segdata.Fileoff + ld.Segdata.Filelen)
|
symo = uint32(ld.Segdata.Fileoff + ld.Segdata.Filelen)
|
||||||
|
|
||||||
case obj.Hdarwin:
|
case objabi.Hdarwin:
|
||||||
symo = uint32(ld.Segdwarf.Fileoff + uint64(ld.Rnd(int64(ld.Segdwarf.Filelen), int64(*ld.FlagRound))) + uint64(machlink))
|
symo = uint32(ld.Segdwarf.Fileoff + uint64(ld.Rnd(int64(ld.Segdwarf.Filelen), int64(*ld.FlagRound))) + uint64(machlink))
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -822,7 +822,7 @@ func asmb(ctxt *ld.Link) {
|
||||||
default:
|
default:
|
||||||
if ld.Iself {
|
if ld.Iself {
|
||||||
if ctxt.Debugvlog != 0 {
|
if ctxt.Debugvlog != 0 {
|
||||||
ctxt.Logf("%5.2f elfsym\n", obj.Cputime())
|
ctxt.Logf("%5.2f elfsym\n", ld.Cputime())
|
||||||
}
|
}
|
||||||
ld.Asmelfsym(ctxt)
|
ld.Asmelfsym(ctxt)
|
||||||
ld.Cflush()
|
ld.Cflush()
|
||||||
|
|
@ -833,7 +833,7 @@ func asmb(ctxt *ld.Link) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
case obj.Hplan9:
|
case objabi.Hplan9:
|
||||||
ld.Asmplan9sym(ctxt)
|
ld.Asmplan9sym(ctxt)
|
||||||
ld.Cflush()
|
ld.Cflush()
|
||||||
|
|
||||||
|
|
@ -847,7 +847,7 @@ func asmb(ctxt *ld.Link) {
|
||||||
ld.Cflush()
|
ld.Cflush()
|
||||||
}
|
}
|
||||||
|
|
||||||
case obj.Hdarwin:
|
case objabi.Hdarwin:
|
||||||
if ld.Linkmode == ld.LinkExternal {
|
if ld.Linkmode == ld.LinkExternal {
|
||||||
ld.Machoemitreloc(ctxt)
|
ld.Machoemitreloc(ctxt)
|
||||||
}
|
}
|
||||||
|
|
@ -855,12 +855,12 @@ func asmb(ctxt *ld.Link) {
|
||||||
}
|
}
|
||||||
|
|
||||||
if ctxt.Debugvlog != 0 {
|
if ctxt.Debugvlog != 0 {
|
||||||
ctxt.Logf("%5.2f header\n", obj.Cputime())
|
ctxt.Logf("%5.2f header\n", ld.Cputime())
|
||||||
}
|
}
|
||||||
ld.Cseek(0)
|
ld.Cseek(0)
|
||||||
switch ld.Headtype {
|
switch ld.Headtype {
|
||||||
default:
|
default:
|
||||||
case obj.Hplan9: /* plan 9 */
|
case objabi.Hplan9: /* plan 9 */
|
||||||
ld.Lputb(0x647) /* magic */
|
ld.Lputb(0x647) /* magic */
|
||||||
ld.Lputb(uint32(ld.Segtext.Filelen)) /* sizes */
|
ld.Lputb(uint32(ld.Segtext.Filelen)) /* sizes */
|
||||||
ld.Lputb(uint32(ld.Segdata.Filelen))
|
ld.Lputb(uint32(ld.Segdata.Filelen))
|
||||||
|
|
@ -870,14 +870,14 @@ func asmb(ctxt *ld.Link) {
|
||||||
ld.Lputb(0)
|
ld.Lputb(0)
|
||||||
ld.Lputb(uint32(ld.Lcsize))
|
ld.Lputb(uint32(ld.Lcsize))
|
||||||
|
|
||||||
case obj.Hlinux,
|
case objabi.Hlinux,
|
||||||
obj.Hfreebsd,
|
objabi.Hfreebsd,
|
||||||
obj.Hnetbsd,
|
objabi.Hnetbsd,
|
||||||
obj.Hopenbsd,
|
objabi.Hopenbsd,
|
||||||
obj.Hnacl:
|
objabi.Hnacl:
|
||||||
ld.Asmbelf(ctxt, int64(symo))
|
ld.Asmbelf(ctxt, int64(symo))
|
||||||
|
|
||||||
case obj.Hdarwin:
|
case objabi.Hdarwin:
|
||||||
ld.Asmbmacho(ctxt)
|
ld.Asmbmacho(ctxt)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -31,7 +31,7 @@
|
||||||
package arm
|
package arm
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"cmd/internal/obj"
|
"cmd/internal/objabi"
|
||||||
"cmd/internal/sys"
|
"cmd/internal/sys"
|
||||||
"cmd/link/internal/ld"
|
"cmd/link/internal/ld"
|
||||||
"fmt"
|
"fmt"
|
||||||
|
|
@ -76,7 +76,7 @@ func archinit(ctxt *ld.Link) {
|
||||||
default:
|
default:
|
||||||
ld.Exitf("unknown -H option: %v", ld.Headtype)
|
ld.Exitf("unknown -H option: %v", ld.Headtype)
|
||||||
|
|
||||||
case obj.Hplan9: /* plan 9 */
|
case objabi.Hplan9: /* plan 9 */
|
||||||
ld.HEADR = 32
|
ld.HEADR = 32
|
||||||
|
|
||||||
if *ld.FlagTextAddr == -1 {
|
if *ld.FlagTextAddr == -1 {
|
||||||
|
|
@ -89,10 +89,10 @@ func archinit(ctxt *ld.Link) {
|
||||||
*ld.FlagRound = 4096
|
*ld.FlagRound = 4096
|
||||||
}
|
}
|
||||||
|
|
||||||
case obj.Hlinux, /* arm elf */
|
case objabi.Hlinux, /* arm elf */
|
||||||
obj.Hfreebsd,
|
objabi.Hfreebsd,
|
||||||
obj.Hnetbsd,
|
objabi.Hnetbsd,
|
||||||
obj.Hopenbsd:
|
objabi.Hopenbsd:
|
||||||
*ld.FlagD = false
|
*ld.FlagD = false
|
||||||
// with dynamic linking
|
// with dynamic linking
|
||||||
ld.Elfinit(ctxt)
|
ld.Elfinit(ctxt)
|
||||||
|
|
@ -107,7 +107,7 @@ func archinit(ctxt *ld.Link) {
|
||||||
*ld.FlagRound = 0x10000
|
*ld.FlagRound = 0x10000
|
||||||
}
|
}
|
||||||
|
|
||||||
case obj.Hnacl:
|
case objabi.Hnacl:
|
||||||
ld.Elfinit(ctxt)
|
ld.Elfinit(ctxt)
|
||||||
ld.HEADR = 0x10000
|
ld.HEADR = 0x10000
|
||||||
ld.Funcalign = 16
|
ld.Funcalign = 16
|
||||||
|
|
@ -121,7 +121,7 @@ func archinit(ctxt *ld.Link) {
|
||||||
*ld.FlagRound = 0x10000
|
*ld.FlagRound = 0x10000
|
||||||
}
|
}
|
||||||
|
|
||||||
case obj.Hdarwin: /* apple MACH */
|
case objabi.Hdarwin: /* apple MACH */
|
||||||
*ld.FlagW = true // disable DWARF generation
|
*ld.FlagW = true // disable DWARF generation
|
||||||
ld.Machoinit()
|
ld.Machoinit()
|
||||||
ld.HEADR = ld.INITIAL_MACHO_HEADR
|
ld.HEADR = ld.INITIAL_MACHO_HEADR
|
||||||
|
|
|
||||||
|
|
@ -31,7 +31,7 @@
|
||||||
package arm64
|
package arm64
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"cmd/internal/obj"
|
"cmd/internal/objabi"
|
||||||
"cmd/link/internal/ld"
|
"cmd/link/internal/ld"
|
||||||
"encoding/binary"
|
"encoding/binary"
|
||||||
"fmt"
|
"fmt"
|
||||||
|
|
@ -43,14 +43,14 @@ func gentext(ctxt *ld.Link) {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
addmoduledata := ctxt.Syms.Lookup("runtime.addmoduledata", 0)
|
addmoduledata := ctxt.Syms.Lookup("runtime.addmoduledata", 0)
|
||||||
if addmoduledata.Type == obj.STEXT {
|
if addmoduledata.Type == objabi.STEXT {
|
||||||
// we're linking a module containing the runtime -> no need for
|
// we're linking a module containing the runtime -> no need for
|
||||||
// an init function
|
// an init function
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
addmoduledata.Attr |= ld.AttrReachable
|
addmoduledata.Attr |= ld.AttrReachable
|
||||||
initfunc := ctxt.Syms.Lookup("go.link.addmoduledata", 0)
|
initfunc := ctxt.Syms.Lookup("go.link.addmoduledata", 0)
|
||||||
initfunc.Type = obj.STEXT
|
initfunc.Type = objabi.STEXT
|
||||||
initfunc.Attr |= ld.AttrLocal
|
initfunc.Attr |= ld.AttrLocal
|
||||||
initfunc.Attr |= ld.AttrReachable
|
initfunc.Attr |= ld.AttrReachable
|
||||||
o := func(op uint32) {
|
o := func(op uint32) {
|
||||||
|
|
@ -67,7 +67,7 @@ func gentext(ctxt *ld.Link) {
|
||||||
rel.Off = 0
|
rel.Off = 0
|
||||||
rel.Siz = 8
|
rel.Siz = 8
|
||||||
rel.Sym = ctxt.Moduledata
|
rel.Sym = ctxt.Moduledata
|
||||||
rel.Type = obj.R_ADDRARM64
|
rel.Type = objabi.R_ADDRARM64
|
||||||
|
|
||||||
// 8: 14000000 bl 0 <runtime.addmoduledata>
|
// 8: 14000000 bl 0 <runtime.addmoduledata>
|
||||||
// 8: R_AARCH64_CALL26 runtime.addmoduledata
|
// 8: R_AARCH64_CALL26 runtime.addmoduledata
|
||||||
|
|
@ -76,13 +76,13 @@ func gentext(ctxt *ld.Link) {
|
||||||
rel.Off = 8
|
rel.Off = 8
|
||||||
rel.Siz = 4
|
rel.Siz = 4
|
||||||
rel.Sym = ctxt.Syms.Lookup("runtime.addmoduledata", 0)
|
rel.Sym = ctxt.Syms.Lookup("runtime.addmoduledata", 0)
|
||||||
rel.Type = obj.R_CALLARM64 // Really should be R_AARCH64_JUMP26 but doesn't seem to make any difference
|
rel.Type = objabi.R_CALLARM64 // Really should be R_AARCH64_JUMP26 but doesn't seem to make any difference
|
||||||
|
|
||||||
ctxt.Textp = append(ctxt.Textp, initfunc)
|
ctxt.Textp = append(ctxt.Textp, initfunc)
|
||||||
initarray_entry := ctxt.Syms.Lookup("go.link.addmoduledatainit", 0)
|
initarray_entry := ctxt.Syms.Lookup("go.link.addmoduledatainit", 0)
|
||||||
initarray_entry.Attr |= ld.AttrReachable
|
initarray_entry.Attr |= ld.AttrReachable
|
||||||
initarray_entry.Attr |= ld.AttrLocal
|
initarray_entry.Attr |= ld.AttrLocal
|
||||||
initarray_entry.Type = obj.SINITARR
|
initarray_entry.Type = objabi.SINITARR
|
||||||
ld.Addaddr(ctxt, initarray_entry, initfunc)
|
ld.Addaddr(ctxt, initarray_entry, initfunc)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -99,7 +99,7 @@ func elfreloc1(ctxt *ld.Link, r *ld.Reloc, sectoff int64) int {
|
||||||
default:
|
default:
|
||||||
return -1
|
return -1
|
||||||
|
|
||||||
case obj.R_ADDR:
|
case objabi.R_ADDR:
|
||||||
switch r.Siz {
|
switch r.Siz {
|
||||||
case 4:
|
case 4:
|
||||||
ld.Thearch.Vput(ld.R_AARCH64_ABS32 | uint64(elfsym)<<32)
|
ld.Thearch.Vput(ld.R_AARCH64_ABS32 | uint64(elfsym)<<32)
|
||||||
|
|
@ -109,29 +109,29 @@ func elfreloc1(ctxt *ld.Link, r *ld.Reloc, sectoff int64) int {
|
||||||
return -1
|
return -1
|
||||||
}
|
}
|
||||||
|
|
||||||
case obj.R_ADDRARM64:
|
case objabi.R_ADDRARM64:
|
||||||
// two relocations: R_AARCH64_ADR_PREL_PG_HI21 and R_AARCH64_ADD_ABS_LO12_NC
|
// two relocations: R_AARCH64_ADR_PREL_PG_HI21 and R_AARCH64_ADD_ABS_LO12_NC
|
||||||
ld.Thearch.Vput(ld.R_AARCH64_ADR_PREL_PG_HI21 | uint64(elfsym)<<32)
|
ld.Thearch.Vput(ld.R_AARCH64_ADR_PREL_PG_HI21 | uint64(elfsym)<<32)
|
||||||
ld.Thearch.Vput(uint64(r.Xadd))
|
ld.Thearch.Vput(uint64(r.Xadd))
|
||||||
ld.Thearch.Vput(uint64(sectoff + 4))
|
ld.Thearch.Vput(uint64(sectoff + 4))
|
||||||
ld.Thearch.Vput(ld.R_AARCH64_ADD_ABS_LO12_NC | uint64(elfsym)<<32)
|
ld.Thearch.Vput(ld.R_AARCH64_ADD_ABS_LO12_NC | uint64(elfsym)<<32)
|
||||||
|
|
||||||
case obj.R_ARM64_TLS_LE:
|
case objabi.R_ARM64_TLS_LE:
|
||||||
ld.Thearch.Vput(ld.R_AARCH64_TLSLE_MOVW_TPREL_G0 | uint64(elfsym)<<32)
|
ld.Thearch.Vput(ld.R_AARCH64_TLSLE_MOVW_TPREL_G0 | uint64(elfsym)<<32)
|
||||||
|
|
||||||
case obj.R_ARM64_TLS_IE:
|
case objabi.R_ARM64_TLS_IE:
|
||||||
ld.Thearch.Vput(ld.R_AARCH64_TLSIE_ADR_GOTTPREL_PAGE21 | uint64(elfsym)<<32)
|
ld.Thearch.Vput(ld.R_AARCH64_TLSIE_ADR_GOTTPREL_PAGE21 | uint64(elfsym)<<32)
|
||||||
ld.Thearch.Vput(uint64(r.Xadd))
|
ld.Thearch.Vput(uint64(r.Xadd))
|
||||||
ld.Thearch.Vput(uint64(sectoff + 4))
|
ld.Thearch.Vput(uint64(sectoff + 4))
|
||||||
ld.Thearch.Vput(ld.R_AARCH64_TLSIE_LD64_GOTTPREL_LO12_NC | uint64(elfsym)<<32)
|
ld.Thearch.Vput(ld.R_AARCH64_TLSIE_LD64_GOTTPREL_LO12_NC | uint64(elfsym)<<32)
|
||||||
|
|
||||||
case obj.R_ARM64_GOTPCREL:
|
case objabi.R_ARM64_GOTPCREL:
|
||||||
ld.Thearch.Vput(ld.R_AARCH64_ADR_GOT_PAGE | uint64(elfsym)<<32)
|
ld.Thearch.Vput(ld.R_AARCH64_ADR_GOT_PAGE | uint64(elfsym)<<32)
|
||||||
ld.Thearch.Vput(uint64(r.Xadd))
|
ld.Thearch.Vput(uint64(r.Xadd))
|
||||||
ld.Thearch.Vput(uint64(sectoff + 4))
|
ld.Thearch.Vput(uint64(sectoff + 4))
|
||||||
ld.Thearch.Vput(ld.R_AARCH64_LD64_GOT_LO12_NC | uint64(elfsym)<<32)
|
ld.Thearch.Vput(ld.R_AARCH64_LD64_GOT_LO12_NC | uint64(elfsym)<<32)
|
||||||
|
|
||||||
case obj.R_CALLARM64:
|
case objabi.R_CALLARM64:
|
||||||
if r.Siz != 4 {
|
if r.Siz != 4 {
|
||||||
return -1
|
return -1
|
||||||
}
|
}
|
||||||
|
|
@ -156,7 +156,7 @@ func machoreloc1(s *ld.Symbol, r *ld.Reloc, sectoff int64) int {
|
||||||
// ld64 has a bug handling MACHO_ARM64_RELOC_UNSIGNED with !extern relocation.
|
// ld64 has a bug handling MACHO_ARM64_RELOC_UNSIGNED with !extern relocation.
|
||||||
// see cmd/internal/ld/data.go for details. The workaround is that don't use !extern
|
// see cmd/internal/ld/data.go for details. The workaround is that don't use !extern
|
||||||
// UNSIGNED relocation at all.
|
// UNSIGNED relocation at all.
|
||||||
if rs.Type == obj.SHOSTOBJ || r.Type == obj.R_CALLARM64 || r.Type == obj.R_ADDRARM64 || r.Type == obj.R_ADDR {
|
if rs.Type == objabi.SHOSTOBJ || r.Type == objabi.R_CALLARM64 || r.Type == objabi.R_ADDRARM64 || r.Type == objabi.R_ADDR {
|
||||||
if rs.Dynid < 0 {
|
if rs.Dynid < 0 {
|
||||||
ld.Errorf(s, "reloc %d to non-macho symbol %s type=%d", r.Type, rs.Name, rs.Type)
|
ld.Errorf(s, "reloc %d to non-macho symbol %s type=%d", r.Type, rs.Name, rs.Type)
|
||||||
return -1
|
return -1
|
||||||
|
|
@ -176,10 +176,10 @@ func machoreloc1(s *ld.Symbol, r *ld.Reloc, sectoff int64) int {
|
||||||
default:
|
default:
|
||||||
return -1
|
return -1
|
||||||
|
|
||||||
case obj.R_ADDR:
|
case objabi.R_ADDR:
|
||||||
v |= ld.MACHO_ARM64_RELOC_UNSIGNED << 28
|
v |= ld.MACHO_ARM64_RELOC_UNSIGNED << 28
|
||||||
|
|
||||||
case obj.R_CALLARM64:
|
case objabi.R_CALLARM64:
|
||||||
if r.Xadd != 0 {
|
if r.Xadd != 0 {
|
||||||
ld.Errorf(s, "ld64 doesn't allow BR26 reloc with non-zero addend: %s+%d", rs.Name, r.Xadd)
|
ld.Errorf(s, "ld64 doesn't allow BR26 reloc with non-zero addend: %s+%d", rs.Name, r.Xadd)
|
||||||
}
|
}
|
||||||
|
|
@ -187,7 +187,7 @@ func machoreloc1(s *ld.Symbol, r *ld.Reloc, sectoff int64) int {
|
||||||
v |= 1 << 24 // pc-relative bit
|
v |= 1 << 24 // pc-relative bit
|
||||||
v |= ld.MACHO_ARM64_RELOC_BRANCH26 << 28
|
v |= ld.MACHO_ARM64_RELOC_BRANCH26 << 28
|
||||||
|
|
||||||
case obj.R_ADDRARM64:
|
case objabi.R_ADDRARM64:
|
||||||
r.Siz = 4
|
r.Siz = 4
|
||||||
// Two relocation entries: MACHO_ARM64_RELOC_PAGEOFF12 MACHO_ARM64_RELOC_PAGE21
|
// Two relocation entries: MACHO_ARM64_RELOC_PAGEOFF12 MACHO_ARM64_RELOC_PAGE21
|
||||||
// if r.Xadd is non-zero, add two MACHO_ARM64_RELOC_ADDEND.
|
// if r.Xadd is non-zero, add two MACHO_ARM64_RELOC_ADDEND.
|
||||||
|
|
@ -233,7 +233,7 @@ func archreloc(ctxt *ld.Link, r *ld.Reloc, s *ld.Symbol, val *int64) int {
|
||||||
default:
|
default:
|
||||||
return -1
|
return -1
|
||||||
|
|
||||||
case obj.R_ARM64_GOTPCREL:
|
case objabi.R_ARM64_GOTPCREL:
|
||||||
var o1, o2 uint32
|
var o1, o2 uint32
|
||||||
if ctxt.Arch.ByteOrder == binary.BigEndian {
|
if ctxt.Arch.ByteOrder == binary.BigEndian {
|
||||||
o1 = uint32(*val >> 32)
|
o1 = uint32(*val >> 32)
|
||||||
|
|
@ -250,12 +250,12 @@ func archreloc(ctxt *ld.Link, r *ld.Reloc, s *ld.Symbol, val *int64) int {
|
||||||
// (https://sourceware.org/bugzilla/show_bug.cgi?id=18270). So
|
// (https://sourceware.org/bugzilla/show_bug.cgi?id=18270). So
|
||||||
// we convert the adrp; ld64 + R_ARM64_GOTPCREL into adrp;
|
// we convert the adrp; ld64 + R_ARM64_GOTPCREL into adrp;
|
||||||
// add + R_ADDRARM64.
|
// add + R_ADDRARM64.
|
||||||
if !(r.Sym.Version != 0 || (r.Sym.Type&obj.SHIDDEN != 0) || r.Sym.Attr.Local()) && r.Sym.Type == obj.STEXT && ctxt.DynlinkingGo() {
|
if !(r.Sym.Version != 0 || (r.Sym.Type&objabi.SHIDDEN != 0) || r.Sym.Attr.Local()) && r.Sym.Type == objabi.STEXT && ctxt.DynlinkingGo() {
|
||||||
if o2&0xffc00000 != 0xf9400000 {
|
if o2&0xffc00000 != 0xf9400000 {
|
||||||
ld.Errorf(s, "R_ARM64_GOTPCREL against unexpected instruction %x", o2)
|
ld.Errorf(s, "R_ARM64_GOTPCREL against unexpected instruction %x", o2)
|
||||||
}
|
}
|
||||||
o2 = 0x91000000 | (o2 & 0x000003ff)
|
o2 = 0x91000000 | (o2 & 0x000003ff)
|
||||||
r.Type = obj.R_ADDRARM64
|
r.Type = objabi.R_ADDRARM64
|
||||||
}
|
}
|
||||||
if ctxt.Arch.ByteOrder == binary.BigEndian {
|
if ctxt.Arch.ByteOrder == binary.BigEndian {
|
||||||
*val = int64(o1)<<32 | int64(o2)
|
*val = int64(o1)<<32 | int64(o2)
|
||||||
|
|
@ -264,7 +264,7 @@ func archreloc(ctxt *ld.Link, r *ld.Reloc, s *ld.Symbol, val *int64) int {
|
||||||
}
|
}
|
||||||
fallthrough
|
fallthrough
|
||||||
|
|
||||||
case obj.R_ADDRARM64:
|
case objabi.R_ADDRARM64:
|
||||||
r.Done = 0
|
r.Done = 0
|
||||||
|
|
||||||
// set up addend for eventual relocation via outer symbol.
|
// set up addend for eventual relocation via outer symbol.
|
||||||
|
|
@ -275,7 +275,7 @@ func archreloc(ctxt *ld.Link, r *ld.Reloc, s *ld.Symbol, val *int64) int {
|
||||||
rs = rs.Outer
|
rs = rs.Outer
|
||||||
}
|
}
|
||||||
|
|
||||||
if rs.Type != obj.SHOSTOBJ && rs.Type != obj.SDYNIMPORT && rs.Sect == nil {
|
if rs.Type != objabi.SHOSTOBJ && rs.Type != objabi.SDYNIMPORT && rs.Sect == nil {
|
||||||
ld.Errorf(s, "missing section for %s", rs.Name)
|
ld.Errorf(s, "missing section for %s", rs.Name)
|
||||||
}
|
}
|
||||||
r.Xsym = rs
|
r.Xsym = rs
|
||||||
|
|
@ -285,7 +285,7 @@ func archreloc(ctxt *ld.Link, r *ld.Reloc, s *ld.Symbol, val *int64) int {
|
||||||
// the BR26 relocation should be fully resolved at link time.
|
// the BR26 relocation should be fully resolved at link time.
|
||||||
// That is the reason why the next if block is disabled. When the bug in ld64
|
// That is the reason why the next if block is disabled. When the bug in ld64
|
||||||
// is fixed, we can enable this block and also enable duff's device in cmd/7g.
|
// is fixed, we can enable this block and also enable duff's device in cmd/7g.
|
||||||
if false && ld.Headtype == obj.Hdarwin {
|
if false && ld.Headtype == objabi.Hdarwin {
|
||||||
var o0, o1 uint32
|
var o0, o1 uint32
|
||||||
|
|
||||||
if ctxt.Arch.ByteOrder == binary.BigEndian {
|
if ctxt.Arch.ByteOrder == binary.BigEndian {
|
||||||
|
|
@ -314,9 +314,9 @@ func archreloc(ctxt *ld.Link, r *ld.Reloc, s *ld.Symbol, val *int64) int {
|
||||||
|
|
||||||
return 0
|
return 0
|
||||||
|
|
||||||
case obj.R_CALLARM64,
|
case objabi.R_CALLARM64,
|
||||||
obj.R_ARM64_TLS_LE,
|
objabi.R_ARM64_TLS_LE,
|
||||||
obj.R_ARM64_TLS_IE:
|
objabi.R_ARM64_TLS_IE:
|
||||||
r.Done = 0
|
r.Done = 0
|
||||||
r.Xsym = r.Sym
|
r.Xsym = r.Sym
|
||||||
r.Xadd = r.Add
|
r.Xadd = r.Add
|
||||||
|
|
@ -325,15 +325,15 @@ func archreloc(ctxt *ld.Link, r *ld.Reloc, s *ld.Symbol, val *int64) int {
|
||||||
}
|
}
|
||||||
|
|
||||||
switch r.Type {
|
switch r.Type {
|
||||||
case obj.R_CONST:
|
case objabi.R_CONST:
|
||||||
*val = r.Add
|
*val = r.Add
|
||||||
return 0
|
return 0
|
||||||
|
|
||||||
case obj.R_GOTOFF:
|
case objabi.R_GOTOFF:
|
||||||
*val = ld.Symaddr(r.Sym) + r.Add - ld.Symaddr(ctxt.Syms.Lookup(".got", 0))
|
*val = ld.Symaddr(r.Sym) + r.Add - ld.Symaddr(ctxt.Syms.Lookup(".got", 0))
|
||||||
return 0
|
return 0
|
||||||
|
|
||||||
case obj.R_ADDRARM64:
|
case objabi.R_ADDRARM64:
|
||||||
t := ld.Symaddr(r.Sym) + r.Add - ((s.Value + int64(r.Off)) &^ 0xfff)
|
t := ld.Symaddr(r.Sym) + r.Add - ((s.Value + int64(r.Off)) &^ 0xfff)
|
||||||
if t >= 1<<32 || t < -1<<32 {
|
if t >= 1<<32 || t < -1<<32 {
|
||||||
ld.Errorf(s, "program too large, address relocation distance = %d", t)
|
ld.Errorf(s, "program too large, address relocation distance = %d", t)
|
||||||
|
|
@ -360,9 +360,9 @@ func archreloc(ctxt *ld.Link, r *ld.Reloc, s *ld.Symbol, val *int64) int {
|
||||||
}
|
}
|
||||||
return 0
|
return 0
|
||||||
|
|
||||||
case obj.R_ARM64_TLS_LE:
|
case objabi.R_ARM64_TLS_LE:
|
||||||
r.Done = 0
|
r.Done = 0
|
||||||
if ld.Headtype != obj.Hlinux {
|
if ld.Headtype != objabi.Hlinux {
|
||||||
ld.Errorf(s, "TLS reloc on unsupported OS %v", ld.Headtype)
|
ld.Errorf(s, "TLS reloc on unsupported OS %v", ld.Headtype)
|
||||||
}
|
}
|
||||||
// The TCB is two pointers. This is not documented anywhere, but is
|
// The TCB is two pointers. This is not documented anywhere, but is
|
||||||
|
|
@ -374,7 +374,7 @@ func archreloc(ctxt *ld.Link, r *ld.Reloc, s *ld.Symbol, val *int64) int {
|
||||||
*val |= v << 5
|
*val |= v << 5
|
||||||
return 0
|
return 0
|
||||||
|
|
||||||
case obj.R_CALLARM64:
|
case objabi.R_CALLARM64:
|
||||||
t := (ld.Symaddr(r.Sym) + r.Add) - (s.Value + int64(r.Off))
|
t := (ld.Symaddr(r.Sym) + r.Add) - (s.Value + int64(r.Off))
|
||||||
if t >= 1<<27 || t < -1<<27 {
|
if t >= 1<<27 || t < -1<<27 {
|
||||||
ld.Errorf(s, "program too large, call relocation distance = %d", t)
|
ld.Errorf(s, "program too large, call relocation distance = %d", t)
|
||||||
|
|
@ -393,7 +393,7 @@ func archrelocvariant(ctxt *ld.Link, r *ld.Reloc, s *ld.Symbol, t int64) int64 {
|
||||||
|
|
||||||
func asmb(ctxt *ld.Link) {
|
func asmb(ctxt *ld.Link) {
|
||||||
if ctxt.Debugvlog != 0 {
|
if ctxt.Debugvlog != 0 {
|
||||||
ctxt.Logf("%5.2f asmb\n", obj.Cputime())
|
ctxt.Logf("%5.2f asmb\n", ld.Cputime())
|
||||||
}
|
}
|
||||||
|
|
||||||
if ld.Iself {
|
if ld.Iself {
|
||||||
|
|
@ -410,21 +410,21 @@ func asmb(ctxt *ld.Link) {
|
||||||
|
|
||||||
if ld.Segrodata.Filelen > 0 {
|
if ld.Segrodata.Filelen > 0 {
|
||||||
if ctxt.Debugvlog != 0 {
|
if ctxt.Debugvlog != 0 {
|
||||||
ctxt.Logf("%5.2f rodatblk\n", obj.Cputime())
|
ctxt.Logf("%5.2f rodatblk\n", ld.Cputime())
|
||||||
}
|
}
|
||||||
ld.Cseek(int64(ld.Segrodata.Fileoff))
|
ld.Cseek(int64(ld.Segrodata.Fileoff))
|
||||||
ld.Datblk(ctxt, int64(ld.Segrodata.Vaddr), int64(ld.Segrodata.Filelen))
|
ld.Datblk(ctxt, int64(ld.Segrodata.Vaddr), int64(ld.Segrodata.Filelen))
|
||||||
}
|
}
|
||||||
if ld.Segrelrodata.Filelen > 0 {
|
if ld.Segrelrodata.Filelen > 0 {
|
||||||
if ctxt.Debugvlog != 0 {
|
if ctxt.Debugvlog != 0 {
|
||||||
ctxt.Logf("%5.2f relrodatblk\n", obj.Cputime())
|
ctxt.Logf("%5.2f relrodatblk\n", ld.Cputime())
|
||||||
}
|
}
|
||||||
ld.Cseek(int64(ld.Segrelrodata.Fileoff))
|
ld.Cseek(int64(ld.Segrelrodata.Fileoff))
|
||||||
ld.Datblk(ctxt, int64(ld.Segrelrodata.Vaddr), int64(ld.Segrelrodata.Filelen))
|
ld.Datblk(ctxt, int64(ld.Segrelrodata.Vaddr), int64(ld.Segrelrodata.Filelen))
|
||||||
}
|
}
|
||||||
|
|
||||||
if ctxt.Debugvlog != 0 {
|
if ctxt.Debugvlog != 0 {
|
||||||
ctxt.Logf("%5.2f datblk\n", obj.Cputime())
|
ctxt.Logf("%5.2f datblk\n", ld.Cputime())
|
||||||
}
|
}
|
||||||
|
|
||||||
ld.Cseek(int64(ld.Segdata.Fileoff))
|
ld.Cseek(int64(ld.Segdata.Fileoff))
|
||||||
|
|
@ -434,7 +434,7 @@ func asmb(ctxt *ld.Link) {
|
||||||
ld.Dwarfblk(ctxt, int64(ld.Segdwarf.Vaddr), int64(ld.Segdwarf.Filelen))
|
ld.Dwarfblk(ctxt, int64(ld.Segdwarf.Vaddr), int64(ld.Segdwarf.Filelen))
|
||||||
|
|
||||||
machlink := uint32(0)
|
machlink := uint32(0)
|
||||||
if ld.Headtype == obj.Hdarwin {
|
if ld.Headtype == objabi.Hdarwin {
|
||||||
machlink = uint32(ld.Domacholink(ctxt))
|
machlink = uint32(ld.Domacholink(ctxt))
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -446,7 +446,7 @@ func asmb(ctxt *ld.Link) {
|
||||||
if !*ld.FlagS {
|
if !*ld.FlagS {
|
||||||
// TODO: rationalize
|
// TODO: rationalize
|
||||||
if ctxt.Debugvlog != 0 {
|
if ctxt.Debugvlog != 0 {
|
||||||
ctxt.Logf("%5.2f sym\n", obj.Cputime())
|
ctxt.Logf("%5.2f sym\n", ld.Cputime())
|
||||||
}
|
}
|
||||||
switch ld.Headtype {
|
switch ld.Headtype {
|
||||||
default:
|
default:
|
||||||
|
|
@ -455,10 +455,10 @@ func asmb(ctxt *ld.Link) {
|
||||||
symo = uint32(ld.Rnd(int64(symo), int64(*ld.FlagRound)))
|
symo = uint32(ld.Rnd(int64(symo), int64(*ld.FlagRound)))
|
||||||
}
|
}
|
||||||
|
|
||||||
case obj.Hplan9:
|
case objabi.Hplan9:
|
||||||
symo = uint32(ld.Segdata.Fileoff + ld.Segdata.Filelen)
|
symo = uint32(ld.Segdata.Fileoff + ld.Segdata.Filelen)
|
||||||
|
|
||||||
case obj.Hdarwin:
|
case objabi.Hdarwin:
|
||||||
symo = uint32(ld.Segdwarf.Fileoff + uint64(ld.Rnd(int64(ld.Segdwarf.Filelen), int64(*ld.FlagRound))) + uint64(machlink))
|
symo = uint32(ld.Segdwarf.Fileoff + uint64(ld.Rnd(int64(ld.Segdwarf.Filelen), int64(*ld.FlagRound))) + uint64(machlink))
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -467,7 +467,7 @@ func asmb(ctxt *ld.Link) {
|
||||||
default:
|
default:
|
||||||
if ld.Iself {
|
if ld.Iself {
|
||||||
if ctxt.Debugvlog != 0 {
|
if ctxt.Debugvlog != 0 {
|
||||||
ctxt.Logf("%5.2f elfsym\n", obj.Cputime())
|
ctxt.Logf("%5.2f elfsym\n", ld.Cputime())
|
||||||
}
|
}
|
||||||
ld.Asmelfsym(ctxt)
|
ld.Asmelfsym(ctxt)
|
||||||
ld.Cflush()
|
ld.Cflush()
|
||||||
|
|
@ -478,7 +478,7 @@ func asmb(ctxt *ld.Link) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
case obj.Hplan9:
|
case objabi.Hplan9:
|
||||||
ld.Asmplan9sym(ctxt)
|
ld.Asmplan9sym(ctxt)
|
||||||
ld.Cflush()
|
ld.Cflush()
|
||||||
|
|
||||||
|
|
@ -492,7 +492,7 @@ func asmb(ctxt *ld.Link) {
|
||||||
ld.Cflush()
|
ld.Cflush()
|
||||||
}
|
}
|
||||||
|
|
||||||
case obj.Hdarwin:
|
case objabi.Hdarwin:
|
||||||
if ld.Linkmode == ld.LinkExternal {
|
if ld.Linkmode == ld.LinkExternal {
|
||||||
ld.Machoemitreloc(ctxt)
|
ld.Machoemitreloc(ctxt)
|
||||||
}
|
}
|
||||||
|
|
@ -500,12 +500,12 @@ func asmb(ctxt *ld.Link) {
|
||||||
}
|
}
|
||||||
|
|
||||||
if ctxt.Debugvlog != 0 {
|
if ctxt.Debugvlog != 0 {
|
||||||
ctxt.Logf("%5.2f header\n", obj.Cputime())
|
ctxt.Logf("%5.2f header\n", ld.Cputime())
|
||||||
}
|
}
|
||||||
ld.Cseek(0)
|
ld.Cseek(0)
|
||||||
switch ld.Headtype {
|
switch ld.Headtype {
|
||||||
default:
|
default:
|
||||||
case obj.Hplan9: /* plan 9 */
|
case objabi.Hplan9: /* plan 9 */
|
||||||
ld.Thearch.Lput(0x647) /* magic */
|
ld.Thearch.Lput(0x647) /* magic */
|
||||||
ld.Thearch.Lput(uint32(ld.Segtext.Filelen)) /* sizes */
|
ld.Thearch.Lput(uint32(ld.Segtext.Filelen)) /* sizes */
|
||||||
ld.Thearch.Lput(uint32(ld.Segdata.Filelen))
|
ld.Thearch.Lput(uint32(ld.Segdata.Filelen))
|
||||||
|
|
@ -515,14 +515,14 @@ func asmb(ctxt *ld.Link) {
|
||||||
ld.Thearch.Lput(0)
|
ld.Thearch.Lput(0)
|
||||||
ld.Thearch.Lput(uint32(ld.Lcsize))
|
ld.Thearch.Lput(uint32(ld.Lcsize))
|
||||||
|
|
||||||
case obj.Hlinux,
|
case objabi.Hlinux,
|
||||||
obj.Hfreebsd,
|
objabi.Hfreebsd,
|
||||||
obj.Hnetbsd,
|
objabi.Hnetbsd,
|
||||||
obj.Hopenbsd,
|
objabi.Hopenbsd,
|
||||||
obj.Hnacl:
|
objabi.Hnacl:
|
||||||
ld.Asmbelf(ctxt, int64(symo))
|
ld.Asmbelf(ctxt, int64(symo))
|
||||||
|
|
||||||
case obj.Hdarwin:
|
case objabi.Hdarwin:
|
||||||
ld.Asmbmacho(ctxt)
|
ld.Asmbmacho(ctxt)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -31,7 +31,7 @@
|
||||||
package arm64
|
package arm64
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"cmd/internal/obj"
|
"cmd/internal/objabi"
|
||||||
"cmd/internal/sys"
|
"cmd/internal/sys"
|
||||||
"cmd/link/internal/ld"
|
"cmd/link/internal/ld"
|
||||||
"fmt"
|
"fmt"
|
||||||
|
|
@ -76,7 +76,7 @@ func archinit(ctxt *ld.Link) {
|
||||||
default:
|
default:
|
||||||
ld.Exitf("unknown -H option: %v", ld.Headtype)
|
ld.Exitf("unknown -H option: %v", ld.Headtype)
|
||||||
|
|
||||||
case obj.Hplan9: /* plan 9 */
|
case objabi.Hplan9: /* plan 9 */
|
||||||
ld.HEADR = 32
|
ld.HEADR = 32
|
||||||
|
|
||||||
if *ld.FlagTextAddr == -1 {
|
if *ld.FlagTextAddr == -1 {
|
||||||
|
|
@ -89,7 +89,7 @@ func archinit(ctxt *ld.Link) {
|
||||||
*ld.FlagRound = 4096
|
*ld.FlagRound = 4096
|
||||||
}
|
}
|
||||||
|
|
||||||
case obj.Hlinux: /* arm64 elf */
|
case objabi.Hlinux: /* arm64 elf */
|
||||||
ld.Elfinit(ctxt)
|
ld.Elfinit(ctxt)
|
||||||
ld.HEADR = ld.ELFRESERVE
|
ld.HEADR = ld.ELFRESERVE
|
||||||
if *ld.FlagTextAddr == -1 {
|
if *ld.FlagTextAddr == -1 {
|
||||||
|
|
@ -102,7 +102,7 @@ func archinit(ctxt *ld.Link) {
|
||||||
*ld.FlagRound = 0x10000
|
*ld.FlagRound = 0x10000
|
||||||
}
|
}
|
||||||
|
|
||||||
case obj.Hdarwin: /* apple MACH */
|
case objabi.Hdarwin: /* apple MACH */
|
||||||
*ld.FlagW = true // disable DWARF generation
|
*ld.FlagW = true // disable DWARF generation
|
||||||
ld.Machoinit()
|
ld.Machoinit()
|
||||||
ld.HEADR = ld.INITIAL_MACHO_HEADR
|
ld.HEADR = ld.INITIAL_MACHO_HEADR
|
||||||
|
|
@ -116,7 +116,7 @@ func archinit(ctxt *ld.Link) {
|
||||||
*ld.FlagRound = 4096
|
*ld.FlagRound = 4096
|
||||||
}
|
}
|
||||||
|
|
||||||
case obj.Hnacl:
|
case objabi.Hnacl:
|
||||||
ld.Elfinit(ctxt)
|
ld.Elfinit(ctxt)
|
||||||
ld.HEADR = 0x10000
|
ld.HEADR = 0x10000
|
||||||
ld.Funcalign = 16
|
ld.Funcalign = 16
|
||||||
|
|
|
||||||
|
|
@ -32,7 +32,7 @@ package ld
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"cmd/internal/bio"
|
"cmd/internal/bio"
|
||||||
"cmd/internal/obj"
|
"cmd/internal/objabi"
|
||||||
"encoding/binary"
|
"encoding/binary"
|
||||||
"fmt"
|
"fmt"
|
||||||
"io"
|
"io"
|
||||||
|
|
@ -101,7 +101,7 @@ func hostArchive(ctxt *Link, name string) {
|
||||||
var load []uint64
|
var load []uint64
|
||||||
for _, s := range ctxt.Syms.Allsym {
|
for _, s := range ctxt.Syms.Allsym {
|
||||||
for _, r := range s.R {
|
for _, r := range s.R {
|
||||||
if r.Sym != nil && r.Sym.Type&obj.SMASK == obj.SXREF {
|
if r.Sym != nil && r.Sym.Type&objabi.SMASK == objabi.SXREF {
|
||||||
if off := armap[r.Sym.Name]; off != 0 && !loaded[off] {
|
if off := armap[r.Sym.Name]; off != 0 && !loaded[off] {
|
||||||
load = append(load, off)
|
load = append(load, off)
|
||||||
loaded[off] = true
|
loaded[off] = true
|
||||||
|
|
@ -166,7 +166,7 @@ func readArmap(filename string, f *bio.Reader, arhdr ArHdr) archiveMap {
|
||||||
|
|
||||||
// For Mach-O and PE/386 files we strip a leading
|
// For Mach-O and PE/386 files we strip a leading
|
||||||
// underscore from the symbol name.
|
// underscore from the symbol name.
|
||||||
if obj.GOOS == "darwin" || (obj.GOOS == "windows" && obj.GOARCH == "386") {
|
if objabi.GOOS == "darwin" || (objabi.GOOS == "windows" && objabi.GOARCH == "386") {
|
||||||
if name[0] == '_' && len(name) > 1 {
|
if name[0] == '_' && len(name) > 1 {
|
||||||
name = name[1:]
|
name = name[1:]
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -5,7 +5,7 @@
|
||||||
package ld
|
package ld
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"cmd/internal/obj"
|
"cmd/internal/objabi"
|
||||||
"cmd/internal/sys"
|
"cmd/internal/sys"
|
||||||
"fmt"
|
"fmt"
|
||||||
"log"
|
"log"
|
||||||
|
|
@ -34,7 +34,7 @@ const (
|
||||||
|
|
||||||
func (mode *BuildMode) Set(s string) error {
|
func (mode *BuildMode) Set(s string) error {
|
||||||
badmode := func() error {
|
badmode := func() error {
|
||||||
return fmt.Errorf("buildmode %s not supported on %s/%s", s, obj.GOOS, obj.GOARCH)
|
return fmt.Errorf("buildmode %s not supported on %s/%s", s, objabi.GOOS, objabi.GOARCH)
|
||||||
}
|
}
|
||||||
switch s {
|
switch s {
|
||||||
default:
|
default:
|
||||||
|
|
@ -42,17 +42,17 @@ func (mode *BuildMode) Set(s string) error {
|
||||||
case "exe":
|
case "exe":
|
||||||
*mode = BuildmodeExe
|
*mode = BuildmodeExe
|
||||||
case "pie":
|
case "pie":
|
||||||
switch obj.GOOS {
|
switch objabi.GOOS {
|
||||||
case "android", "linux":
|
case "android", "linux":
|
||||||
default:
|
default:
|
||||||
return badmode()
|
return badmode()
|
||||||
}
|
}
|
||||||
*mode = BuildmodePIE
|
*mode = BuildmodePIE
|
||||||
case "c-archive":
|
case "c-archive":
|
||||||
switch obj.GOOS {
|
switch objabi.GOOS {
|
||||||
case "darwin", "linux":
|
case "darwin", "linux":
|
||||||
case "windows":
|
case "windows":
|
||||||
switch obj.GOARCH {
|
switch objabi.GOARCH {
|
||||||
case "amd64", "386":
|
case "amd64", "386":
|
||||||
default:
|
default:
|
||||||
return badmode()
|
return badmode()
|
||||||
|
|
@ -62,16 +62,16 @@ func (mode *BuildMode) Set(s string) error {
|
||||||
}
|
}
|
||||||
*mode = BuildmodeCArchive
|
*mode = BuildmodeCArchive
|
||||||
case "c-shared":
|
case "c-shared":
|
||||||
switch obj.GOARCH {
|
switch objabi.GOARCH {
|
||||||
case "386", "amd64", "arm", "arm64":
|
case "386", "amd64", "arm", "arm64":
|
||||||
default:
|
default:
|
||||||
return badmode()
|
return badmode()
|
||||||
}
|
}
|
||||||
*mode = BuildmodeCShared
|
*mode = BuildmodeCShared
|
||||||
case "shared":
|
case "shared":
|
||||||
switch obj.GOOS {
|
switch objabi.GOOS {
|
||||||
case "linux":
|
case "linux":
|
||||||
switch obj.GOARCH {
|
switch objabi.GOARCH {
|
||||||
case "386", "amd64", "arm", "arm64", "ppc64le", "s390x":
|
case "386", "amd64", "arm", "arm64", "ppc64le", "s390x":
|
||||||
default:
|
default:
|
||||||
return badmode()
|
return badmode()
|
||||||
|
|
@ -81,15 +81,15 @@ func (mode *BuildMode) Set(s string) error {
|
||||||
}
|
}
|
||||||
*mode = BuildmodeShared
|
*mode = BuildmodeShared
|
||||||
case "plugin":
|
case "plugin":
|
||||||
switch obj.GOOS {
|
switch objabi.GOOS {
|
||||||
case "linux":
|
case "linux":
|
||||||
switch obj.GOARCH {
|
switch objabi.GOARCH {
|
||||||
case "386", "amd64", "arm", "arm64", "s390x":
|
case "386", "amd64", "arm", "arm64", "s390x":
|
||||||
default:
|
default:
|
||||||
return badmode()
|
return badmode()
|
||||||
}
|
}
|
||||||
case "darwin":
|
case "darwin":
|
||||||
switch obj.GOARCH {
|
switch objabi.GOARCH {
|
||||||
case "amd64":
|
case "amd64":
|
||||||
default:
|
default:
|
||||||
return badmode()
|
return badmode()
|
||||||
|
|
@ -168,7 +168,7 @@ func mustLinkExternal(ctxt *Link) (res bool, reason string) {
|
||||||
}()
|
}()
|
||||||
}
|
}
|
||||||
|
|
||||||
switch obj.GOOS {
|
switch objabi.GOOS {
|
||||||
case "android":
|
case "android":
|
||||||
return true, "android"
|
return true, "android"
|
||||||
case "darwin":
|
case "darwin":
|
||||||
|
|
@ -185,7 +185,7 @@ func mustLinkExternal(ctxt *Link) (res bool, reason string) {
|
||||||
// https://golang.org/issue/10373
|
// https://golang.org/issue/10373
|
||||||
// https://golang.org/issue/14449
|
// https://golang.org/issue/14449
|
||||||
if iscgo && SysArch.InFamily(sys.ARM64, sys.MIPS64, sys.MIPS) {
|
if iscgo && SysArch.InFamily(sys.ARM64, sys.MIPS64, sys.MIPS) {
|
||||||
return true, obj.GOARCH + " does not support internal cgo"
|
return true, objabi.GOARCH + " does not support internal cgo"
|
||||||
}
|
}
|
||||||
|
|
||||||
// Some build modes require work the internal linker cannot do (yet).
|
// Some build modes require work the internal linker cannot do (yet).
|
||||||
|
|
@ -195,7 +195,7 @@ func mustLinkExternal(ctxt *Link) (res bool, reason string) {
|
||||||
case BuildmodeCShared:
|
case BuildmodeCShared:
|
||||||
return true, "buildmode=c-shared"
|
return true, "buildmode=c-shared"
|
||||||
case BuildmodePIE:
|
case BuildmodePIE:
|
||||||
switch obj.GOOS + "/" + obj.GOARCH {
|
switch objabi.GOOS + "/" + objabi.GOARCH {
|
||||||
case "linux/amd64":
|
case "linux/amd64":
|
||||||
default:
|
default:
|
||||||
// Internal linking does not support TLS_IE.
|
// Internal linking does not support TLS_IE.
|
||||||
|
|
@ -225,7 +225,7 @@ func determineLinkMode(ctxt *Link) {
|
||||||
// default value of -linkmode. If it is not set when the
|
// default value of -linkmode. If it is not set when the
|
||||||
// linker is called we take the value it was set to when
|
// linker is called we take the value it was set to when
|
||||||
// cmd/link was compiled. (See make.bash.)
|
// cmd/link was compiled. (See make.bash.)
|
||||||
switch obj.Getgoextlinkenabled() {
|
switch objabi.Getgoextlinkenabled() {
|
||||||
case "0":
|
case "0":
|
||||||
if needed, reason := mustLinkExternal(ctxt); needed {
|
if needed, reason := mustLinkExternal(ctxt); needed {
|
||||||
Exitf("internal linking requested via GO_EXTLINK_ENABLED, but external linking required: %s", reason)
|
Exitf("internal linking requested via GO_EXTLINK_ENABLED, but external linking required: %s", reason)
|
||||||
|
|
|
||||||
File diff suppressed because it is too large
Load diff
|
|
@ -5,7 +5,7 @@
|
||||||
package ld
|
package ld
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"cmd/internal/obj"
|
"cmd/internal/objabi"
|
||||||
"cmd/internal/sys"
|
"cmd/internal/sys"
|
||||||
"fmt"
|
"fmt"
|
||||||
"strings"
|
"strings"
|
||||||
|
|
@ -46,7 +46,7 @@ import (
|
||||||
// Any unreached text symbols are removed from ctxt.Textp.
|
// Any unreached text symbols are removed from ctxt.Textp.
|
||||||
func deadcode(ctxt *Link) {
|
func deadcode(ctxt *Link) {
|
||||||
if ctxt.Debugvlog != 0 {
|
if ctxt.Debugvlog != 0 {
|
||||||
ctxt.Logf("%5.2f deadcode\n", obj.Cputime())
|
ctxt.Logf("%5.2f deadcode\n", Cputime())
|
||||||
}
|
}
|
||||||
|
|
||||||
d := &deadcodepass{
|
d := &deadcodepass{
|
||||||
|
|
@ -156,7 +156,7 @@ type deadcodepass struct {
|
||||||
|
|
||||||
func (d *deadcodepass) cleanupReloc(r *Reloc) {
|
func (d *deadcodepass) cleanupReloc(r *Reloc) {
|
||||||
if r.Sym.Attr.Reachable() {
|
if r.Sym.Attr.Reachable() {
|
||||||
r.Type = obj.R_ADDROFF
|
r.Type = objabi.R_ADDROFF
|
||||||
} else {
|
} else {
|
||||||
if d.ctxt.Debugvlog > 1 {
|
if d.ctxt.Debugvlog > 1 {
|
||||||
d.ctxt.Logf("removing method %s\n", r.Sym.Name)
|
d.ctxt.Logf("removing method %s\n", r.Sym.Name)
|
||||||
|
|
@ -190,7 +190,7 @@ func (d *deadcodepass) mark(s, parent *Symbol) {
|
||||||
func (d *deadcodepass) markMethod(m methodref) {
|
func (d *deadcodepass) markMethod(m methodref) {
|
||||||
for _, r := range m.r {
|
for _, r := range m.r {
|
||||||
d.mark(r.Sym, m.src)
|
d.mark(r.Sym, m.src)
|
||||||
r.Type = obj.R_ADDROFF
|
r.Type = objabi.R_ADDROFF
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -208,7 +208,7 @@ func (d *deadcodepass) init() {
|
||||||
// Mark all symbols defined in this library as reachable when
|
// Mark all symbols defined in this library as reachable when
|
||||||
// building a shared library.
|
// building a shared library.
|
||||||
for _, s := range d.ctxt.Syms.Allsym {
|
for _, s := range d.ctxt.Syms.Allsym {
|
||||||
if s.Type != 0 && s.Type != obj.SDYNIMPORT {
|
if s.Type != 0 && s.Type != objabi.SDYNIMPORT {
|
||||||
d.mark(s, nil)
|
d.mark(s, nil)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
@ -246,7 +246,7 @@ func (d *deadcodepass) flood() {
|
||||||
for len(d.markQueue) > 0 {
|
for len(d.markQueue) > 0 {
|
||||||
s := d.markQueue[0]
|
s := d.markQueue[0]
|
||||||
d.markQueue = d.markQueue[1:]
|
d.markQueue = d.markQueue[1:]
|
||||||
if s.Type == obj.STEXT {
|
if s.Type == objabi.STEXT {
|
||||||
if d.ctxt.Debugvlog > 1 {
|
if d.ctxt.Debugvlog > 1 {
|
||||||
d.ctxt.Logf("marktext %s\n", s.Name)
|
d.ctxt.Logf("marktext %s\n", s.Name)
|
||||||
}
|
}
|
||||||
|
|
@ -281,13 +281,13 @@ func (d *deadcodepass) flood() {
|
||||||
if r.Sym == nil {
|
if r.Sym == nil {
|
||||||
continue
|
continue
|
||||||
}
|
}
|
||||||
if r.Type == obj.R_WEAKADDROFF {
|
if r.Type == objabi.R_WEAKADDROFF {
|
||||||
// An R_WEAKADDROFF relocation is not reason
|
// An R_WEAKADDROFF relocation is not reason
|
||||||
// enough to mark the pointed-to symbol as
|
// enough to mark the pointed-to symbol as
|
||||||
// reachable.
|
// reachable.
|
||||||
continue
|
continue
|
||||||
}
|
}
|
||||||
if r.Type != obj.R_METHODOFF {
|
if r.Type != objabi.R_METHODOFF {
|
||||||
d.mark(r.Sym, s)
|
d.mark(r.Sym, s)
|
||||||
continue
|
continue
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -6,7 +6,7 @@ package ld
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"bytes"
|
"bytes"
|
||||||
"cmd/internal/obj"
|
"cmd/internal/objabi"
|
||||||
"cmd/internal/sys"
|
"cmd/internal/sys"
|
||||||
"debug/elf"
|
"debug/elf"
|
||||||
"fmt"
|
"fmt"
|
||||||
|
|
@ -65,12 +65,12 @@ func uncommonSize() int { return 4 + 2 + 2 + 4 + 4 } // runtime.uncom
|
||||||
|
|
||||||
// Type.commonType.kind
|
// Type.commonType.kind
|
||||||
func decodetypeKind(s *Symbol) uint8 {
|
func decodetypeKind(s *Symbol) uint8 {
|
||||||
return s.P[2*SysArch.PtrSize+7] & obj.KindMask // 0x13 / 0x1f
|
return s.P[2*SysArch.PtrSize+7] & objabi.KindMask // 0x13 / 0x1f
|
||||||
}
|
}
|
||||||
|
|
||||||
// Type.commonType.kind
|
// Type.commonType.kind
|
||||||
func decodetypeUsegcprog(s *Symbol) uint8 {
|
func decodetypeUsegcprog(s *Symbol) uint8 {
|
||||||
return s.P[2*SysArch.PtrSize+7] & obj.KindGCProg // 0x13 / 0x1f
|
return s.P[2*SysArch.PtrSize+7] & objabi.KindGCProg // 0x13 / 0x1f
|
||||||
}
|
}
|
||||||
|
|
||||||
// Type.commonType.size
|
// Type.commonType.size
|
||||||
|
|
@ -104,7 +104,7 @@ func findShlibSection(ctxt *Link, path string, addr uint64) *elf.Section {
|
||||||
|
|
||||||
// Type.commonType.gc
|
// Type.commonType.gc
|
||||||
func decodetypeGcprog(ctxt *Link, s *Symbol) []byte {
|
func decodetypeGcprog(ctxt *Link, s *Symbol) []byte {
|
||||||
if s.Type == obj.SDYNIMPORT {
|
if s.Type == objabi.SDYNIMPORT {
|
||||||
addr := decodetypeGcprogShlib(ctxt, s)
|
addr := decodetypeGcprogShlib(ctxt, s)
|
||||||
sect := findShlibSection(ctxt, s.File, addr)
|
sect := findShlibSection(ctxt, s.File, addr)
|
||||||
if sect != nil {
|
if sect != nil {
|
||||||
|
|
@ -135,7 +135,7 @@ func decodetypeGcprogShlib(ctxt *Link, s *Symbol) uint64 {
|
||||||
}
|
}
|
||||||
|
|
||||||
func decodetypeGcmask(ctxt *Link, s *Symbol) []byte {
|
func decodetypeGcmask(ctxt *Link, s *Symbol) []byte {
|
||||||
if s.Type == obj.SDYNIMPORT {
|
if s.Type == objabi.SDYNIMPORT {
|
||||||
addr := decodetypeGcprogShlib(ctxt, s)
|
addr := decodetypeGcprogShlib(ctxt, s)
|
||||||
ptrdata := decodetypePtrdata(ctxt.Arch, s)
|
ptrdata := decodetypePtrdata(ctxt.Arch, s)
|
||||||
sect := findShlibSection(ctxt, s.File, addr)
|
sect := findShlibSection(ctxt, s.File, addr)
|
||||||
|
|
|
||||||
|
|
@ -16,7 +16,7 @@ package ld
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"cmd/internal/dwarf"
|
"cmd/internal/dwarf"
|
||||||
"cmd/internal/obj"
|
"cmd/internal/objabi"
|
||||||
"fmt"
|
"fmt"
|
||||||
"log"
|
"log"
|
||||||
"os"
|
"os"
|
||||||
|
|
@ -64,7 +64,7 @@ func (c dwctxt) AddSectionOffset(s dwarf.Sym, size int, t interface{}, ofs int64
|
||||||
addaddrplus4(c.linkctxt, ls, t.(*Symbol), 0)
|
addaddrplus4(c.linkctxt, ls, t.(*Symbol), 0)
|
||||||
}
|
}
|
||||||
r := &ls.R[len(ls.R)-1]
|
r := &ls.R[len(ls.R)-1]
|
||||||
r.Type = obj.R_DWARFREF
|
r.Type = objabi.R_DWARFREF
|
||||||
r.Add = ofs
|
r.Add = ofs
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -83,7 +83,7 @@ var dwarfp []*Symbol
|
||||||
|
|
||||||
func writeabbrev(ctxt *Link, syms []*Symbol) []*Symbol {
|
func writeabbrev(ctxt *Link, syms []*Symbol) []*Symbol {
|
||||||
s := ctxt.Syms.Lookup(".debug_abbrev", 0)
|
s := ctxt.Syms.Lookup(".debug_abbrev", 0)
|
||||||
s.Type = obj.SDWARFSECT
|
s.Type = objabi.SDWARFSECT
|
||||||
abbrevsym = s
|
abbrevsym = s
|
||||||
Addbytes(s, dwarf.GetAbbrev())
|
Addbytes(s, dwarf.GetAbbrev())
|
||||||
return append(syms, s)
|
return append(syms, s)
|
||||||
|
|
@ -148,7 +148,7 @@ func newdie(ctxt *Link, parent *dwarf.DWDie, abbrev int, name string, version in
|
||||||
if abbrev != dwarf.DW_ABRV_VARIABLE || version == 0 {
|
if abbrev != dwarf.DW_ABRV_VARIABLE || version == 0 {
|
||||||
sym := ctxt.Syms.Lookup(dwarf.InfoPrefix+name, version)
|
sym := ctxt.Syms.Lookup(dwarf.InfoPrefix+name, version)
|
||||||
sym.Attr |= AttrHidden
|
sym.Attr |= AttrHidden
|
||||||
sym.Type = obj.SDWARFINFO
|
sym.Type = objabi.SDWARFINFO
|
||||||
die.Sym = sym
|
die.Sym = sym
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
@ -202,7 +202,7 @@ func find(ctxt *Link, name string) *Symbol {
|
||||||
// The string allocation below is optimized away because it is only used in a map lookup.
|
// The string allocation below is optimized away because it is only used in a map lookup.
|
||||||
s := ctxt.Syms.ROLookup(string(n), 0)
|
s := ctxt.Syms.ROLookup(string(n), 0)
|
||||||
prefixBuf = n[:len(dwarf.InfoPrefix)]
|
prefixBuf = n[:len(dwarf.InfoPrefix)]
|
||||||
if s != nil && s.Type == obj.SDWARFINFO {
|
if s != nil && s.Type == objabi.SDWARFINFO {
|
||||||
return s
|
return s
|
||||||
}
|
}
|
||||||
return nil
|
return nil
|
||||||
|
|
@ -228,7 +228,7 @@ func adddwarfref(ctxt *Link, s *Symbol, t *Symbol, size int) int64 {
|
||||||
result = addaddrplus4(ctxt, s, t, 0)
|
result = addaddrplus4(ctxt, s, t, 0)
|
||||||
}
|
}
|
||||||
r := &s.R[len(s.R)-1]
|
r := &s.R[len(s.R)-1]
|
||||||
r.Type = obj.R_DWARFREF
|
r.Type = objabi.R_DWARFREF
|
||||||
return result
|
return result
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -340,7 +340,7 @@ func dotypedef(ctxt *Link, parent *dwarf.DWDie, name string, def *dwarf.DWDie) {
|
||||||
|
|
||||||
sym := ctxt.Syms.Lookup(dtolsym(def.Sym).Name+"..def", 0)
|
sym := ctxt.Syms.Lookup(dtolsym(def.Sym).Name+"..def", 0)
|
||||||
sym.Attr |= AttrHidden
|
sym.Attr |= AttrHidden
|
||||||
sym.Type = obj.SDWARFINFO
|
sym.Type = objabi.SDWARFINFO
|
||||||
def.Sym = sym
|
def.Sym = sym
|
||||||
|
|
||||||
// The typedef entry must be created after the def,
|
// The typedef entry must be created after the def,
|
||||||
|
|
@ -381,43 +381,43 @@ func newtype(ctxt *Link, gotype *Symbol) *dwarf.DWDie {
|
||||||
|
|
||||||
var die *dwarf.DWDie
|
var die *dwarf.DWDie
|
||||||
switch kind {
|
switch kind {
|
||||||
case obj.KindBool:
|
case objabi.KindBool:
|
||||||
die = newdie(ctxt, &dwtypes, dwarf.DW_ABRV_BASETYPE, name, 0)
|
die = newdie(ctxt, &dwtypes, dwarf.DW_ABRV_BASETYPE, name, 0)
|
||||||
newattr(die, dwarf.DW_AT_encoding, dwarf.DW_CLS_CONSTANT, dwarf.DW_ATE_boolean, 0)
|
newattr(die, dwarf.DW_AT_encoding, dwarf.DW_CLS_CONSTANT, dwarf.DW_ATE_boolean, 0)
|
||||||
newattr(die, dwarf.DW_AT_byte_size, dwarf.DW_CLS_CONSTANT, bytesize, 0)
|
newattr(die, dwarf.DW_AT_byte_size, dwarf.DW_CLS_CONSTANT, bytesize, 0)
|
||||||
|
|
||||||
case obj.KindInt,
|
case objabi.KindInt,
|
||||||
obj.KindInt8,
|
objabi.KindInt8,
|
||||||
obj.KindInt16,
|
objabi.KindInt16,
|
||||||
obj.KindInt32,
|
objabi.KindInt32,
|
||||||
obj.KindInt64:
|
objabi.KindInt64:
|
||||||
die = newdie(ctxt, &dwtypes, dwarf.DW_ABRV_BASETYPE, name, 0)
|
die = newdie(ctxt, &dwtypes, dwarf.DW_ABRV_BASETYPE, name, 0)
|
||||||
newattr(die, dwarf.DW_AT_encoding, dwarf.DW_CLS_CONSTANT, dwarf.DW_ATE_signed, 0)
|
newattr(die, dwarf.DW_AT_encoding, dwarf.DW_CLS_CONSTANT, dwarf.DW_ATE_signed, 0)
|
||||||
newattr(die, dwarf.DW_AT_byte_size, dwarf.DW_CLS_CONSTANT, bytesize, 0)
|
newattr(die, dwarf.DW_AT_byte_size, dwarf.DW_CLS_CONSTANT, bytesize, 0)
|
||||||
|
|
||||||
case obj.KindUint,
|
case objabi.KindUint,
|
||||||
obj.KindUint8,
|
objabi.KindUint8,
|
||||||
obj.KindUint16,
|
objabi.KindUint16,
|
||||||
obj.KindUint32,
|
objabi.KindUint32,
|
||||||
obj.KindUint64,
|
objabi.KindUint64,
|
||||||
obj.KindUintptr:
|
objabi.KindUintptr:
|
||||||
die = newdie(ctxt, &dwtypes, dwarf.DW_ABRV_BASETYPE, name, 0)
|
die = newdie(ctxt, &dwtypes, dwarf.DW_ABRV_BASETYPE, name, 0)
|
||||||
newattr(die, dwarf.DW_AT_encoding, dwarf.DW_CLS_CONSTANT, dwarf.DW_ATE_unsigned, 0)
|
newattr(die, dwarf.DW_AT_encoding, dwarf.DW_CLS_CONSTANT, dwarf.DW_ATE_unsigned, 0)
|
||||||
newattr(die, dwarf.DW_AT_byte_size, dwarf.DW_CLS_CONSTANT, bytesize, 0)
|
newattr(die, dwarf.DW_AT_byte_size, dwarf.DW_CLS_CONSTANT, bytesize, 0)
|
||||||
|
|
||||||
case obj.KindFloat32,
|
case objabi.KindFloat32,
|
||||||
obj.KindFloat64:
|
objabi.KindFloat64:
|
||||||
die = newdie(ctxt, &dwtypes, dwarf.DW_ABRV_BASETYPE, name, 0)
|
die = newdie(ctxt, &dwtypes, dwarf.DW_ABRV_BASETYPE, name, 0)
|
||||||
newattr(die, dwarf.DW_AT_encoding, dwarf.DW_CLS_CONSTANT, dwarf.DW_ATE_float, 0)
|
newattr(die, dwarf.DW_AT_encoding, dwarf.DW_CLS_CONSTANT, dwarf.DW_ATE_float, 0)
|
||||||
newattr(die, dwarf.DW_AT_byte_size, dwarf.DW_CLS_CONSTANT, bytesize, 0)
|
newattr(die, dwarf.DW_AT_byte_size, dwarf.DW_CLS_CONSTANT, bytesize, 0)
|
||||||
|
|
||||||
case obj.KindComplex64,
|
case objabi.KindComplex64,
|
||||||
obj.KindComplex128:
|
objabi.KindComplex128:
|
||||||
die = newdie(ctxt, &dwtypes, dwarf.DW_ABRV_BASETYPE, name, 0)
|
die = newdie(ctxt, &dwtypes, dwarf.DW_ABRV_BASETYPE, name, 0)
|
||||||
newattr(die, dwarf.DW_AT_encoding, dwarf.DW_CLS_CONSTANT, dwarf.DW_ATE_complex_float, 0)
|
newattr(die, dwarf.DW_AT_encoding, dwarf.DW_CLS_CONSTANT, dwarf.DW_ATE_complex_float, 0)
|
||||||
newattr(die, dwarf.DW_AT_byte_size, dwarf.DW_CLS_CONSTANT, bytesize, 0)
|
newattr(die, dwarf.DW_AT_byte_size, dwarf.DW_CLS_CONSTANT, bytesize, 0)
|
||||||
|
|
||||||
case obj.KindArray:
|
case objabi.KindArray:
|
||||||
die = newdie(ctxt, &dwtypes, dwarf.DW_ABRV_ARRAYTYPE, name, 0)
|
die = newdie(ctxt, &dwtypes, dwarf.DW_ABRV_ARRAYTYPE, name, 0)
|
||||||
dotypedef(ctxt, &dwtypes, name, die)
|
dotypedef(ctxt, &dwtypes, name, die)
|
||||||
newattr(die, dwarf.DW_AT_byte_size, dwarf.DW_CLS_CONSTANT, bytesize, 0)
|
newattr(die, dwarf.DW_AT_byte_size, dwarf.DW_CLS_CONSTANT, bytesize, 0)
|
||||||
|
|
@ -430,7 +430,7 @@ func newtype(ctxt *Link, gotype *Symbol) *dwarf.DWDie {
|
||||||
|
|
||||||
newrefattr(fld, dwarf.DW_AT_type, mustFind(ctxt, "uintptr"))
|
newrefattr(fld, dwarf.DW_AT_type, mustFind(ctxt, "uintptr"))
|
||||||
|
|
||||||
case obj.KindChan:
|
case objabi.KindChan:
|
||||||
die = newdie(ctxt, &dwtypes, dwarf.DW_ABRV_CHANTYPE, name, 0)
|
die = newdie(ctxt, &dwtypes, dwarf.DW_ABRV_CHANTYPE, name, 0)
|
||||||
newattr(die, dwarf.DW_AT_byte_size, dwarf.DW_CLS_CONSTANT, bytesize, 0)
|
newattr(die, dwarf.DW_AT_byte_size, dwarf.DW_CLS_CONSTANT, bytesize, 0)
|
||||||
s := decodetypeChanElem(gotype)
|
s := decodetypeChanElem(gotype)
|
||||||
|
|
@ -439,7 +439,7 @@ func newtype(ctxt *Link, gotype *Symbol) *dwarf.DWDie {
|
||||||
// but that would change the order of DIEs we output.
|
// but that would change the order of DIEs we output.
|
||||||
newrefattr(die, dwarf.DW_AT_type, s)
|
newrefattr(die, dwarf.DW_AT_type, s)
|
||||||
|
|
||||||
case obj.KindFunc:
|
case objabi.KindFunc:
|
||||||
die = newdie(ctxt, &dwtypes, dwarf.DW_ABRV_FUNCTYPE, name, 0)
|
die = newdie(ctxt, &dwtypes, dwarf.DW_ABRV_FUNCTYPE, name, 0)
|
||||||
dotypedef(ctxt, &dwtypes, name, die)
|
dotypedef(ctxt, &dwtypes, name, die)
|
||||||
newrefattr(die, dwarf.DW_AT_type, mustFind(ctxt, "void"))
|
newrefattr(die, dwarf.DW_AT_type, mustFind(ctxt, "void"))
|
||||||
|
|
@ -462,7 +462,7 @@ func newtype(ctxt *Link, gotype *Symbol) *dwarf.DWDie {
|
||||||
newrefattr(fld, dwarf.DW_AT_type, defptrto(ctxt, defgotype(ctxt, s)))
|
newrefattr(fld, dwarf.DW_AT_type, defptrto(ctxt, defgotype(ctxt, s)))
|
||||||
}
|
}
|
||||||
|
|
||||||
case obj.KindInterface:
|
case objabi.KindInterface:
|
||||||
die = newdie(ctxt, &dwtypes, dwarf.DW_ABRV_IFACETYPE, name, 0)
|
die = newdie(ctxt, &dwtypes, dwarf.DW_ABRV_IFACETYPE, name, 0)
|
||||||
dotypedef(ctxt, &dwtypes, name, die)
|
dotypedef(ctxt, &dwtypes, name, die)
|
||||||
newattr(die, dwarf.DW_AT_byte_size, dwarf.DW_CLS_CONSTANT, bytesize, 0)
|
newattr(die, dwarf.DW_AT_byte_size, dwarf.DW_CLS_CONSTANT, bytesize, 0)
|
||||||
|
|
@ -475,7 +475,7 @@ func newtype(ctxt *Link, gotype *Symbol) *dwarf.DWDie {
|
||||||
}
|
}
|
||||||
newrefattr(die, dwarf.DW_AT_type, defgotype(ctxt, s))
|
newrefattr(die, dwarf.DW_AT_type, defgotype(ctxt, s))
|
||||||
|
|
||||||
case obj.KindMap:
|
case objabi.KindMap:
|
||||||
die = newdie(ctxt, &dwtypes, dwarf.DW_ABRV_MAPTYPE, name, 0)
|
die = newdie(ctxt, &dwtypes, dwarf.DW_ABRV_MAPTYPE, name, 0)
|
||||||
s := decodetypeMapKey(gotype)
|
s := decodetypeMapKey(gotype)
|
||||||
newrefattr(die, dwarf.DW_AT_go_key, defgotype(ctxt, s))
|
newrefattr(die, dwarf.DW_AT_go_key, defgotype(ctxt, s))
|
||||||
|
|
@ -485,13 +485,13 @@ func newtype(ctxt *Link, gotype *Symbol) *dwarf.DWDie {
|
||||||
// but that would change the order of the DIEs.
|
// but that would change the order of the DIEs.
|
||||||
newrefattr(die, dwarf.DW_AT_type, gotype)
|
newrefattr(die, dwarf.DW_AT_type, gotype)
|
||||||
|
|
||||||
case obj.KindPtr:
|
case objabi.KindPtr:
|
||||||
die = newdie(ctxt, &dwtypes, dwarf.DW_ABRV_PTRTYPE, name, 0)
|
die = newdie(ctxt, &dwtypes, dwarf.DW_ABRV_PTRTYPE, name, 0)
|
||||||
dotypedef(ctxt, &dwtypes, name, die)
|
dotypedef(ctxt, &dwtypes, name, die)
|
||||||
s := decodetypePtrElem(gotype)
|
s := decodetypePtrElem(gotype)
|
||||||
newrefattr(die, dwarf.DW_AT_type, defgotype(ctxt, s))
|
newrefattr(die, dwarf.DW_AT_type, defgotype(ctxt, s))
|
||||||
|
|
||||||
case obj.KindSlice:
|
case objabi.KindSlice:
|
||||||
die = newdie(ctxt, &dwtypes, dwarf.DW_ABRV_SLICETYPE, name, 0)
|
die = newdie(ctxt, &dwtypes, dwarf.DW_ABRV_SLICETYPE, name, 0)
|
||||||
dotypedef(ctxt, &dwtypes, name, die)
|
dotypedef(ctxt, &dwtypes, name, die)
|
||||||
newattr(die, dwarf.DW_AT_byte_size, dwarf.DW_CLS_CONSTANT, bytesize, 0)
|
newattr(die, dwarf.DW_AT_byte_size, dwarf.DW_CLS_CONSTANT, bytesize, 0)
|
||||||
|
|
@ -499,11 +499,11 @@ func newtype(ctxt *Link, gotype *Symbol) *dwarf.DWDie {
|
||||||
elem := defgotype(ctxt, s)
|
elem := defgotype(ctxt, s)
|
||||||
newrefattr(die, dwarf.DW_AT_go_elem, elem)
|
newrefattr(die, dwarf.DW_AT_go_elem, elem)
|
||||||
|
|
||||||
case obj.KindString:
|
case objabi.KindString:
|
||||||
die = newdie(ctxt, &dwtypes, dwarf.DW_ABRV_STRINGTYPE, name, 0)
|
die = newdie(ctxt, &dwtypes, dwarf.DW_ABRV_STRINGTYPE, name, 0)
|
||||||
newattr(die, dwarf.DW_AT_byte_size, dwarf.DW_CLS_CONSTANT, bytesize, 0)
|
newattr(die, dwarf.DW_AT_byte_size, dwarf.DW_CLS_CONSTANT, bytesize, 0)
|
||||||
|
|
||||||
case obj.KindStruct:
|
case objabi.KindStruct:
|
||||||
die = newdie(ctxt, &dwtypes, dwarf.DW_ABRV_STRUCTTYPE, name, 0)
|
die = newdie(ctxt, &dwtypes, dwarf.DW_ABRV_STRUCTTYPE, name, 0)
|
||||||
dotypedef(ctxt, &dwtypes, name, die)
|
dotypedef(ctxt, &dwtypes, name, die)
|
||||||
newattr(die, dwarf.DW_AT_byte_size, dwarf.DW_CLS_CONSTANT, bytesize, 0)
|
newattr(die, dwarf.DW_AT_byte_size, dwarf.DW_CLS_CONSTANT, bytesize, 0)
|
||||||
|
|
@ -522,7 +522,7 @@ func newtype(ctxt *Link, gotype *Symbol) *dwarf.DWDie {
|
||||||
newmemberoffsetattr(fld, int32(decodetypeStructFieldOffs(ctxt.Arch, gotype, i)))
|
newmemberoffsetattr(fld, int32(decodetypeStructFieldOffs(ctxt.Arch, gotype, i)))
|
||||||
}
|
}
|
||||||
|
|
||||||
case obj.KindUnsafePointer:
|
case objabi.KindUnsafePointer:
|
||||||
die = newdie(ctxt, &dwtypes, dwarf.DW_ABRV_BARE_PTRTYPE, name, 0)
|
die = newdie(ctxt, &dwtypes, dwarf.DW_ABRV_BARE_PTRTYPE, name, 0)
|
||||||
|
|
||||||
default:
|
default:
|
||||||
|
|
@ -659,7 +659,7 @@ func mkinternaltype(ctxt *Link, abbrev int, typename, keyname, valname string, f
|
||||||
name := mkinternaltypename(typename, keyname, valname)
|
name := mkinternaltypename(typename, keyname, valname)
|
||||||
symname := dwarf.InfoPrefix + name
|
symname := dwarf.InfoPrefix + name
|
||||||
s := ctxt.Syms.ROLookup(symname, 0)
|
s := ctxt.Syms.ROLookup(symname, 0)
|
||||||
if s != nil && s.Type == obj.SDWARFINFO {
|
if s != nil && s.Type == objabi.SDWARFINFO {
|
||||||
return s
|
return s
|
||||||
}
|
}
|
||||||
die := newdie(ctxt, &dwtypes, abbrev, name, 0)
|
die := newdie(ctxt, &dwtypes, abbrev, name, 0)
|
||||||
|
|
@ -995,7 +995,7 @@ func writelines(ctxt *Link, syms []*Symbol) ([]*Symbol, []*Symbol) {
|
||||||
if linesec == nil {
|
if linesec == nil {
|
||||||
linesec = ctxt.Syms.Lookup(".debug_line", 0)
|
linesec = ctxt.Syms.Lookup(".debug_line", 0)
|
||||||
}
|
}
|
||||||
linesec.Type = obj.SDWARFSECT
|
linesec.Type = objabi.SDWARFSECT
|
||||||
linesec.R = linesec.R[:0]
|
linesec.R = linesec.R[:0]
|
||||||
|
|
||||||
ls := linesec
|
ls := linesec
|
||||||
|
|
@ -1012,7 +1012,7 @@ func writelines(ctxt *Link, syms []*Symbol) ([]*Symbol, []*Symbol) {
|
||||||
lang := dwarf.DW_LANG_Go
|
lang := dwarf.DW_LANG_Go
|
||||||
|
|
||||||
s := ctxt.Textp[0]
|
s := ctxt.Textp[0]
|
||||||
if ctxt.DynlinkingGo() && Headtype == obj.Hdarwin {
|
if ctxt.DynlinkingGo() && Headtype == objabi.Hdarwin {
|
||||||
s = ctxt.Textp[1] // skip runtime.text
|
s = ctxt.Textp[1] // skip runtime.text
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -1081,9 +1081,9 @@ func writelines(ctxt *Link, syms []*Symbol) ([]*Symbol, []*Symbol) {
|
||||||
|
|
||||||
dsym := ctxt.Syms.Lookup(dwarf.InfoPrefix+s.Name, int(s.Version))
|
dsym := ctxt.Syms.Lookup(dwarf.InfoPrefix+s.Name, int(s.Version))
|
||||||
dsym.Attr |= AttrHidden | AttrReachable
|
dsym.Attr |= AttrHidden | AttrReachable
|
||||||
dsym.Type = obj.SDWARFINFO
|
dsym.Type = objabi.SDWARFINFO
|
||||||
for _, r := range dsym.R {
|
for _, r := range dsym.R {
|
||||||
if r.Type == obj.R_DWARFREF && r.Sym.Size == 0 {
|
if r.Type == objabi.R_DWARFREF && r.Sym.Size == 0 {
|
||||||
if Buildmode == BuildmodeShared {
|
if Buildmode == BuildmodeShared {
|
||||||
// These type symbols may not be present in BuildmodeShared. Skip.
|
// These type symbols may not be present in BuildmodeShared. Skip.
|
||||||
continue
|
continue
|
||||||
|
|
@ -1178,7 +1178,7 @@ func writeframes(ctxt *Link, syms []*Symbol) []*Symbol {
|
||||||
if framesec == nil {
|
if framesec == nil {
|
||||||
framesec = ctxt.Syms.Lookup(".debug_frame", 0)
|
framesec = ctxt.Syms.Lookup(".debug_frame", 0)
|
||||||
}
|
}
|
||||||
framesec.Type = obj.SDWARFSECT
|
framesec.Type = objabi.SDWARFSECT
|
||||||
framesec.R = framesec.R[:0]
|
framesec.R = framesec.R[:0]
|
||||||
fs := framesec
|
fs := framesec
|
||||||
syms = append(syms, fs)
|
syms = append(syms, fs)
|
||||||
|
|
@ -1300,7 +1300,7 @@ func writeinfo(ctxt *Link, syms []*Symbol, funcs []*Symbol) []*Symbol {
|
||||||
infosec = ctxt.Syms.Lookup(".debug_info", 0)
|
infosec = ctxt.Syms.Lookup(".debug_info", 0)
|
||||||
}
|
}
|
||||||
infosec.R = infosec.R[:0]
|
infosec.R = infosec.R[:0]
|
||||||
infosec.Type = obj.SDWARFINFO
|
infosec.Type = objabi.SDWARFINFO
|
||||||
infosec.Attr |= AttrReachable
|
infosec.Attr |= AttrReachable
|
||||||
syms = append(syms, infosec)
|
syms = append(syms, infosec)
|
||||||
|
|
||||||
|
|
@ -1366,7 +1366,7 @@ func ispubtype(die *dwarf.DWDie) bool {
|
||||||
|
|
||||||
func writepub(ctxt *Link, sname string, ispub func(*dwarf.DWDie) bool, syms []*Symbol) []*Symbol {
|
func writepub(ctxt *Link, sname string, ispub func(*dwarf.DWDie) bool, syms []*Symbol) []*Symbol {
|
||||||
s := ctxt.Syms.Lookup(sname, 0)
|
s := ctxt.Syms.Lookup(sname, 0)
|
||||||
s.Type = obj.SDWARFSECT
|
s.Type = objabi.SDWARFSECT
|
||||||
syms = append(syms, s)
|
syms = append(syms, s)
|
||||||
|
|
||||||
for compunit := dwroot.Child; compunit != nil; compunit = compunit.Link {
|
for compunit := dwroot.Child; compunit != nil; compunit = compunit.Link {
|
||||||
|
|
@ -1406,7 +1406,7 @@ func writepub(ctxt *Link, sname string, ispub func(*dwarf.DWDie) bool, syms []*S
|
||||||
*/
|
*/
|
||||||
func writearanges(ctxt *Link, syms []*Symbol) []*Symbol {
|
func writearanges(ctxt *Link, syms []*Symbol) []*Symbol {
|
||||||
s := ctxt.Syms.Lookup(".debug_aranges", 0)
|
s := ctxt.Syms.Lookup(".debug_aranges", 0)
|
||||||
s.Type = obj.SDWARFSECT
|
s.Type = objabi.SDWARFSECT
|
||||||
// The first tuple is aligned to a multiple of the size of a single tuple
|
// The first tuple is aligned to a multiple of the size of a single tuple
|
||||||
// (twice the size of an address)
|
// (twice the size of an address)
|
||||||
headersize := int(Rnd(4+2+4+1+1, int64(SysArch.PtrSize*2))) // don't count unit_length field itself
|
headersize := int(Rnd(4+2+4+1+1, int64(SysArch.PtrSize*2))) // don't count unit_length field itself
|
||||||
|
|
@ -1450,7 +1450,7 @@ func writegdbscript(ctxt *Link, syms []*Symbol) []*Symbol {
|
||||||
|
|
||||||
if gdbscript != "" {
|
if gdbscript != "" {
|
||||||
s := ctxt.Syms.Lookup(".debug_gdb_scripts", 0)
|
s := ctxt.Syms.Lookup(".debug_gdb_scripts", 0)
|
||||||
s.Type = obj.SDWARFSECT
|
s.Type = objabi.SDWARFSECT
|
||||||
syms = append(syms, s)
|
syms = append(syms, s)
|
||||||
Adduint8(ctxt, s, 1) // magic 1 byte?
|
Adduint8(ctxt, s, 1) // magic 1 byte?
|
||||||
Addstring(s, gdbscript)
|
Addstring(s, gdbscript)
|
||||||
|
|
@ -1474,25 +1474,25 @@ func dwarfgeneratedebugsyms(ctxt *Link) {
|
||||||
if *FlagW { // disable dwarf
|
if *FlagW { // disable dwarf
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
if *FlagS && Headtype != obj.Hdarwin {
|
if *FlagS && Headtype != objabi.Hdarwin {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
if Headtype == obj.Hplan9 {
|
if Headtype == objabi.Hplan9 {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
if Linkmode == LinkExternal {
|
if Linkmode == LinkExternal {
|
||||||
switch {
|
switch {
|
||||||
case Iself:
|
case Iself:
|
||||||
case Headtype == obj.Hdarwin:
|
case Headtype == objabi.Hdarwin:
|
||||||
case Headtype == obj.Hwindows:
|
case Headtype == objabi.Hwindows:
|
||||||
default:
|
default:
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if ctxt.Debugvlog != 0 {
|
if ctxt.Debugvlog != 0 {
|
||||||
ctxt.Logf("%5.2f dwarf\n", obj.Cputime())
|
ctxt.Logf("%5.2f dwarf\n", Cputime())
|
||||||
}
|
}
|
||||||
|
|
||||||
// Forctxt.Diagnostic messages.
|
// Forctxt.Diagnostic messages.
|
||||||
|
|
@ -1507,7 +1507,7 @@ func dwarfgeneratedebugsyms(ctxt *Link) {
|
||||||
die := newdie(ctxt, &dwtypes, dwarf.DW_ABRV_BASETYPE, "uintptr", 0) // needed for array size
|
die := newdie(ctxt, &dwtypes, dwarf.DW_ABRV_BASETYPE, "uintptr", 0) // needed for array size
|
||||||
newattr(die, dwarf.DW_AT_encoding, dwarf.DW_CLS_CONSTANT, dwarf.DW_ATE_unsigned, 0)
|
newattr(die, dwarf.DW_AT_encoding, dwarf.DW_CLS_CONSTANT, dwarf.DW_ATE_unsigned, 0)
|
||||||
newattr(die, dwarf.DW_AT_byte_size, dwarf.DW_CLS_CONSTANT, int64(SysArch.PtrSize), 0)
|
newattr(die, dwarf.DW_AT_byte_size, dwarf.DW_CLS_CONSTANT, int64(SysArch.PtrSize), 0)
|
||||||
newattr(die, dwarf.DW_AT_go_kind, dwarf.DW_CLS_CONSTANT, obj.KindUintptr, 0)
|
newattr(die, dwarf.DW_AT_go_kind, dwarf.DW_CLS_CONSTANT, objabi.KindUintptr, 0)
|
||||||
|
|
||||||
// Prototypes needed for type synthesis.
|
// Prototypes needed for type synthesis.
|
||||||
prototypedies = map[string]*dwarf.DWDie{
|
prototypedies = map[string]*dwarf.DWDie{
|
||||||
|
|
|
||||||
|
|
@ -5,7 +5,7 @@
|
||||||
package ld
|
package ld
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"cmd/internal/obj"
|
"cmd/internal/objabi"
|
||||||
"cmd/internal/sys"
|
"cmd/internal/sys"
|
||||||
"crypto/sha1"
|
"crypto/sha1"
|
||||||
"encoding/binary"
|
"encoding/binary"
|
||||||
|
|
@ -950,7 +950,7 @@ func Elfinit(ctxt *Link) {
|
||||||
case sys.ARM, sys.MIPS:
|
case sys.ARM, sys.MIPS:
|
||||||
if SysArch.Family == sys.ARM {
|
if SysArch.Family == sys.ARM {
|
||||||
// we use EABI on linux/arm, freebsd/arm, netbsd/arm.
|
// we use EABI on linux/arm, freebsd/arm, netbsd/arm.
|
||||||
if Headtype == obj.Hlinux || Headtype == obj.Hfreebsd || Headtype == obj.Hnetbsd {
|
if Headtype == objabi.Hlinux || Headtype == objabi.Hfreebsd || Headtype == objabi.Hnetbsd {
|
||||||
// We set a value here that makes no indication of which
|
// We set a value here that makes no indication of which
|
||||||
// float ABI the object uses, because this is information
|
// float ABI the object uses, because this is information
|
||||||
// used by the dynamic linker to compare executables and
|
// used by the dynamic linker to compare executables and
|
||||||
|
|
@ -1451,7 +1451,7 @@ func elfdynhash(ctxt *Link) {
|
||||||
|
|
||||||
nsym := Nelfsym
|
nsym := Nelfsym
|
||||||
s := ctxt.Syms.Lookup(".hash", 0)
|
s := ctxt.Syms.Lookup(".hash", 0)
|
||||||
s.Type = obj.SELFROSECT
|
s.Type = objabi.SELFROSECT
|
||||||
s.Attr |= AttrReachable
|
s.Attr |= AttrReachable
|
||||||
|
|
||||||
i := nsym
|
i := nsym
|
||||||
|
|
@ -1856,7 +1856,7 @@ func Elfemitreloc(ctxt *Link) {
|
||||||
func addgonote(ctxt *Link, sectionName string, tag uint32, desc []byte) {
|
func addgonote(ctxt *Link, sectionName string, tag uint32, desc []byte) {
|
||||||
s := ctxt.Syms.Lookup(sectionName, 0)
|
s := ctxt.Syms.Lookup(sectionName, 0)
|
||||||
s.Attr |= AttrReachable
|
s.Attr |= AttrReachable
|
||||||
s.Type = obj.SELFROSECT
|
s.Type = objabi.SELFROSECT
|
||||||
// namesz
|
// namesz
|
||||||
Adduint32(ctxt, s, uint32(len(ELF_NOTE_GO_NAME)))
|
Adduint32(ctxt, s, uint32(len(ELF_NOTE_GO_NAME)))
|
||||||
// descsz
|
// descsz
|
||||||
|
|
@ -1884,7 +1884,7 @@ func (ctxt *Link) doelf() {
|
||||||
/* predefine strings we need for section headers */
|
/* predefine strings we need for section headers */
|
||||||
shstrtab := ctxt.Syms.Lookup(".shstrtab", 0)
|
shstrtab := ctxt.Syms.Lookup(".shstrtab", 0)
|
||||||
|
|
||||||
shstrtab.Type = obj.SELFROSECT
|
shstrtab.Type = objabi.SELFROSECT
|
||||||
shstrtab.Attr |= AttrReachable
|
shstrtab.Attr |= AttrReachable
|
||||||
|
|
||||||
Addstring(shstrtab, "")
|
Addstring(shstrtab, "")
|
||||||
|
|
@ -1900,10 +1900,10 @@ func (ctxt *Link) doelf() {
|
||||||
if !*FlagD || Linkmode == LinkExternal {
|
if !*FlagD || Linkmode == LinkExternal {
|
||||||
Addstring(shstrtab, ".tbss")
|
Addstring(shstrtab, ".tbss")
|
||||||
}
|
}
|
||||||
if Headtype == obj.Hnetbsd {
|
if Headtype == objabi.Hnetbsd {
|
||||||
Addstring(shstrtab, ".note.netbsd.ident")
|
Addstring(shstrtab, ".note.netbsd.ident")
|
||||||
}
|
}
|
||||||
if Headtype == obj.Hopenbsd {
|
if Headtype == objabi.Hopenbsd {
|
||||||
Addstring(shstrtab, ".note.openbsd.ident")
|
Addstring(shstrtab, ".note.openbsd.ident")
|
||||||
}
|
}
|
||||||
if len(buildinfo) > 0 {
|
if len(buildinfo) > 0 {
|
||||||
|
|
@ -1992,7 +1992,7 @@ func (ctxt *Link) doelf() {
|
||||||
/* dynamic symbol table - first entry all zeros */
|
/* dynamic symbol table - first entry all zeros */
|
||||||
s := ctxt.Syms.Lookup(".dynsym", 0)
|
s := ctxt.Syms.Lookup(".dynsym", 0)
|
||||||
|
|
||||||
s.Type = obj.SELFROSECT
|
s.Type = objabi.SELFROSECT
|
||||||
s.Attr |= AttrReachable
|
s.Attr |= AttrReachable
|
||||||
if elf64 {
|
if elf64 {
|
||||||
s.Size += ELF64SYMSIZE
|
s.Size += ELF64SYMSIZE
|
||||||
|
|
@ -2003,7 +2003,7 @@ func (ctxt *Link) doelf() {
|
||||||
/* dynamic string table */
|
/* dynamic string table */
|
||||||
s = ctxt.Syms.Lookup(".dynstr", 0)
|
s = ctxt.Syms.Lookup(".dynstr", 0)
|
||||||
|
|
||||||
s.Type = obj.SELFROSECT
|
s.Type = objabi.SELFROSECT
|
||||||
s.Attr |= AttrReachable
|
s.Attr |= AttrReachable
|
||||||
if s.Size == 0 {
|
if s.Size == 0 {
|
||||||
Addstring(s, "")
|
Addstring(s, "")
|
||||||
|
|
@ -2013,30 +2013,30 @@ func (ctxt *Link) doelf() {
|
||||||
/* relocation table */
|
/* relocation table */
|
||||||
s = ctxt.Syms.Lookup(elfRelType, 0)
|
s = ctxt.Syms.Lookup(elfRelType, 0)
|
||||||
s.Attr |= AttrReachable
|
s.Attr |= AttrReachable
|
||||||
s.Type = obj.SELFROSECT
|
s.Type = objabi.SELFROSECT
|
||||||
|
|
||||||
/* global offset table */
|
/* global offset table */
|
||||||
s = ctxt.Syms.Lookup(".got", 0)
|
s = ctxt.Syms.Lookup(".got", 0)
|
||||||
|
|
||||||
s.Attr |= AttrReachable
|
s.Attr |= AttrReachable
|
||||||
s.Type = obj.SELFGOT // writable
|
s.Type = objabi.SELFGOT // writable
|
||||||
|
|
||||||
/* ppc64 glink resolver */
|
/* ppc64 glink resolver */
|
||||||
if SysArch.Family == sys.PPC64 {
|
if SysArch.Family == sys.PPC64 {
|
||||||
s := ctxt.Syms.Lookup(".glink", 0)
|
s := ctxt.Syms.Lookup(".glink", 0)
|
||||||
s.Attr |= AttrReachable
|
s.Attr |= AttrReachable
|
||||||
s.Type = obj.SELFRXSECT
|
s.Type = objabi.SELFRXSECT
|
||||||
}
|
}
|
||||||
|
|
||||||
/* hash */
|
/* hash */
|
||||||
s = ctxt.Syms.Lookup(".hash", 0)
|
s = ctxt.Syms.Lookup(".hash", 0)
|
||||||
|
|
||||||
s.Attr |= AttrReachable
|
s.Attr |= AttrReachable
|
||||||
s.Type = obj.SELFROSECT
|
s.Type = objabi.SELFROSECT
|
||||||
|
|
||||||
s = ctxt.Syms.Lookup(".got.plt", 0)
|
s = ctxt.Syms.Lookup(".got.plt", 0)
|
||||||
s.Attr |= AttrReachable
|
s.Attr |= AttrReachable
|
||||||
s.Type = obj.SELFSECT // writable
|
s.Type = objabi.SELFSECT // writable
|
||||||
|
|
||||||
s = ctxt.Syms.Lookup(".plt", 0)
|
s = ctxt.Syms.Lookup(".plt", 0)
|
||||||
|
|
||||||
|
|
@ -2044,30 +2044,30 @@ func (ctxt *Link) doelf() {
|
||||||
if SysArch.Family == sys.PPC64 {
|
if SysArch.Family == sys.PPC64 {
|
||||||
// In the ppc64 ABI, .plt is a data section
|
// In the ppc64 ABI, .plt is a data section
|
||||||
// written by the dynamic linker.
|
// written by the dynamic linker.
|
||||||
s.Type = obj.SELFSECT
|
s.Type = objabi.SELFSECT
|
||||||
} else {
|
} else {
|
||||||
s.Type = obj.SELFRXSECT
|
s.Type = objabi.SELFRXSECT
|
||||||
}
|
}
|
||||||
|
|
||||||
Thearch.Elfsetupplt(ctxt)
|
Thearch.Elfsetupplt(ctxt)
|
||||||
|
|
||||||
s = ctxt.Syms.Lookup(elfRelType+".plt", 0)
|
s = ctxt.Syms.Lookup(elfRelType+".plt", 0)
|
||||||
s.Attr |= AttrReachable
|
s.Attr |= AttrReachable
|
||||||
s.Type = obj.SELFROSECT
|
s.Type = objabi.SELFROSECT
|
||||||
|
|
||||||
s = ctxt.Syms.Lookup(".gnu.version", 0)
|
s = ctxt.Syms.Lookup(".gnu.version", 0)
|
||||||
s.Attr |= AttrReachable
|
s.Attr |= AttrReachable
|
||||||
s.Type = obj.SELFROSECT
|
s.Type = objabi.SELFROSECT
|
||||||
|
|
||||||
s = ctxt.Syms.Lookup(".gnu.version_r", 0)
|
s = ctxt.Syms.Lookup(".gnu.version_r", 0)
|
||||||
s.Attr |= AttrReachable
|
s.Attr |= AttrReachable
|
||||||
s.Type = obj.SELFROSECT
|
s.Type = objabi.SELFROSECT
|
||||||
|
|
||||||
/* define dynamic elf table */
|
/* define dynamic elf table */
|
||||||
s = ctxt.Syms.Lookup(".dynamic", 0)
|
s = ctxt.Syms.Lookup(".dynamic", 0)
|
||||||
|
|
||||||
s.Attr |= AttrReachable
|
s.Attr |= AttrReachable
|
||||||
s.Type = obj.SELFSECT // writable
|
s.Type = objabi.SELFSECT // writable
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* .dynamic table
|
* .dynamic table
|
||||||
|
|
@ -2120,7 +2120,7 @@ func (ctxt *Link) doelf() {
|
||||||
// part of the .note.go.abihash section in data.go:func address().
|
// part of the .note.go.abihash section in data.go:func address().
|
||||||
s := ctxt.Syms.Lookup("go.link.abihashbytes", 0)
|
s := ctxt.Syms.Lookup("go.link.abihashbytes", 0)
|
||||||
s.Attr |= AttrLocal
|
s.Attr |= AttrLocal
|
||||||
s.Type = obj.SRODATA
|
s.Type = objabi.SRODATA
|
||||||
s.Attr |= AttrSpecial
|
s.Attr |= AttrSpecial
|
||||||
s.Attr |= AttrReachable
|
s.Attr |= AttrReachable
|
||||||
s.Size = int64(sha1.Size)
|
s.Size = int64(sha1.Size)
|
||||||
|
|
@ -2276,7 +2276,7 @@ func Asmbelf(ctxt *Link, symo int64) {
|
||||||
* segment boundaries downwards to include it.
|
* segment boundaries downwards to include it.
|
||||||
* Except on NaCl where it must not be loaded.
|
* Except on NaCl where it must not be loaded.
|
||||||
*/
|
*/
|
||||||
if Headtype != obj.Hnacl {
|
if Headtype != objabi.Hnacl {
|
||||||
o := int64(Segtext.Vaddr - pph.vaddr)
|
o := int64(Segtext.Vaddr - pph.vaddr)
|
||||||
Segtext.Vaddr -= uint64(o)
|
Segtext.Vaddr -= uint64(o)
|
||||||
Segtext.Length += uint64(o)
|
Segtext.Length += uint64(o)
|
||||||
|
|
@ -2294,22 +2294,22 @@ func Asmbelf(ctxt *Link, symo int64) {
|
||||||
sh.addralign = 1
|
sh.addralign = 1
|
||||||
if interpreter == "" {
|
if interpreter == "" {
|
||||||
switch Headtype {
|
switch Headtype {
|
||||||
case obj.Hlinux:
|
case objabi.Hlinux:
|
||||||
interpreter = Thearch.Linuxdynld
|
interpreter = Thearch.Linuxdynld
|
||||||
|
|
||||||
case obj.Hfreebsd:
|
case objabi.Hfreebsd:
|
||||||
interpreter = Thearch.Freebsddynld
|
interpreter = Thearch.Freebsddynld
|
||||||
|
|
||||||
case obj.Hnetbsd:
|
case objabi.Hnetbsd:
|
||||||
interpreter = Thearch.Netbsddynld
|
interpreter = Thearch.Netbsddynld
|
||||||
|
|
||||||
case obj.Hopenbsd:
|
case objabi.Hopenbsd:
|
||||||
interpreter = Thearch.Openbsddynld
|
interpreter = Thearch.Openbsddynld
|
||||||
|
|
||||||
case obj.Hdragonfly:
|
case objabi.Hdragonfly:
|
||||||
interpreter = Thearch.Dragonflydynld
|
interpreter = Thearch.Dragonflydynld
|
||||||
|
|
||||||
case obj.Hsolaris:
|
case objabi.Hsolaris:
|
||||||
interpreter = Thearch.Solarisdynld
|
interpreter = Thearch.Solarisdynld
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
@ -2323,14 +2323,14 @@ func Asmbelf(ctxt *Link, symo int64) {
|
||||||
}
|
}
|
||||||
|
|
||||||
pnote = nil
|
pnote = nil
|
||||||
if Headtype == obj.Hnetbsd || Headtype == obj.Hopenbsd {
|
if Headtype == objabi.Hnetbsd || Headtype == objabi.Hopenbsd {
|
||||||
var sh *ElfShdr
|
var sh *ElfShdr
|
||||||
switch Headtype {
|
switch Headtype {
|
||||||
case obj.Hnetbsd:
|
case objabi.Hnetbsd:
|
||||||
sh = elfshname(".note.netbsd.ident")
|
sh = elfshname(".note.netbsd.ident")
|
||||||
resoff -= int64(elfnetbsdsig(sh, uint64(startva), uint64(resoff)))
|
resoff -= int64(elfnetbsdsig(sh, uint64(startva), uint64(resoff)))
|
||||||
|
|
||||||
case obj.Hopenbsd:
|
case objabi.Hopenbsd:
|
||||||
sh = elfshname(".note.openbsd.ident")
|
sh = elfshname(".note.openbsd.ident")
|
||||||
resoff -= int64(elfopenbsdsig(sh, uint64(startva), uint64(resoff)))
|
resoff -= int64(elfopenbsdsig(sh, uint64(startva), uint64(resoff)))
|
||||||
}
|
}
|
||||||
|
|
@ -2537,7 +2537,7 @@ func Asmbelf(ctxt *Link, symo int64) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if Headtype == obj.Hlinux {
|
if Headtype == objabi.Hlinux {
|
||||||
ph := newElfPhdr()
|
ph := newElfPhdr()
|
||||||
ph.type_ = PT_GNU_STACK
|
ph.type_ = PT_GNU_STACK
|
||||||
ph.flags = PF_W + PF_R
|
ph.flags = PF_W + PF_R
|
||||||
|
|
@ -2547,7 +2547,7 @@ func Asmbelf(ctxt *Link, symo int64) {
|
||||||
ph.type_ = PT_PAX_FLAGS
|
ph.type_ = PT_PAX_FLAGS
|
||||||
ph.flags = 0x2a00 // mprotect, randexec, emutramp disabled
|
ph.flags = 0x2a00 // mprotect, randexec, emutramp disabled
|
||||||
ph.align = uint64(SysArch.RegSize)
|
ph.align = uint64(SysArch.RegSize)
|
||||||
} else if Headtype == obj.Hsolaris {
|
} else if Headtype == objabi.Hsolaris {
|
||||||
ph := newElfPhdr()
|
ph := newElfPhdr()
|
||||||
ph.type_ = PT_SUNWSTACK
|
ph.type_ = PT_SUNWSTACK
|
||||||
ph.flags = PF_W + PF_R
|
ph.flags = PF_W + PF_R
|
||||||
|
|
@ -2596,10 +2596,10 @@ elfobj:
|
||||||
elfshreloc(sect)
|
elfshreloc(sect)
|
||||||
}
|
}
|
||||||
for _, s := range dwarfp {
|
for _, s := range dwarfp {
|
||||||
if len(s.R) > 0 || s.Type == obj.SDWARFINFO {
|
if len(s.R) > 0 || s.Type == objabi.SDWARFINFO {
|
||||||
elfshreloc(s.Sect)
|
elfshreloc(s.Sect)
|
||||||
}
|
}
|
||||||
if s.Type == obj.SDWARFINFO {
|
if s.Type == objabi.SDWARFINFO {
|
||||||
break
|
break
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
@ -2634,13 +2634,13 @@ elfobj:
|
||||||
eh.ident[EI_MAG1] = 'E'
|
eh.ident[EI_MAG1] = 'E'
|
||||||
eh.ident[EI_MAG2] = 'L'
|
eh.ident[EI_MAG2] = 'L'
|
||||||
eh.ident[EI_MAG3] = 'F'
|
eh.ident[EI_MAG3] = 'F'
|
||||||
if Headtype == obj.Hfreebsd {
|
if Headtype == objabi.Hfreebsd {
|
||||||
eh.ident[EI_OSABI] = ELFOSABI_FREEBSD
|
eh.ident[EI_OSABI] = ELFOSABI_FREEBSD
|
||||||
} else if Headtype == obj.Hnetbsd {
|
} else if Headtype == objabi.Hnetbsd {
|
||||||
eh.ident[EI_OSABI] = ELFOSABI_NETBSD
|
eh.ident[EI_OSABI] = ELFOSABI_NETBSD
|
||||||
} else if Headtype == obj.Hopenbsd {
|
} else if Headtype == objabi.Hopenbsd {
|
||||||
eh.ident[EI_OSABI] = ELFOSABI_OPENBSD
|
eh.ident[EI_OSABI] = ELFOSABI_OPENBSD
|
||||||
} else if Headtype == obj.Hdragonfly {
|
} else if Headtype == objabi.Hdragonfly {
|
||||||
eh.ident[EI_OSABI] = ELFOSABI_NONE
|
eh.ident[EI_OSABI] = ELFOSABI_NONE
|
||||||
}
|
}
|
||||||
if elf64 {
|
if elf64 {
|
||||||
|
|
@ -2683,10 +2683,10 @@ elfobj:
|
||||||
a += int64(elfwriteinterp())
|
a += int64(elfwriteinterp())
|
||||||
}
|
}
|
||||||
if Linkmode != LinkExternal {
|
if Linkmode != LinkExternal {
|
||||||
if Headtype == obj.Hnetbsd {
|
if Headtype == objabi.Hnetbsd {
|
||||||
a += int64(elfwritenetbsdsig())
|
a += int64(elfwritenetbsdsig())
|
||||||
}
|
}
|
||||||
if Headtype == obj.Hopenbsd {
|
if Headtype == objabi.Hopenbsd {
|
||||||
a += int64(elfwriteopenbsdsig())
|
a += int64(elfwriteopenbsdsig())
|
||||||
}
|
}
|
||||||
if len(buildinfo) > 0 {
|
if len(buildinfo) > 0 {
|
||||||
|
|
@ -2715,7 +2715,7 @@ func Elfadddynsym(ctxt *Link, s *Symbol) {
|
||||||
/* type */
|
/* type */
|
||||||
t := STB_GLOBAL << 4
|
t := STB_GLOBAL << 4
|
||||||
|
|
||||||
if s.Attr.CgoExport() && s.Type&obj.SMASK == obj.STEXT {
|
if s.Attr.CgoExport() && s.Type&objabi.SMASK == objabi.STEXT {
|
||||||
t |= STT_FUNC
|
t |= STT_FUNC
|
||||||
} else {
|
} else {
|
||||||
t |= STT_OBJECT
|
t |= STT_OBJECT
|
||||||
|
|
@ -2726,14 +2726,14 @@ func Elfadddynsym(ctxt *Link, s *Symbol) {
|
||||||
Adduint8(ctxt, d, 0)
|
Adduint8(ctxt, d, 0)
|
||||||
|
|
||||||
/* section where symbol is defined */
|
/* section where symbol is defined */
|
||||||
if s.Type == obj.SDYNIMPORT {
|
if s.Type == objabi.SDYNIMPORT {
|
||||||
Adduint16(ctxt, d, SHN_UNDEF)
|
Adduint16(ctxt, d, SHN_UNDEF)
|
||||||
} else {
|
} else {
|
||||||
Adduint16(ctxt, d, 1)
|
Adduint16(ctxt, d, 1)
|
||||||
}
|
}
|
||||||
|
|
||||||
/* value */
|
/* value */
|
||||||
if s.Type == obj.SDYNIMPORT {
|
if s.Type == objabi.SDYNIMPORT {
|
||||||
Adduint64(ctxt, d, 0)
|
Adduint64(ctxt, d, 0)
|
||||||
} else {
|
} else {
|
||||||
Addaddr(ctxt, d, s)
|
Addaddr(ctxt, d, s)
|
||||||
|
|
@ -2757,7 +2757,7 @@ func Elfadddynsym(ctxt *Link, s *Symbol) {
|
||||||
Adduint32(ctxt, d, uint32(Addstring(ctxt.Syms.Lookup(".dynstr", 0), name)))
|
Adduint32(ctxt, d, uint32(Addstring(ctxt.Syms.Lookup(".dynstr", 0), name)))
|
||||||
|
|
||||||
/* value */
|
/* value */
|
||||||
if s.Type == obj.SDYNIMPORT {
|
if s.Type == objabi.SDYNIMPORT {
|
||||||
Adduint32(ctxt, d, 0)
|
Adduint32(ctxt, d, 0)
|
||||||
} else {
|
} else {
|
||||||
Addaddr(ctxt, d, s)
|
Addaddr(ctxt, d, s)
|
||||||
|
|
@ -2770,9 +2770,9 @@ func Elfadddynsym(ctxt *Link, s *Symbol) {
|
||||||
t := STB_GLOBAL << 4
|
t := STB_GLOBAL << 4
|
||||||
|
|
||||||
// TODO(mwhudson): presumably the behavior should actually be the same on both arm and 386.
|
// TODO(mwhudson): presumably the behavior should actually be the same on both arm and 386.
|
||||||
if SysArch.Family == sys.I386 && s.Attr.CgoExport() && s.Type&obj.SMASK == obj.STEXT {
|
if SysArch.Family == sys.I386 && s.Attr.CgoExport() && s.Type&objabi.SMASK == objabi.STEXT {
|
||||||
t |= STT_FUNC
|
t |= STT_FUNC
|
||||||
} else if SysArch.Family == sys.ARM && s.Attr.CgoExportDynamic() && s.Type&obj.SMASK == obj.STEXT {
|
} else if SysArch.Family == sys.ARM && s.Attr.CgoExportDynamic() && s.Type&objabi.SMASK == objabi.STEXT {
|
||||||
t |= STT_FUNC
|
t |= STT_FUNC
|
||||||
} else {
|
} else {
|
||||||
t |= STT_OBJECT
|
t |= STT_OBJECT
|
||||||
|
|
@ -2781,7 +2781,7 @@ func Elfadddynsym(ctxt *Link, s *Symbol) {
|
||||||
Adduint8(ctxt, d, 0)
|
Adduint8(ctxt, d, 0)
|
||||||
|
|
||||||
/* shndx */
|
/* shndx */
|
||||||
if s.Type == obj.SDYNIMPORT {
|
if s.Type == objabi.SDYNIMPORT {
|
||||||
Adduint16(ctxt, d, SHN_UNDEF)
|
Adduint16(ctxt, d, SHN_UNDEF)
|
||||||
} else {
|
} else {
|
||||||
Adduint16(ctxt, d, 1)
|
Adduint16(ctxt, d, 1)
|
||||||
|
|
|
||||||
|
|
@ -9,7 +9,7 @@ package ld
|
||||||
import (
|
import (
|
||||||
"bytes"
|
"bytes"
|
||||||
"cmd/internal/bio"
|
"cmd/internal/bio"
|
||||||
"cmd/internal/obj"
|
"cmd/internal/objabi"
|
||||||
"fmt"
|
"fmt"
|
||||||
"io"
|
"io"
|
||||||
"os"
|
"os"
|
||||||
|
|
@ -174,7 +174,7 @@ func loadcgo(ctxt *Link, file string, pkg string, p string) {
|
||||||
// to force a link of foo.so.
|
// to force a link of foo.so.
|
||||||
havedynamic = 1
|
havedynamic = 1
|
||||||
|
|
||||||
if Headtype == obj.Hdarwin {
|
if Headtype == objabi.Hdarwin {
|
||||||
Machoadddynlib(lib)
|
Machoadddynlib(lib)
|
||||||
} else {
|
} else {
|
||||||
dynlib = append(dynlib, lib)
|
dynlib = append(dynlib, lib)
|
||||||
|
|
@ -190,12 +190,12 @@ func loadcgo(ctxt *Link, file string, pkg string, p string) {
|
||||||
s = ctxt.Syms.Lookup(local, 0)
|
s = ctxt.Syms.Lookup(local, 0)
|
||||||
if local != f[1] {
|
if local != f[1] {
|
||||||
}
|
}
|
||||||
if s.Type == 0 || s.Type == obj.SXREF || s.Type == obj.SHOSTOBJ {
|
if s.Type == 0 || s.Type == objabi.SXREF || s.Type == objabi.SHOSTOBJ {
|
||||||
s.Dynimplib = lib
|
s.Dynimplib = lib
|
||||||
s.Extname = remote
|
s.Extname = remote
|
||||||
s.Dynimpvers = q
|
s.Dynimpvers = q
|
||||||
if s.Type != obj.SHOSTOBJ {
|
if s.Type != objabi.SHOSTOBJ {
|
||||||
s.Type = obj.SDYNIMPORT
|
s.Type = objabi.SDYNIMPORT
|
||||||
}
|
}
|
||||||
havedynamic = 1
|
havedynamic = 1
|
||||||
}
|
}
|
||||||
|
|
@ -209,7 +209,7 @@ func loadcgo(ctxt *Link, file string, pkg string, p string) {
|
||||||
}
|
}
|
||||||
local = f[1]
|
local = f[1]
|
||||||
s = ctxt.Syms.Lookup(local, 0)
|
s = ctxt.Syms.Lookup(local, 0)
|
||||||
s.Type = obj.SHOSTOBJ
|
s.Type = objabi.SHOSTOBJ
|
||||||
s.Size = 0
|
s.Size = 0
|
||||||
continue
|
continue
|
||||||
}
|
}
|
||||||
|
|
@ -322,9 +322,9 @@ func Adddynsym(ctxt *Link, s *Symbol) {
|
||||||
|
|
||||||
if Iself {
|
if Iself {
|
||||||
Elfadddynsym(ctxt, s)
|
Elfadddynsym(ctxt, s)
|
||||||
} else if Headtype == obj.Hdarwin {
|
} else if Headtype == objabi.Hdarwin {
|
||||||
Errorf(s, "adddynsym: missed symbol (Extname=%s)", s.Extname)
|
Errorf(s, "adddynsym: missed symbol (Extname=%s)", s.Extname)
|
||||||
} else if Headtype == obj.Hwindows {
|
} else if Headtype == objabi.Hwindows {
|
||||||
// already taken care of
|
// already taken care of
|
||||||
} else {
|
} else {
|
||||||
Errorf(s, "adddynsym: unsupported binary format")
|
Errorf(s, "adddynsym: unsupported binary format")
|
||||||
|
|
@ -347,7 +347,7 @@ func fieldtrack(ctxt *Link) {
|
||||||
buf.WriteString("\n")
|
buf.WriteString("\n")
|
||||||
}
|
}
|
||||||
|
|
||||||
s.Type = obj.SCONST
|
s.Type = objabi.SCONST
|
||||||
s.Value = 0
|
s.Value = 0
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
@ -363,7 +363,7 @@ func fieldtrack(ctxt *Link) {
|
||||||
}
|
}
|
||||||
|
|
||||||
func (ctxt *Link) addexport() {
|
func (ctxt *Link) addexport() {
|
||||||
if Headtype == obj.Hdarwin {
|
if Headtype == objabi.Hdarwin {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -32,7 +32,6 @@
|
||||||
package ld
|
package ld
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"cmd/internal/obj"
|
|
||||||
"io/ioutil"
|
"io/ioutil"
|
||||||
"os"
|
"os"
|
||||||
"path"
|
"path"
|
||||||
|
|
@ -105,7 +104,7 @@ func addlibpath(ctxt *Link, srcref string, objref string, file string, pkg strin
|
||||||
}
|
}
|
||||||
|
|
||||||
if ctxt.Debugvlog > 1 {
|
if ctxt.Debugvlog > 1 {
|
||||||
ctxt.Logf("%5.2f addlibpath: srcref: %s objref: %s file: %s pkg: %s shlibnamefile: %s\n", obj.Cputime(), srcref, objref, file, pkg, shlibnamefile)
|
ctxt.Logf("%5.2f addlibpath: srcref: %s objref: %s file: %s pkg: %s shlibnamefile: %s\n", Cputime(), srcref, objref, file, pkg, shlibnamefile)
|
||||||
}
|
}
|
||||||
|
|
||||||
ctxt.Library = append(ctxt.Library, &Library{})
|
ctxt.Library = append(ctxt.Library, &Library{})
|
||||||
|
|
|
||||||
|
|
@ -3,7 +3,7 @@ package ld
|
||||||
import (
|
import (
|
||||||
"bytes"
|
"bytes"
|
||||||
"cmd/internal/bio"
|
"cmd/internal/bio"
|
||||||
"cmd/internal/obj"
|
"cmd/internal/objabi"
|
||||||
"cmd/internal/sys"
|
"cmd/internal/sys"
|
||||||
"encoding/binary"
|
"encoding/binary"
|
||||||
"fmt"
|
"fmt"
|
||||||
|
|
@ -444,7 +444,7 @@ func parseArmAttributes(ctxt *Link, e binary.ByteOrder, data []byte) {
|
||||||
|
|
||||||
func ldelf(ctxt *Link, f *bio.Reader, pkg string, length int64, pn string) {
|
func ldelf(ctxt *Link, f *bio.Reader, pkg string, length int64, pn string) {
|
||||||
if ctxt.Debugvlog != 0 {
|
if ctxt.Debugvlog != 0 {
|
||||||
ctxt.Logf("%5.2f ldelf %s\n", obj.Cputime(), pn)
|
ctxt.Logf("%5.2f ldelf %s\n", Cputime(), pn)
|
||||||
}
|
}
|
||||||
|
|
||||||
localSymVersion := ctxt.Syms.IncVersion()
|
localSymVersion := ctxt.Syms.IncVersion()
|
||||||
|
|
@ -718,21 +718,21 @@ func ldelf(ctxt *Link, f *bio.Reader, pkg string, length int64, pn string) {
|
||||||
goto bad
|
goto bad
|
||||||
|
|
||||||
case ElfSectFlagAlloc:
|
case ElfSectFlagAlloc:
|
||||||
s.Type = obj.SRODATA
|
s.Type = objabi.SRODATA
|
||||||
|
|
||||||
case ElfSectFlagAlloc + ElfSectFlagWrite:
|
case ElfSectFlagAlloc + ElfSectFlagWrite:
|
||||||
if sect.type_ == ElfSectNobits {
|
if sect.type_ == ElfSectNobits {
|
||||||
s.Type = obj.SNOPTRBSS
|
s.Type = objabi.SNOPTRBSS
|
||||||
} else {
|
} else {
|
||||||
s.Type = obj.SNOPTRDATA
|
s.Type = objabi.SNOPTRDATA
|
||||||
}
|
}
|
||||||
|
|
||||||
case ElfSectFlagAlloc + ElfSectFlagExec:
|
case ElfSectFlagAlloc + ElfSectFlagExec:
|
||||||
s.Type = obj.STEXT
|
s.Type = objabi.STEXT
|
||||||
}
|
}
|
||||||
|
|
||||||
if sect.name == ".got" || sect.name == ".toc" {
|
if sect.name == ".got" || sect.name == ".toc" {
|
||||||
s.Type = obj.SELFGOT
|
s.Type = objabi.SELFGOT
|
||||||
}
|
}
|
||||||
if sect.type_ == ElfSectProgbits {
|
if sect.type_ == ElfSectProgbits {
|
||||||
s.P = sect.base
|
s.P = sect.base
|
||||||
|
|
@ -761,8 +761,8 @@ func ldelf(ctxt *Link, f *bio.Reader, pkg string, length int64, pn string) {
|
||||||
if uint64(s.Size) < sym.size {
|
if uint64(s.Size) < sym.size {
|
||||||
s.Size = int64(sym.size)
|
s.Size = int64(sym.size)
|
||||||
}
|
}
|
||||||
if s.Type == 0 || s.Type == obj.SXREF {
|
if s.Type == 0 || s.Type == objabi.SXREF {
|
||||||
s.Type = obj.SNOPTRBSS
|
s.Type = objabi.SNOPTRBSS
|
||||||
}
|
}
|
||||||
continue
|
continue
|
||||||
}
|
}
|
||||||
|
|
@ -804,14 +804,14 @@ func ldelf(ctxt *Link, f *bio.Reader, pkg string, length int64, pn string) {
|
||||||
|
|
||||||
s.Sub = sect.sym.Sub
|
s.Sub = sect.sym.Sub
|
||||||
sect.sym.Sub = s
|
sect.sym.Sub = s
|
||||||
s.Type = sect.sym.Type | s.Type&^obj.SMASK | obj.SSUB
|
s.Type = sect.sym.Type | s.Type&^objabi.SMASK | objabi.SSUB
|
||||||
if !s.Attr.CgoExportDynamic() {
|
if !s.Attr.CgoExportDynamic() {
|
||||||
s.Dynimplib = "" // satisfy dynimport
|
s.Dynimplib = "" // satisfy dynimport
|
||||||
}
|
}
|
||||||
s.Value = int64(sym.value)
|
s.Value = int64(sym.value)
|
||||||
s.Size = int64(sym.size)
|
s.Size = int64(sym.size)
|
||||||
s.Outer = sect.sym
|
s.Outer = sect.sym
|
||||||
if sect.sym.Type == obj.STEXT {
|
if sect.sym.Type == objabi.STEXT {
|
||||||
if s.Attr.External() && !s.Attr.DuplicateOK() {
|
if s.Attr.External() && !s.Attr.DuplicateOK() {
|
||||||
Errorf(s, "%s: duplicate symbol definition", pn)
|
Errorf(s, "%s: duplicate symbol definition", pn)
|
||||||
}
|
}
|
||||||
|
|
@ -838,7 +838,7 @@ func ldelf(ctxt *Link, f *bio.Reader, pkg string, length int64, pn string) {
|
||||||
if s.Sub != nil {
|
if s.Sub != nil {
|
||||||
s.Sub = listsort(s.Sub)
|
s.Sub = listsort(s.Sub)
|
||||||
}
|
}
|
||||||
if s.Type == obj.STEXT {
|
if s.Type == objabi.STEXT {
|
||||||
if s.Attr.OnList() {
|
if s.Attr.OnList() {
|
||||||
log.Fatalf("symbol %s listed multiple times", s.Name)
|
log.Fatalf("symbol %s listed multiple times", s.Name)
|
||||||
}
|
}
|
||||||
|
|
@ -923,7 +923,7 @@ func ldelf(ctxt *Link, f *bio.Reader, pkg string, length int64, pn string) {
|
||||||
rp.Sym = sym.sym
|
rp.Sym = sym.sym
|
||||||
}
|
}
|
||||||
|
|
||||||
rp.Type = 256 + obj.RelocType(info)
|
rp.Type = 256 + objabi.RelocType(info)
|
||||||
rp.Siz = relSize(ctxt, pn, uint32(info))
|
rp.Siz = relSize(ctxt, pn, uint32(info))
|
||||||
if rela != 0 {
|
if rela != 0 {
|
||||||
rp.Add = int64(add)
|
rp.Add = int64(add)
|
||||||
|
|
@ -1051,7 +1051,7 @@ func readelfsym(ctxt *Link, elfobj *ElfObj, i int, sym *ElfSym, needSym int, loc
|
||||||
// set dupok generally. See http://codereview.appspot.com/5823055/
|
// set dupok generally. See http://codereview.appspot.com/5823055/
|
||||||
// comment #5 for details.
|
// comment #5 for details.
|
||||||
if s != nil && sym.other == 2 {
|
if s != nil && sym.other == 2 {
|
||||||
s.Type |= obj.SHIDDEN
|
s.Type |= objabi.SHIDDEN
|
||||||
s.Attr |= AttrDuplicateOK
|
s.Attr |= AttrDuplicateOK
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
@ -1068,7 +1068,7 @@ func readelfsym(ctxt *Link, elfobj *ElfObj, i int, sym *ElfSym, needSym int, loc
|
||||||
// so put it in the hash table.
|
// so put it in the hash table.
|
||||||
if needSym != 0 {
|
if needSym != 0 {
|
||||||
s = ctxt.Syms.Lookup(sym.name, localSymVersion)
|
s = ctxt.Syms.Lookup(sym.name, localSymVersion)
|
||||||
s.Type |= obj.SHIDDEN
|
s.Type |= objabi.SHIDDEN
|
||||||
}
|
}
|
||||||
|
|
||||||
break
|
break
|
||||||
|
|
@ -1080,14 +1080,14 @@ func readelfsym(ctxt *Link, elfobj *ElfObj, i int, sym *ElfSym, needSym int, loc
|
||||||
// don't bother to add them into the hash table
|
// don't bother to add them into the hash table
|
||||||
s = ctxt.Syms.newsym(sym.name, localSymVersion)
|
s = ctxt.Syms.newsym(sym.name, localSymVersion)
|
||||||
|
|
||||||
s.Type |= obj.SHIDDEN
|
s.Type |= objabi.SHIDDEN
|
||||||
}
|
}
|
||||||
|
|
||||||
case ElfSymBindWeak:
|
case ElfSymBindWeak:
|
||||||
if needSym != 0 {
|
if needSym != 0 {
|
||||||
s = ctxt.Syms.Lookup(sym.name, 0)
|
s = ctxt.Syms.Lookup(sym.name, 0)
|
||||||
if sym.other == 2 {
|
if sym.other == 2 {
|
||||||
s.Type |= obj.SHIDDEN
|
s.Type |= objabi.SHIDDEN
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -1098,7 +1098,7 @@ func readelfsym(ctxt *Link, elfobj *ElfObj, i int, sym *ElfSym, needSym int, loc
|
||||||
}
|
}
|
||||||
|
|
||||||
if s != nil && s.Type == 0 && sym.type_ != ElfSymTypeSection {
|
if s != nil && s.Type == 0 && sym.type_ != ElfSymTypeSection {
|
||||||
s.Type = obj.SXREF
|
s.Type = objabi.SXREF
|
||||||
}
|
}
|
||||||
sym.sym = s
|
sym.sym = s
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -2,7 +2,7 @@ package ld
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"cmd/internal/bio"
|
"cmd/internal/bio"
|
||||||
"cmd/internal/obj"
|
"cmd/internal/objabi"
|
||||||
"cmd/internal/sys"
|
"cmd/internal/sys"
|
||||||
"encoding/binary"
|
"encoding/binary"
|
||||||
"fmt"
|
"fmt"
|
||||||
|
|
@ -602,16 +602,16 @@ func ldmacho(ctxt *Link, f *bio.Reader, pkg string, length int64, pn string) {
|
||||||
|
|
||||||
if sect.segname == "__TEXT" {
|
if sect.segname == "__TEXT" {
|
||||||
if sect.name == "__text" {
|
if sect.name == "__text" {
|
||||||
s.Type = obj.STEXT
|
s.Type = objabi.STEXT
|
||||||
} else {
|
} else {
|
||||||
s.Type = obj.SRODATA
|
s.Type = objabi.SRODATA
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
if sect.name == "__bss" {
|
if sect.name == "__bss" {
|
||||||
s.Type = obj.SNOPTRBSS
|
s.Type = objabi.SNOPTRBSS
|
||||||
s.P = s.P[:0]
|
s.P = s.P[:0]
|
||||||
} else {
|
} else {
|
||||||
s.Type = obj.SNOPTRDATA
|
s.Type = objabi.SNOPTRDATA
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -663,7 +663,7 @@ func ldmacho(ctxt *Link, f *bio.Reader, pkg string, length int64, pn string) {
|
||||||
Exitf("%s: duplicate symbol reference: %s in both %s and %s", pn, s.Name, s.Outer.Name, sect.sym.Name)
|
Exitf("%s: duplicate symbol reference: %s in both %s and %s", pn, s.Name, s.Outer.Name, sect.sym.Name)
|
||||||
}
|
}
|
||||||
|
|
||||||
s.Type = outer.Type | obj.SSUB
|
s.Type = outer.Type | objabi.SSUB
|
||||||
s.Sub = outer.Sub
|
s.Sub = outer.Sub
|
||||||
outer.Sub = s
|
outer.Sub = s
|
||||||
s.Outer = outer
|
s.Outer = outer
|
||||||
|
|
@ -671,7 +671,7 @@ func ldmacho(ctxt *Link, f *bio.Reader, pkg string, length int64, pn string) {
|
||||||
if !s.Attr.CgoExportDynamic() {
|
if !s.Attr.CgoExportDynamic() {
|
||||||
s.Dynimplib = "" // satisfy dynimport
|
s.Dynimplib = "" // satisfy dynimport
|
||||||
}
|
}
|
||||||
if outer.Type == obj.STEXT {
|
if outer.Type == objabi.STEXT {
|
||||||
if s.Attr.External() && !s.Attr.DuplicateOK() {
|
if s.Attr.External() && !s.Attr.DuplicateOK() {
|
||||||
Errorf(s, "%s: duplicate symbol definition", pn)
|
Errorf(s, "%s: duplicate symbol definition", pn)
|
||||||
}
|
}
|
||||||
|
|
@ -702,7 +702,7 @@ func ldmacho(ctxt *Link, f *bio.Reader, pkg string, length int64, pn string) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if s.Type == obj.STEXT {
|
if s.Type == objabi.STEXT {
|
||||||
if s.Attr.OnList() {
|
if s.Attr.OnList() {
|
||||||
log.Fatalf("symbol %s listed multiple times", s.Name)
|
log.Fatalf("symbol %s listed multiple times", s.Name)
|
||||||
}
|
}
|
||||||
|
|
@ -772,7 +772,7 @@ func ldmacho(ctxt *Link, f *bio.Reader, pkg string, length int64, pn string) {
|
||||||
// want to make it pc-relative aka relative to rp->off+4
|
// want to make it pc-relative aka relative to rp->off+4
|
||||||
// but the scatter asks for relative to off = sect->rel[j+1].value - sect->addr.
|
// but the scatter asks for relative to off = sect->rel[j+1].value - sect->addr.
|
||||||
// adjust rp->add accordingly.
|
// adjust rp->add accordingly.
|
||||||
rp.Type = obj.R_PCREL
|
rp.Type = objabi.R_PCREL
|
||||||
|
|
||||||
rp.Add += int64(uint64(int64(rp.Off)+4) - (uint64(sect.rel[j+1].value) - sect.addr))
|
rp.Add += int64(uint64(int64(rp.Off)+4) - (uint64(sect.rel[j+1].value) - sect.addr))
|
||||||
|
|
||||||
|
|
@ -828,7 +828,7 @@ func ldmacho(ctxt *Link, f *bio.Reader, pkg string, length int64, pn string) {
|
||||||
}
|
}
|
||||||
|
|
||||||
rp.Siz = rel.length
|
rp.Siz = rel.length
|
||||||
rp.Type = 512 + (obj.RelocType(rel.type_) << 1) + obj.RelocType(rel.pcrel)
|
rp.Type = 512 + (objabi.RelocType(rel.type_) << 1) + objabi.RelocType(rel.pcrel)
|
||||||
rp.Off = int32(rel.addr)
|
rp.Off = int32(rel.addr)
|
||||||
|
|
||||||
// Handle X86_64_RELOC_SIGNED referencing a section (rel->extrn == 0).
|
// Handle X86_64_RELOC_SIGNED referencing a section (rel->extrn == 0).
|
||||||
|
|
|
||||||
|
|
@ -6,7 +6,7 @@ package ld
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"cmd/internal/bio"
|
"cmd/internal/bio"
|
||||||
"cmd/internal/obj"
|
"cmd/internal/objabi"
|
||||||
"cmd/internal/sys"
|
"cmd/internal/sys"
|
||||||
"debug/pe"
|
"debug/pe"
|
||||||
"errors"
|
"errors"
|
||||||
|
|
@ -127,7 +127,7 @@ func ldpe(ctxt *Link, input *bio.Reader, pkg string, length int64, pn string) {
|
||||||
|
|
||||||
func ldpeError(ctxt *Link, input *bio.Reader, pkg string, length int64, pn string) error {
|
func ldpeError(ctxt *Link, input *bio.Reader, pkg string, length int64, pn string) error {
|
||||||
if ctxt.Debugvlog != 0 {
|
if ctxt.Debugvlog != 0 {
|
||||||
ctxt.Logf("%5.2f ldpe %s\n", obj.Cputime(), pn)
|
ctxt.Logf("%5.2f ldpe %s\n", Cputime(), pn)
|
||||||
}
|
}
|
||||||
|
|
||||||
localSymVersion := ctxt.Syms.IncVersion()
|
localSymVersion := ctxt.Syms.IncVersion()
|
||||||
|
|
@ -173,16 +173,16 @@ func ldpeError(ctxt *Link, input *bio.Reader, pkg string, length int64, pn strin
|
||||||
|
|
||||||
switch sect.Characteristics & (IMAGE_SCN_CNT_UNINITIALIZED_DATA | IMAGE_SCN_CNT_INITIALIZED_DATA | IMAGE_SCN_MEM_READ | IMAGE_SCN_MEM_WRITE | IMAGE_SCN_CNT_CODE | IMAGE_SCN_MEM_EXECUTE) {
|
switch sect.Characteristics & (IMAGE_SCN_CNT_UNINITIALIZED_DATA | IMAGE_SCN_CNT_INITIALIZED_DATA | IMAGE_SCN_MEM_READ | IMAGE_SCN_MEM_WRITE | IMAGE_SCN_CNT_CODE | IMAGE_SCN_MEM_EXECUTE) {
|
||||||
case IMAGE_SCN_CNT_INITIALIZED_DATA | IMAGE_SCN_MEM_READ: //.rdata
|
case IMAGE_SCN_CNT_INITIALIZED_DATA | IMAGE_SCN_MEM_READ: //.rdata
|
||||||
s.Type = obj.SRODATA
|
s.Type = objabi.SRODATA
|
||||||
|
|
||||||
case IMAGE_SCN_CNT_UNINITIALIZED_DATA | IMAGE_SCN_MEM_READ | IMAGE_SCN_MEM_WRITE: //.bss
|
case IMAGE_SCN_CNT_UNINITIALIZED_DATA | IMAGE_SCN_MEM_READ | IMAGE_SCN_MEM_WRITE: //.bss
|
||||||
s.Type = obj.SNOPTRBSS
|
s.Type = objabi.SNOPTRBSS
|
||||||
|
|
||||||
case IMAGE_SCN_CNT_INITIALIZED_DATA | IMAGE_SCN_MEM_READ | IMAGE_SCN_MEM_WRITE: //.data
|
case IMAGE_SCN_CNT_INITIALIZED_DATA | IMAGE_SCN_MEM_READ | IMAGE_SCN_MEM_WRITE: //.data
|
||||||
s.Type = obj.SNOPTRDATA
|
s.Type = objabi.SNOPTRDATA
|
||||||
|
|
||||||
case IMAGE_SCN_CNT_CODE | IMAGE_SCN_MEM_EXECUTE | IMAGE_SCN_MEM_READ: //.text
|
case IMAGE_SCN_CNT_CODE | IMAGE_SCN_MEM_EXECUTE | IMAGE_SCN_MEM_READ: //.text
|
||||||
s.Type = obj.STEXT
|
s.Type = objabi.STEXT
|
||||||
|
|
||||||
default:
|
default:
|
||||||
return fmt.Errorf("unexpected flags %#06x for PE section %s", sect.Characteristics, sect.Name)
|
return fmt.Errorf("unexpected flags %#06x for PE section %s", sect.Characteristics, sect.Name)
|
||||||
|
|
@ -243,12 +243,12 @@ func ldpeError(ctxt *Link, input *bio.Reader, pkg string, length int64, pn strin
|
||||||
case IMAGE_REL_I386_REL32, IMAGE_REL_AMD64_REL32,
|
case IMAGE_REL_I386_REL32, IMAGE_REL_AMD64_REL32,
|
||||||
IMAGE_REL_AMD64_ADDR32, // R_X86_64_PC32
|
IMAGE_REL_AMD64_ADDR32, // R_X86_64_PC32
|
||||||
IMAGE_REL_AMD64_ADDR32NB:
|
IMAGE_REL_AMD64_ADDR32NB:
|
||||||
rp.Type = obj.R_PCREL
|
rp.Type = objabi.R_PCREL
|
||||||
|
|
||||||
rp.Add = int64(int32(Le32(sectdata[rsect][rp.Off:])))
|
rp.Add = int64(int32(Le32(sectdata[rsect][rp.Off:])))
|
||||||
|
|
||||||
case IMAGE_REL_I386_DIR32NB, IMAGE_REL_I386_DIR32:
|
case IMAGE_REL_I386_DIR32NB, IMAGE_REL_I386_DIR32:
|
||||||
rp.Type = obj.R_ADDR
|
rp.Type = objabi.R_ADDR
|
||||||
|
|
||||||
// load addend from image
|
// load addend from image
|
||||||
rp.Add = int64(int32(Le32(sectdata[rsect][rp.Off:])))
|
rp.Add = int64(int32(Le32(sectdata[rsect][rp.Off:])))
|
||||||
|
|
@ -256,7 +256,7 @@ func ldpeError(ctxt *Link, input *bio.Reader, pkg string, length int64, pn strin
|
||||||
case IMAGE_REL_AMD64_ADDR64: // R_X86_64_64
|
case IMAGE_REL_AMD64_ADDR64: // R_X86_64_64
|
||||||
rp.Siz = 8
|
rp.Siz = 8
|
||||||
|
|
||||||
rp.Type = obj.R_ADDR
|
rp.Type = objabi.R_ADDR
|
||||||
|
|
||||||
// load addend from image
|
// load addend from image
|
||||||
rp.Add = int64(Le64(sectdata[rsect][rp.Off:]))
|
rp.Add = int64(Le64(sectdata[rsect][rp.Off:]))
|
||||||
|
|
@ -313,11 +313,11 @@ func ldpeError(ctxt *Link, input *bio.Reader, pkg string, length int64, pn strin
|
||||||
}
|
}
|
||||||
|
|
||||||
if pesym.SectionNumber == 0 { // extern
|
if pesym.SectionNumber == 0 { // extern
|
||||||
if s.Type == obj.SDYNIMPORT {
|
if s.Type == objabi.SDYNIMPORT {
|
||||||
s.Plt = -2 // flag for dynimport in PE object files.
|
s.Plt = -2 // flag for dynimport in PE object files.
|
||||||
}
|
}
|
||||||
if s.Type == obj.SXREF && pesym.Value > 0 { // global data
|
if s.Type == objabi.SXREF && pesym.Value > 0 { // global data
|
||||||
s.Type = obj.SNOPTRDATA
|
s.Type = objabi.SNOPTRDATA
|
||||||
s.Size = int64(pesym.Value)
|
s.Size = int64(pesym.Value)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -345,11 +345,11 @@ func ldpeError(ctxt *Link, input *bio.Reader, pkg string, length int64, pn strin
|
||||||
sectsym := sectsyms[sect]
|
sectsym := sectsyms[sect]
|
||||||
s.Sub = sectsym.Sub
|
s.Sub = sectsym.Sub
|
||||||
sectsym.Sub = s
|
sectsym.Sub = s
|
||||||
s.Type = sectsym.Type | obj.SSUB
|
s.Type = sectsym.Type | objabi.SSUB
|
||||||
s.Value = int64(pesym.Value)
|
s.Value = int64(pesym.Value)
|
||||||
s.Size = 4
|
s.Size = 4
|
||||||
s.Outer = sectsym
|
s.Outer = sectsym
|
||||||
if sectsym.Type == obj.STEXT {
|
if sectsym.Type == objabi.STEXT {
|
||||||
if s.Attr.External() && !s.Attr.DuplicateOK() {
|
if s.Attr.External() && !s.Attr.DuplicateOK() {
|
||||||
Errorf(s, "%s: duplicate symbol definition", pn)
|
Errorf(s, "%s: duplicate symbol definition", pn)
|
||||||
}
|
}
|
||||||
|
|
@ -367,7 +367,7 @@ func ldpeError(ctxt *Link, input *bio.Reader, pkg string, length int64, pn strin
|
||||||
if s.Sub != nil {
|
if s.Sub != nil {
|
||||||
s.Sub = listsort(s.Sub)
|
s.Sub = listsort(s.Sub)
|
||||||
}
|
}
|
||||||
if s.Type == obj.STEXT {
|
if s.Type == objabi.STEXT {
|
||||||
if s.Attr.OnList() {
|
if s.Attr.OnList() {
|
||||||
log.Fatalf("symbol %s listed multiple times", s.Name)
|
log.Fatalf("symbol %s listed multiple times", s.Name)
|
||||||
}
|
}
|
||||||
|
|
@ -433,7 +433,7 @@ func readpesym(ctxt *Link, f *pe.File, sym *pe.COFFSymbol, sectsyms map[*pe.Sect
|
||||||
}
|
}
|
||||||
|
|
||||||
if s != nil && s.Type == 0 && (sym.StorageClass != IMAGE_SYM_CLASS_STATIC || sym.Value != 0) {
|
if s != nil && s.Type == 0 && (sym.StorageClass != IMAGE_SYM_CLASS_STATIC || sym.Value != 0) {
|
||||||
s.Type = obj.SXREF
|
s.Type = objabi.SXREF
|
||||||
}
|
}
|
||||||
if strings.HasPrefix(symname, "__imp_") {
|
if strings.HasPrefix(symname, "__imp_") {
|
||||||
s.Got = -2 // flag for __imp_
|
s.Got = -2 // flag for __imp_
|
||||||
|
|
|
||||||
|
|
@ -34,7 +34,7 @@ import (
|
||||||
"bufio"
|
"bufio"
|
||||||
"bytes"
|
"bytes"
|
||||||
"cmd/internal/bio"
|
"cmd/internal/bio"
|
||||||
"cmd/internal/obj"
|
"cmd/internal/objabi"
|
||||||
"cmd/internal/sys"
|
"cmd/internal/sys"
|
||||||
"crypto/sha1"
|
"crypto/sha1"
|
||||||
"debug/elf"
|
"debug/elf"
|
||||||
|
|
@ -196,7 +196,7 @@ var (
|
||||||
|
|
||||||
debug_s bool // backup old value of debug['s']
|
debug_s bool // backup old value of debug['s']
|
||||||
HEADR int32
|
HEADR int32
|
||||||
Headtype obj.HeadType
|
Headtype objabi.HeadType
|
||||||
|
|
||||||
nerrors int
|
nerrors int
|
||||||
liveness int64
|
liveness int64
|
||||||
|
|
@ -286,7 +286,7 @@ func libinit(ctxt *Link) {
|
||||||
suffix = "msan"
|
suffix = "msan"
|
||||||
}
|
}
|
||||||
|
|
||||||
Lflag(ctxt, filepath.Join(obj.GOROOT, "pkg", fmt.Sprintf("%s_%s%s%s", obj.GOOS, obj.GOARCH, suffixsep, suffix)))
|
Lflag(ctxt, filepath.Join(objabi.GOROOT, "pkg", fmt.Sprintf("%s_%s%s%s", objabi.GOOS, objabi.GOARCH, suffixsep, suffix)))
|
||||||
|
|
||||||
mayberemoveoutfile()
|
mayberemoveoutfile()
|
||||||
f, err := os.OpenFile(*flagOutfile, os.O_WRONLY|os.O_CREATE|os.O_TRUNC, 0775)
|
f, err := os.OpenFile(*flagOutfile, os.O_WRONLY|os.O_CREATE|os.O_TRUNC, 0775)
|
||||||
|
|
@ -300,9 +300,9 @@ func libinit(ctxt *Link) {
|
||||||
if *flagEntrySymbol == "" {
|
if *flagEntrySymbol == "" {
|
||||||
switch Buildmode {
|
switch Buildmode {
|
||||||
case BuildmodeCShared, BuildmodeCArchive:
|
case BuildmodeCShared, BuildmodeCArchive:
|
||||||
*flagEntrySymbol = fmt.Sprintf("_rt0_%s_%s_lib", obj.GOARCH, obj.GOOS)
|
*flagEntrySymbol = fmt.Sprintf("_rt0_%s_%s_lib", objabi.GOARCH, objabi.GOOS)
|
||||||
case BuildmodeExe, BuildmodePIE:
|
case BuildmodeExe, BuildmodePIE:
|
||||||
*flagEntrySymbol = fmt.Sprintf("_rt0_%s_%s", obj.GOARCH, obj.GOOS)
|
*flagEntrySymbol = fmt.Sprintf("_rt0_%s_%s", objabi.GOARCH, objabi.GOOS)
|
||||||
case BuildmodeShared, BuildmodePlugin:
|
case BuildmodeShared, BuildmodePlugin:
|
||||||
// No *flagEntrySymbol for -buildmode=shared and plugin
|
// No *flagEntrySymbol for -buildmode=shared and plugin
|
||||||
default:
|
default:
|
||||||
|
|
@ -411,7 +411,7 @@ func (ctxt *Link) loadlib() {
|
||||||
iscgo = iscgo || ctxt.Library[i].Pkg == "runtime/cgo"
|
iscgo = iscgo || ctxt.Library[i].Pkg == "runtime/cgo"
|
||||||
if ctxt.Library[i].Shlib == "" {
|
if ctxt.Library[i].Shlib == "" {
|
||||||
if ctxt.Debugvlog > 1 {
|
if ctxt.Debugvlog > 1 {
|
||||||
ctxt.Logf("%5.2f autolib: %s (from %s)\n", obj.Cputime(), ctxt.Library[i].File, ctxt.Library[i].Objref)
|
ctxt.Logf("%5.2f autolib: %s (from %s)\n", Cputime(), ctxt.Library[i].File, ctxt.Library[i].Objref)
|
||||||
}
|
}
|
||||||
objfile(ctxt, ctxt.Library[i])
|
objfile(ctxt, ctxt.Library[i])
|
||||||
}
|
}
|
||||||
|
|
@ -420,7 +420,7 @@ func (ctxt *Link) loadlib() {
|
||||||
for i = 0; i < len(ctxt.Library); i++ {
|
for i = 0; i < len(ctxt.Library); i++ {
|
||||||
if ctxt.Library[i].Shlib != "" {
|
if ctxt.Library[i].Shlib != "" {
|
||||||
if ctxt.Debugvlog > 1 {
|
if ctxt.Debugvlog > 1 {
|
||||||
ctxt.Logf("%5.2f autolib: %s (from %s)\n", obj.Cputime(), ctxt.Library[i].Shlib, ctxt.Library[i].Objref)
|
ctxt.Logf("%5.2f autolib: %s (from %s)\n", Cputime(), ctxt.Library[i].Shlib, ctxt.Library[i].Objref)
|
||||||
}
|
}
|
||||||
ldshlibsyms(ctxt, ctxt.Library[i].Shlib)
|
ldshlibsyms(ctxt, ctxt.Library[i].Shlib)
|
||||||
}
|
}
|
||||||
|
|
@ -430,17 +430,17 @@ func (ctxt *Link) loadlib() {
|
||||||
determineLinkMode(ctxt)
|
determineLinkMode(ctxt)
|
||||||
|
|
||||||
// Recalculate pe parameters now that we have Linkmode set.
|
// Recalculate pe parameters now that we have Linkmode set.
|
||||||
if Headtype == obj.Hwindows {
|
if Headtype == objabi.Hwindows {
|
||||||
Peinit(ctxt)
|
Peinit(ctxt)
|
||||||
}
|
}
|
||||||
|
|
||||||
if Headtype == obj.Hdarwin && Linkmode == LinkExternal {
|
if Headtype == objabi.Hdarwin && Linkmode == LinkExternal {
|
||||||
*FlagTextAddr = 0
|
*FlagTextAddr = 0
|
||||||
}
|
}
|
||||||
|
|
||||||
if Linkmode == LinkExternal && SysArch.Family == sys.PPC64 {
|
if Linkmode == LinkExternal && SysArch.Family == sys.PPC64 {
|
||||||
toc := ctxt.Syms.Lookup(".TOC.", 0)
|
toc := ctxt.Syms.Lookup(".TOC.", 0)
|
||||||
toc.Type = obj.SDYNIMPORT
|
toc.Type = objabi.SDYNIMPORT
|
||||||
}
|
}
|
||||||
|
|
||||||
if Linkmode == LinkExternal && !iscgo {
|
if Linkmode == LinkExternal && !iscgo {
|
||||||
|
|
@ -466,13 +466,13 @@ func (ctxt *Link) loadlib() {
|
||||||
// Drop all the cgo_import_static declarations.
|
// Drop all the cgo_import_static declarations.
|
||||||
// Turns out we won't be needing them.
|
// Turns out we won't be needing them.
|
||||||
for _, s := range ctxt.Syms.Allsym {
|
for _, s := range ctxt.Syms.Allsym {
|
||||||
if s.Type == obj.SHOSTOBJ {
|
if s.Type == objabi.SHOSTOBJ {
|
||||||
// If a symbol was marked both
|
// If a symbol was marked both
|
||||||
// cgo_import_static and cgo_import_dynamic,
|
// cgo_import_static and cgo_import_dynamic,
|
||||||
// then we want to make it cgo_import_dynamic
|
// then we want to make it cgo_import_dynamic
|
||||||
// now.
|
// now.
|
||||||
if s.Extname != "" && s.Dynimplib != "" && !s.Attr.CgoExport() {
|
if s.Extname != "" && s.Dynimplib != "" && !s.Attr.CgoExport() {
|
||||||
s.Type = obj.SDYNIMPORT
|
s.Type = objabi.SDYNIMPORT
|
||||||
} else {
|
} else {
|
||||||
s.Type = 0
|
s.Type = 0
|
||||||
}
|
}
|
||||||
|
|
@ -485,9 +485,9 @@ func (ctxt *Link) loadlib() {
|
||||||
// runtime.tlsg is used for external linking on platforms that do not define
|
// runtime.tlsg is used for external linking on platforms that do not define
|
||||||
// a variable to hold g in assembly (currently only intel).
|
// a variable to hold g in assembly (currently only intel).
|
||||||
if tlsg.Type == 0 {
|
if tlsg.Type == 0 {
|
||||||
tlsg.Type = obj.STLSBSS
|
tlsg.Type = objabi.STLSBSS
|
||||||
tlsg.Size = int64(SysArch.PtrSize)
|
tlsg.Size = int64(SysArch.PtrSize)
|
||||||
} else if tlsg.Type != obj.SDYNIMPORT {
|
} else if tlsg.Type != objabi.SDYNIMPORT {
|
||||||
Errorf(nil, "runtime declared tlsg variable %v", tlsg.Type)
|
Errorf(nil, "runtime declared tlsg variable %v", tlsg.Type)
|
||||||
}
|
}
|
||||||
tlsg.Attr |= AttrReachable
|
tlsg.Attr |= AttrReachable
|
||||||
|
|
@ -500,7 +500,7 @@ func (ctxt *Link) loadlib() {
|
||||||
} else {
|
} else {
|
||||||
moduledata = ctxt.Syms.Lookup("runtime.firstmoduledata", 0)
|
moduledata = ctxt.Syms.Lookup("runtime.firstmoduledata", 0)
|
||||||
}
|
}
|
||||||
if moduledata.Type != 0 && moduledata.Type != obj.SDYNIMPORT {
|
if moduledata.Type != 0 && moduledata.Type != objabi.SDYNIMPORT {
|
||||||
// If the module (toolchain-speak for "executable or shared
|
// If the module (toolchain-speak for "executable or shared
|
||||||
// library") we are linking contains the runtime package, it
|
// library") we are linking contains the runtime package, it
|
||||||
// will define the runtime.firstmoduledata symbol and we
|
// will define the runtime.firstmoduledata symbol and we
|
||||||
|
|
@ -512,14 +512,14 @@ func (ctxt *Link) loadlib() {
|
||||||
// recording the value of GOARM.
|
// recording the value of GOARM.
|
||||||
if SysArch.Family == sys.ARM {
|
if SysArch.Family == sys.ARM {
|
||||||
s := ctxt.Syms.Lookup("runtime.goarm", 0)
|
s := ctxt.Syms.Lookup("runtime.goarm", 0)
|
||||||
s.Type = obj.SRODATA
|
s.Type = objabi.SRODATA
|
||||||
s.Size = 0
|
s.Size = 0
|
||||||
Adduint8(ctxt, s, uint8(obj.GOARM))
|
Adduint8(ctxt, s, uint8(objabi.GOARM))
|
||||||
}
|
}
|
||||||
|
|
||||||
if obj.Framepointer_enabled(obj.GOOS, obj.GOARCH) {
|
if objabi.Framepointer_enabled(objabi.GOOS, objabi.GOARCH) {
|
||||||
s := ctxt.Syms.Lookup("runtime.framepointer_enabled", 0)
|
s := ctxt.Syms.Lookup("runtime.framepointer_enabled", 0)
|
||||||
s.Type = obj.SRODATA
|
s.Type = objabi.SRODATA
|
||||||
s.Size = 0
|
s.Size = 0
|
||||||
Adduint8(ctxt, s, 1)
|
Adduint8(ctxt, s, 1)
|
||||||
}
|
}
|
||||||
|
|
@ -531,7 +531,7 @@ func (ctxt *Link) loadlib() {
|
||||||
}
|
}
|
||||||
// In all cases way we mark the moduledata as noptrdata to hide it from
|
// In all cases way we mark the moduledata as noptrdata to hide it from
|
||||||
// the GC.
|
// the GC.
|
||||||
moduledata.Type = obj.SNOPTRDATA
|
moduledata.Type = objabi.SNOPTRDATA
|
||||||
moduledata.Attr |= AttrReachable
|
moduledata.Attr |= AttrReachable
|
||||||
ctxt.Moduledata = moduledata
|
ctxt.Moduledata = moduledata
|
||||||
|
|
||||||
|
|
@ -559,7 +559,7 @@ func (ctxt *Link) loadlib() {
|
||||||
any := false
|
any := false
|
||||||
for _, s := range ctxt.Syms.Allsym {
|
for _, s := range ctxt.Syms.Allsym {
|
||||||
for _, r := range s.R {
|
for _, r := range s.R {
|
||||||
if r.Sym != nil && r.Sym.Type&obj.SMASK == obj.SXREF && r.Sym.Name != ".got" {
|
if r.Sym != nil && r.Sym.Type&objabi.SMASK == objabi.SXREF && r.Sym.Name != ".got" {
|
||||||
any = true
|
any = true
|
||||||
break
|
break
|
||||||
}
|
}
|
||||||
|
|
@ -572,7 +572,7 @@ func (ctxt *Link) loadlib() {
|
||||||
if *flagLibGCC != "none" {
|
if *flagLibGCC != "none" {
|
||||||
hostArchive(ctxt, *flagLibGCC)
|
hostArchive(ctxt, *flagLibGCC)
|
||||||
}
|
}
|
||||||
if Headtype == obj.Hwindows {
|
if Headtype == objabi.Hwindows {
|
||||||
if p := ctxt.findLibPath("libmingwex.a"); p != "none" {
|
if p := ctxt.findLibPath("libmingwex.a"); p != "none" {
|
||||||
hostArchive(ctxt, p)
|
hostArchive(ctxt, p)
|
||||||
}
|
}
|
||||||
|
|
@ -607,7 +607,7 @@ func (ctxt *Link) loadlib() {
|
||||||
// Also leave it enabled on Solaris which doesn't support
|
// Also leave it enabled on Solaris which doesn't support
|
||||||
// statically linked binaries.
|
// statically linked binaries.
|
||||||
if Buildmode == BuildmodeExe {
|
if Buildmode == BuildmodeExe {
|
||||||
if havedynamic == 0 && Headtype != obj.Hdarwin && Headtype != obj.Hsolaris {
|
if havedynamic == 0 && Headtype != objabi.Hdarwin && Headtype != objabi.Hsolaris {
|
||||||
*FlagD = true
|
*FlagD = true
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
@ -625,7 +625,7 @@ func (ctxt *Link) loadlib() {
|
||||||
if SysArch == sys.Arch386 {
|
if SysArch == sys.Arch386 {
|
||||||
if (Buildmode == BuildmodeCArchive && Iself) || Buildmode == BuildmodeCShared || Buildmode == BuildmodePIE || ctxt.DynlinkingGo() {
|
if (Buildmode == BuildmodeCArchive && Iself) || Buildmode == BuildmodeCShared || Buildmode == BuildmodePIE || ctxt.DynlinkingGo() {
|
||||||
got := ctxt.Syms.Lookup("_GLOBAL_OFFSET_TABLE_", 0)
|
got := ctxt.Syms.Lookup("_GLOBAL_OFFSET_TABLE_", 0)
|
||||||
got.Type = obj.SDYNIMPORT
|
got.Type = objabi.SDYNIMPORT
|
||||||
got.Attr |= AttrReachable
|
got.Attr |= AttrReachable
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
@ -663,7 +663,7 @@ func (ctxt *Link) loadlib() {
|
||||||
// pcln table entries for these any more so remove them from Textp.
|
// pcln table entries for these any more so remove them from Textp.
|
||||||
textp := make([]*Symbol, 0, len(ctxt.Textp))
|
textp := make([]*Symbol, 0, len(ctxt.Textp))
|
||||||
for _, s := range ctxt.Textp {
|
for _, s := range ctxt.Textp {
|
||||||
if s.Type != obj.SDYNIMPORT {
|
if s.Type != objabi.SDYNIMPORT {
|
||||||
textp = append(textp, s)
|
textp = append(textp, s)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
@ -755,7 +755,7 @@ func objfile(ctxt *Link, lib *Library) {
|
||||||
pkg := pathtoprefix(lib.Pkg)
|
pkg := pathtoprefix(lib.Pkg)
|
||||||
|
|
||||||
if ctxt.Debugvlog > 1 {
|
if ctxt.Debugvlog > 1 {
|
||||||
ctxt.Logf("%5.2f ldobj: %s (%s)\n", obj.Cputime(), lib.File, pkg)
|
ctxt.Logf("%5.2f ldobj: %s (%s)\n", Cputime(), lib.File, pkg)
|
||||||
}
|
}
|
||||||
f, err := bio.Open(lib.File)
|
f, err := bio.Open(lib.File)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
|
|
@ -866,7 +866,7 @@ func ldhostobj(ld func(*Link, *bio.Reader, string, int64, string), f *bio.Reader
|
||||||
// force external linking for any libraries that link in code that
|
// force external linking for any libraries that link in code that
|
||||||
// uses errno. This can be removed if the Go linker ever supports
|
// uses errno. This can be removed if the Go linker ever supports
|
||||||
// these relocation types.
|
// these relocation types.
|
||||||
if Headtype == obj.Hdragonfly {
|
if Headtype == objabi.Hdragonfly {
|
||||||
if pkg == "net" || pkg == "os/user" {
|
if pkg == "net" || pkg == "os/user" {
|
||||||
isinternal = false
|
isinternal = false
|
||||||
}
|
}
|
||||||
|
|
@ -1037,7 +1037,7 @@ func (l *Link) hostlink() {
|
||||||
|
|
||||||
if !*FlagS && !debug_s {
|
if !*FlagS && !debug_s {
|
||||||
argv = append(argv, "-gdwarf-2")
|
argv = append(argv, "-gdwarf-2")
|
||||||
} else if Headtype == obj.Hdarwin {
|
} else if Headtype == objabi.Hdarwin {
|
||||||
// Recent versions of macOS print
|
// Recent versions of macOS print
|
||||||
// ld: warning: option -s is obsolete and being ignored
|
// ld: warning: option -s is obsolete and being ignored
|
||||||
// so do not pass any arguments.
|
// so do not pass any arguments.
|
||||||
|
|
@ -1046,16 +1046,16 @@ func (l *Link) hostlink() {
|
||||||
}
|
}
|
||||||
|
|
||||||
switch Headtype {
|
switch Headtype {
|
||||||
case obj.Hdarwin:
|
case objabi.Hdarwin:
|
||||||
argv = append(argv, "-Wl,-headerpad,1144")
|
argv = append(argv, "-Wl,-headerpad,1144")
|
||||||
if l.DynlinkingGo() {
|
if l.DynlinkingGo() {
|
||||||
argv = append(argv, "-Wl,-flat_namespace")
|
argv = append(argv, "-Wl,-flat_namespace")
|
||||||
} else {
|
} else {
|
||||||
argv = append(argv, "-Wl,-no_pie")
|
argv = append(argv, "-Wl,-no_pie")
|
||||||
}
|
}
|
||||||
case obj.Hopenbsd:
|
case objabi.Hopenbsd:
|
||||||
argv = append(argv, "-Wl,-nopie")
|
argv = append(argv, "-Wl,-nopie")
|
||||||
case obj.Hwindows:
|
case objabi.Hwindows:
|
||||||
if windowsgui {
|
if windowsgui {
|
||||||
argv = append(argv, "-mwindows")
|
argv = append(argv, "-mwindows")
|
||||||
} else {
|
} else {
|
||||||
|
|
@ -1065,7 +1065,7 @@ func (l *Link) hostlink() {
|
||||||
|
|
||||||
switch Buildmode {
|
switch Buildmode {
|
||||||
case BuildmodeExe:
|
case BuildmodeExe:
|
||||||
if Headtype == obj.Hdarwin {
|
if Headtype == objabi.Hdarwin {
|
||||||
argv = append(argv, "-Wl,-pagezero_size,4000000")
|
argv = append(argv, "-Wl,-pagezero_size,4000000")
|
||||||
}
|
}
|
||||||
case BuildmodePIE:
|
case BuildmodePIE:
|
||||||
|
|
@ -1074,7 +1074,7 @@ func (l *Link) hostlink() {
|
||||||
}
|
}
|
||||||
argv = append(argv, "-pie")
|
argv = append(argv, "-pie")
|
||||||
case BuildmodeCShared:
|
case BuildmodeCShared:
|
||||||
if Headtype == obj.Hdarwin {
|
if Headtype == objabi.Hdarwin {
|
||||||
argv = append(argv, "-dynamiclib", "-Wl,-read_only_relocs,suppress")
|
argv = append(argv, "-dynamiclib", "-Wl,-read_only_relocs,suppress")
|
||||||
} else {
|
} else {
|
||||||
// ELF.
|
// ELF.
|
||||||
|
|
@ -1092,7 +1092,7 @@ func (l *Link) hostlink() {
|
||||||
}
|
}
|
||||||
argv = append(argv, "-shared")
|
argv = append(argv, "-shared")
|
||||||
case BuildmodePlugin:
|
case BuildmodePlugin:
|
||||||
if Headtype == obj.Hdarwin {
|
if Headtype == objabi.Hdarwin {
|
||||||
argv = append(argv, "-dynamiclib")
|
argv = append(argv, "-dynamiclib")
|
||||||
} else {
|
} else {
|
||||||
if UseRelro() {
|
if UseRelro() {
|
||||||
|
|
@ -1147,7 +1147,7 @@ func (l *Link) hostlink() {
|
||||||
// only want to do this when producing a Windows output file
|
// only want to do this when producing a Windows output file
|
||||||
// on a Windows host.
|
// on a Windows host.
|
||||||
outopt := *flagOutfile
|
outopt := *flagOutfile
|
||||||
if obj.GOOS == "windows" && runtime.GOOS == "windows" && filepath.Ext(outopt) == "" {
|
if objabi.GOOS == "windows" && runtime.GOOS == "windows" && filepath.Ext(outopt) == "" {
|
||||||
outopt += "."
|
outopt += "."
|
||||||
}
|
}
|
||||||
argv = append(argv, "-o")
|
argv = append(argv, "-o")
|
||||||
|
|
@ -1243,7 +1243,7 @@ func (l *Link) hostlink() {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if Headtype == obj.Hwindows {
|
if Headtype == objabi.Hwindows {
|
||||||
// libmingw32 and libmingwex have some inter-dependencies,
|
// libmingw32 and libmingwex have some inter-dependencies,
|
||||||
// so must use linker groups.
|
// so must use linker groups.
|
||||||
argv = append(argv, "-Wl,--start-group", "-lmingwex", "-lmingw32", "-Wl,--end-group")
|
argv = append(argv, "-Wl,--start-group", "-lmingwex", "-lmingw32", "-Wl,--end-group")
|
||||||
|
|
@ -1251,7 +1251,7 @@ func (l *Link) hostlink() {
|
||||||
}
|
}
|
||||||
|
|
||||||
if l.Debugvlog != 0 {
|
if l.Debugvlog != 0 {
|
||||||
l.Logf("%5.2f host link:", obj.Cputime())
|
l.Logf("%5.2f host link:", Cputime())
|
||||||
for _, v := range argv {
|
for _, v := range argv {
|
||||||
l.Logf(" %q", v)
|
l.Logf(" %q", v)
|
||||||
}
|
}
|
||||||
|
|
@ -1264,7 +1264,7 @@ func (l *Link) hostlink() {
|
||||||
l.Logf("%s", out)
|
l.Logf("%s", out)
|
||||||
}
|
}
|
||||||
|
|
||||||
if !*FlagS && !*FlagW && !debug_s && Headtype == obj.Hdarwin {
|
if !*FlagS && !*FlagW && !debug_s && Headtype == objabi.Hdarwin {
|
||||||
// Skip combining dwarf on arm.
|
// Skip combining dwarf on arm.
|
||||||
if !SysArch.InFamily(sys.ARM, sys.ARM64) {
|
if !SysArch.InFamily(sys.ARM, sys.ARM64) {
|
||||||
dsym := filepath.Join(*flagTmpdir, "go.dwarf")
|
dsym := filepath.Join(*flagTmpdir, "go.dwarf")
|
||||||
|
|
@ -1359,7 +1359,7 @@ func ldobj(ctxt *Link, f *bio.Reader, lib *Library, length int64, pn string, fil
|
||||||
}
|
}
|
||||||
|
|
||||||
// First, check that the basic GOOS, GOARCH, and Version match.
|
// First, check that the basic GOOS, GOARCH, and Version match.
|
||||||
t := fmt.Sprintf("%s %s %s ", obj.GOOS, obj.GOARCH, obj.Version)
|
t := fmt.Sprintf("%s %s %s ", objabi.GOOS, objabi.GOARCH, objabi.Version)
|
||||||
|
|
||||||
line = strings.TrimRight(line, "\n")
|
line = strings.TrimRight(line, "\n")
|
||||||
if !strings.HasPrefix(line[10:]+" ", t) && !*flagF {
|
if !strings.HasPrefix(line[10:]+" ", t) && !*flagF {
|
||||||
|
|
@ -1489,7 +1489,7 @@ func ldshlibsyms(ctxt *Link, shlib string) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if ctxt.Debugvlog > 1 {
|
if ctxt.Debugvlog > 1 {
|
||||||
ctxt.Logf("%5.2f ldshlibsyms: found library with name %s at %s\n", obj.Cputime(), shlib, libpath)
|
ctxt.Logf("%5.2f ldshlibsyms: found library with name %s at %s\n", Cputime(), shlib, libpath)
|
||||||
}
|
}
|
||||||
|
|
||||||
f, err := elf.Open(libpath)
|
f, err := elf.Open(libpath)
|
||||||
|
|
@ -1526,10 +1526,10 @@ func ldshlibsyms(ctxt *Link, shlib string) {
|
||||||
// libraries, any non-dynimport symbols we find that duplicate symbols
|
// libraries, any non-dynimport symbols we find that duplicate symbols
|
||||||
// already loaded should be ignored (the symbols from the .a files
|
// already loaded should be ignored (the symbols from the .a files
|
||||||
// "win").
|
// "win").
|
||||||
if lsym.Type != 0 && lsym.Type != obj.SDYNIMPORT {
|
if lsym.Type != 0 && lsym.Type != objabi.SDYNIMPORT {
|
||||||
continue
|
continue
|
||||||
}
|
}
|
||||||
lsym.Type = obj.SDYNIMPORT
|
lsym.Type = objabi.SDYNIMPORT
|
||||||
lsym.ElfType = elf.ST_TYPE(elfsym.Info)
|
lsym.ElfType = elf.ST_TYPE(elfsym.Info)
|
||||||
lsym.Size = int64(elfsym.Size)
|
lsym.Size = int64(elfsym.Size)
|
||||||
if elfsym.Section != elf.SHN_UNDEF {
|
if elfsym.Section != elf.SHN_UNDEF {
|
||||||
|
|
@ -1667,7 +1667,7 @@ func (ctxt *Link) dostkcheck() {
|
||||||
// of non-splitting functions.
|
// of non-splitting functions.
|
||||||
ch.up = nil
|
ch.up = nil
|
||||||
|
|
||||||
ch.limit = obj.StackLimit - callsize(ctxt)
|
ch.limit = objabi.StackLimit - callsize(ctxt)
|
||||||
|
|
||||||
// Check every function, but do the nosplit functions in a first pass,
|
// Check every function, but do the nosplit functions in a first pass,
|
||||||
// to make the printed failure chains as short as possible.
|
// to make the printed failure chains as short as possible.
|
||||||
|
|
@ -1699,7 +1699,7 @@ func stkcheck(ctxt *Link, up *chain, depth int) int {
|
||||||
|
|
||||||
// Don't duplicate work: only need to consider each
|
// Don't duplicate work: only need to consider each
|
||||||
// function at top of safe zone once.
|
// function at top of safe zone once.
|
||||||
top := limit == obj.StackLimit-callsize(ctxt)
|
top := limit == objabi.StackLimit-callsize(ctxt)
|
||||||
if top {
|
if top {
|
||||||
if s.Attr.StackCheck() {
|
if s.Attr.StackCheck() {
|
||||||
return 0
|
return 0
|
||||||
|
|
@ -1718,7 +1718,7 @@ func stkcheck(ctxt *Link, up *chain, depth int) int {
|
||||||
// should never be called directly.
|
// should never be called directly.
|
||||||
// onlyctxt.Diagnose the direct caller.
|
// onlyctxt.Diagnose the direct caller.
|
||||||
// TODO(mwhudson): actually think about this.
|
// TODO(mwhudson): actually think about this.
|
||||||
if depth == 1 && s.Type != obj.SXREF && !ctxt.DynlinkingGo() &&
|
if depth == 1 && s.Type != objabi.SXREF && !ctxt.DynlinkingGo() &&
|
||||||
Buildmode != BuildmodeCArchive && Buildmode != BuildmodePIE && Buildmode != BuildmodeCShared && Buildmode != BuildmodePlugin {
|
Buildmode != BuildmodeCArchive && Buildmode != BuildmodePIE && Buildmode != BuildmodeCShared && Buildmode != BuildmodePlugin {
|
||||||
|
|
||||||
Errorf(s, "call to external function")
|
Errorf(s, "call to external function")
|
||||||
|
|
@ -1755,7 +1755,7 @@ func stkcheck(ctxt *Link, up *chain, depth int) int {
|
||||||
if s.FuncInfo != nil {
|
if s.FuncInfo != nil {
|
||||||
locals = s.FuncInfo.Locals
|
locals = s.FuncInfo.Locals
|
||||||
}
|
}
|
||||||
limit = int(obj.StackLimit+locals) + int(ctxt.FixedFrameSize())
|
limit = int(objabi.StackLimit+locals) + int(ctxt.FixedFrameSize())
|
||||||
}
|
}
|
||||||
|
|
||||||
// Walk through sp adjustments in function, consuming relocs.
|
// Walk through sp adjustments in function, consuming relocs.
|
||||||
|
|
@ -1779,7 +1779,7 @@ func stkcheck(ctxt *Link, up *chain, depth int) int {
|
||||||
r = &s.R[ri]
|
r = &s.R[ri]
|
||||||
switch r.Type {
|
switch r.Type {
|
||||||
// Direct call.
|
// Direct call.
|
||||||
case obj.R_CALL, obj.R_CALLARM, obj.R_CALLARM64, obj.R_CALLPOWER, obj.R_CALLMIPS:
|
case objabi.R_CALL, objabi.R_CALLARM, objabi.R_CALLARM64, objabi.R_CALLPOWER, objabi.R_CALLMIPS:
|
||||||
ch.limit = int(int32(limit) - pcsp.value - int32(callsize(ctxt)))
|
ch.limit = int(int32(limit) - pcsp.value - int32(callsize(ctxt)))
|
||||||
ch.sym = r.Sym
|
ch.sym = r.Sym
|
||||||
if stkcheck(ctxt, &ch, depth+1) < 0 {
|
if stkcheck(ctxt, &ch, depth+1) < 0 {
|
||||||
|
|
@ -1790,7 +1790,7 @@ func stkcheck(ctxt *Link, up *chain, depth int) int {
|
||||||
// so we have to make sure it can call morestack.
|
// so we have to make sure it can call morestack.
|
||||||
// Arrange the data structures to report both calls, so that
|
// Arrange the data structures to report both calls, so that
|
||||||
// if there is an error, stkprint shows all the steps involved.
|
// if there is an error, stkprint shows all the steps involved.
|
||||||
case obj.R_CALLIND:
|
case objabi.R_CALLIND:
|
||||||
ch.limit = int(int32(limit) - pcsp.value - int32(callsize(ctxt)))
|
ch.limit = int(int32(limit) - pcsp.value - int32(callsize(ctxt)))
|
||||||
|
|
||||||
ch.sym = nil
|
ch.sym = nil
|
||||||
|
|
@ -1875,12 +1875,12 @@ func Cput(c uint8) {
|
||||||
|
|
||||||
func usage() {
|
func usage() {
|
||||||
fmt.Fprintf(os.Stderr, "usage: link [options] main.o\n")
|
fmt.Fprintf(os.Stderr, "usage: link [options] main.o\n")
|
||||||
obj.Flagprint(2)
|
objabi.Flagprint(2)
|
||||||
Exit(2)
|
Exit(2)
|
||||||
}
|
}
|
||||||
|
|
||||||
func doversion() {
|
func doversion() {
|
||||||
Exitf("version %s", obj.Version)
|
Exitf("version %s", objabi.Version)
|
||||||
}
|
}
|
||||||
|
|
||||||
type SymbolType int8
|
type SymbolType int8
|
||||||
|
|
@ -1901,7 +1901,7 @@ func genasmsym(ctxt *Link, put func(*Link, *Symbol, string, SymbolType, int64, *
|
||||||
// These symbols won't show up in the first loop below because we
|
// These symbols won't show up in the first loop below because we
|
||||||
// skip STEXT symbols. Normal STEXT symbols are emitted by walking textp.
|
// skip STEXT symbols. Normal STEXT symbols are emitted by walking textp.
|
||||||
s := ctxt.Syms.Lookup("runtime.text", 0)
|
s := ctxt.Syms.Lookup("runtime.text", 0)
|
||||||
if s.Type == obj.STEXT {
|
if s.Type == objabi.STEXT {
|
||||||
put(ctxt, s, s.Name, TextSym, s.Value, nil)
|
put(ctxt, s, s.Name, TextSym, s.Value, nil)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -1920,14 +1920,14 @@ func genasmsym(ctxt *Link, put func(*Link, *Symbol, string, SymbolType, int64, *
|
||||||
if s == nil {
|
if s == nil {
|
||||||
break
|
break
|
||||||
}
|
}
|
||||||
if s.Type == obj.STEXT {
|
if s.Type == objabi.STEXT {
|
||||||
put(ctxt, s, s.Name, TextSym, s.Value, nil)
|
put(ctxt, s, s.Name, TextSym, s.Value, nil)
|
||||||
}
|
}
|
||||||
n++
|
n++
|
||||||
}
|
}
|
||||||
|
|
||||||
s = ctxt.Syms.Lookup("runtime.etext", 0)
|
s = ctxt.Syms.Lookup("runtime.etext", 0)
|
||||||
if s.Type == obj.STEXT {
|
if s.Type == objabi.STEXT {
|
||||||
put(ctxt, s, s.Name, TextSym, s.Value, nil)
|
put(ctxt, s, s.Name, TextSym, s.Value, nil)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -1938,36 +1938,36 @@ func genasmsym(ctxt *Link, put func(*Link, *Symbol, string, SymbolType, int64, *
|
||||||
if (s.Name == "" || s.Name[0] == '.') && s.Version == 0 && s.Name != ".rathole" && s.Name != ".TOC." {
|
if (s.Name == "" || s.Name[0] == '.') && s.Version == 0 && s.Name != ".rathole" && s.Name != ".TOC." {
|
||||||
continue
|
continue
|
||||||
}
|
}
|
||||||
switch s.Type & obj.SMASK {
|
switch s.Type & objabi.SMASK {
|
||||||
case obj.SCONST,
|
case objabi.SCONST,
|
||||||
obj.SRODATA,
|
objabi.SRODATA,
|
||||||
obj.SSYMTAB,
|
objabi.SSYMTAB,
|
||||||
obj.SPCLNTAB,
|
objabi.SPCLNTAB,
|
||||||
obj.SINITARR,
|
objabi.SINITARR,
|
||||||
obj.SDATA,
|
objabi.SDATA,
|
||||||
obj.SNOPTRDATA,
|
objabi.SNOPTRDATA,
|
||||||
obj.SELFROSECT,
|
objabi.SELFROSECT,
|
||||||
obj.SMACHOGOT,
|
objabi.SMACHOGOT,
|
||||||
obj.STYPE,
|
objabi.STYPE,
|
||||||
obj.SSTRING,
|
objabi.SSTRING,
|
||||||
obj.SGOSTRING,
|
objabi.SGOSTRING,
|
||||||
obj.SGOFUNC,
|
objabi.SGOFUNC,
|
||||||
obj.SGCBITS,
|
objabi.SGCBITS,
|
||||||
obj.STYPERELRO,
|
objabi.STYPERELRO,
|
||||||
obj.SSTRINGRELRO,
|
objabi.SSTRINGRELRO,
|
||||||
obj.SGOSTRINGRELRO,
|
objabi.SGOSTRINGRELRO,
|
||||||
obj.SGOFUNCRELRO,
|
objabi.SGOFUNCRELRO,
|
||||||
obj.SGCBITSRELRO,
|
objabi.SGCBITSRELRO,
|
||||||
obj.SRODATARELRO,
|
objabi.SRODATARELRO,
|
||||||
obj.STYPELINK,
|
objabi.STYPELINK,
|
||||||
obj.SITABLINK,
|
objabi.SITABLINK,
|
||||||
obj.SWINDOWS:
|
objabi.SWINDOWS:
|
||||||
if !s.Attr.Reachable() {
|
if !s.Attr.Reachable() {
|
||||||
continue
|
continue
|
||||||
}
|
}
|
||||||
put(ctxt, s, s.Name, DataSym, Symaddr(s), s.Gotype)
|
put(ctxt, s, s.Name, DataSym, Symaddr(s), s.Gotype)
|
||||||
|
|
||||||
case obj.SBSS, obj.SNOPTRBSS:
|
case objabi.SBSS, objabi.SNOPTRBSS:
|
||||||
if !s.Attr.Reachable() {
|
if !s.Attr.Reachable() {
|
||||||
continue
|
continue
|
||||||
}
|
}
|
||||||
|
|
@ -1976,21 +1976,21 @@ func genasmsym(ctxt *Link, put func(*Link, *Symbol, string, SymbolType, int64, *
|
||||||
}
|
}
|
||||||
put(ctxt, s, s.Name, BSSSym, Symaddr(s), s.Gotype)
|
put(ctxt, s, s.Name, BSSSym, Symaddr(s), s.Gotype)
|
||||||
|
|
||||||
case obj.SFILE:
|
case objabi.SFILE:
|
||||||
put(ctxt, nil, s.Name, FileSym, s.Value, nil)
|
put(ctxt, nil, s.Name, FileSym, s.Value, nil)
|
||||||
|
|
||||||
case obj.SHOSTOBJ:
|
case objabi.SHOSTOBJ:
|
||||||
if Headtype == obj.Hwindows || Iself {
|
if Headtype == objabi.Hwindows || Iself {
|
||||||
put(ctxt, s, s.Name, UndefinedSym, s.Value, nil)
|
put(ctxt, s, s.Name, UndefinedSym, s.Value, nil)
|
||||||
}
|
}
|
||||||
|
|
||||||
case obj.SDYNIMPORT:
|
case objabi.SDYNIMPORT:
|
||||||
if !s.Attr.Reachable() {
|
if !s.Attr.Reachable() {
|
||||||
continue
|
continue
|
||||||
}
|
}
|
||||||
put(ctxt, s, s.Extname, UndefinedSym, 0, nil)
|
put(ctxt, s, s.Extname, UndefinedSym, 0, nil)
|
||||||
|
|
||||||
case obj.STLSBSS:
|
case objabi.STLSBSS:
|
||||||
if Linkmode == LinkExternal {
|
if Linkmode == LinkExternal {
|
||||||
put(ctxt, s, s.Name, TLSSym, Symaddr(s), s.Gotype)
|
put(ctxt, s, s.Name, TLSSym, Symaddr(s), s.Gotype)
|
||||||
}
|
}
|
||||||
|
|
@ -2014,12 +2014,12 @@ func genasmsym(ctxt *Link, put func(*Link, *Symbol, string, SymbolType, int64, *
|
||||||
for _, a := range s.FuncInfo.Autom {
|
for _, a := range s.FuncInfo.Autom {
|
||||||
// Emit a or p according to actual offset, even if label is wrong.
|
// Emit a or p according to actual offset, even if label is wrong.
|
||||||
// This avoids negative offsets, which cannot be encoded.
|
// This avoids negative offsets, which cannot be encoded.
|
||||||
if a.Name != obj.A_AUTO && a.Name != obj.A_PARAM {
|
if a.Name != objabi.A_AUTO && a.Name != objabi.A_PARAM {
|
||||||
continue
|
continue
|
||||||
}
|
}
|
||||||
|
|
||||||
// compute offset relative to FP
|
// compute offset relative to FP
|
||||||
if a.Name == obj.A_PARAM {
|
if a.Name == objabi.A_PARAM {
|
||||||
off = a.Aoffset
|
off = a.Aoffset
|
||||||
} else {
|
} else {
|
||||||
off = a.Aoffset - int32(SysArch.PtrSize)
|
off = a.Aoffset - int32(SysArch.PtrSize)
|
||||||
|
|
@ -2042,7 +2042,7 @@ func genasmsym(ctxt *Link, put func(*Link, *Symbol, string, SymbolType, int64, *
|
||||||
}
|
}
|
||||||
|
|
||||||
if ctxt.Debugvlog != 0 || *flagN {
|
if ctxt.Debugvlog != 0 || *flagN {
|
||||||
ctxt.Logf("%5.2f symsize = %d\n", obj.Cputime(), uint32(Symsize))
|
ctxt.Logf("%5.2f symsize = %d\n", Cputime(), uint32(Symsize))
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -2053,7 +2053,7 @@ func Symaddr(s *Symbol) int64 {
|
||||||
return s.Value
|
return s.Value
|
||||||
}
|
}
|
||||||
|
|
||||||
func (ctxt *Link) xdefine(p string, t obj.SymKind, v int64) {
|
func (ctxt *Link) xdefine(p string, t objabi.SymKind, v int64) {
|
||||||
s := ctxt.Syms.Lookup(p, 0)
|
s := ctxt.Syms.Lookup(p, 0)
|
||||||
s.Type = t
|
s.Type = t
|
||||||
s.Value = v
|
s.Value = v
|
||||||
|
|
@ -2082,7 +2082,7 @@ func Entryvalue(ctxt *Link) int64 {
|
||||||
if s.Type == 0 {
|
if s.Type == 0 {
|
||||||
return *FlagTextAddr
|
return *FlagTextAddr
|
||||||
}
|
}
|
||||||
if s.Type != obj.STEXT {
|
if s.Type != objabi.STEXT {
|
||||||
Errorf(s, "entry not text")
|
Errorf(s, "entry not text")
|
||||||
}
|
}
|
||||||
return s.Value
|
return s.Value
|
||||||
|
|
@ -2096,10 +2096,10 @@ func undefsym(ctxt *Link, s *Symbol) {
|
||||||
if r.Sym == nil { // happens for some external ARM relocs
|
if r.Sym == nil { // happens for some external ARM relocs
|
||||||
continue
|
continue
|
||||||
}
|
}
|
||||||
if r.Sym.Type == obj.Sxxx || r.Sym.Type == obj.SXREF {
|
if r.Sym.Type == objabi.Sxxx || r.Sym.Type == objabi.SXREF {
|
||||||
Errorf(s, "undefined: %q", r.Sym.Name)
|
Errorf(s, "undefined: %q", r.Sym.Name)
|
||||||
}
|
}
|
||||||
if !r.Sym.Attr.Reachable() && r.Type != obj.R_WEAKADDROFF {
|
if !r.Sym.Attr.Reachable() && r.Type != objabi.R_WEAKADDROFF {
|
||||||
Errorf(s, "relocation target %q", r.Sym.Name)
|
Errorf(s, "relocation target %q", r.Sym.Name)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
@ -2130,7 +2130,7 @@ func (ctxt *Link) callgraph() {
|
||||||
if r.Sym == nil {
|
if r.Sym == nil {
|
||||||
continue
|
continue
|
||||||
}
|
}
|
||||||
if (r.Type == obj.R_CALL || r.Type == obj.R_CALLARM || r.Type == obj.R_CALLPOWER || r.Type == obj.R_CALLMIPS) && r.Sym.Type == obj.STEXT {
|
if (r.Type == objabi.R_CALL || r.Type == objabi.R_CALLARM || r.Type == objabi.R_CALLPOWER || r.Type == objabi.R_CALLMIPS) && r.Sym.Type == objabi.STEXT {
|
||||||
ctxt.Logf("%s calls %s\n", s.Name, r.Sym.Name)
|
ctxt.Logf("%s calls %s\n", s.Name, r.Sym.Name)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -32,7 +32,7 @@ package ld
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"bufio"
|
"bufio"
|
||||||
"cmd/internal/obj"
|
"cmd/internal/objabi"
|
||||||
"cmd/internal/sys"
|
"cmd/internal/sys"
|
||||||
"debug/elf"
|
"debug/elf"
|
||||||
"fmt"
|
"fmt"
|
||||||
|
|
@ -42,7 +42,7 @@ import (
|
||||||
type Symbol struct {
|
type Symbol struct {
|
||||||
Name string
|
Name string
|
||||||
Extname string
|
Extname string
|
||||||
Type obj.SymKind
|
Type objabi.SymKind
|
||||||
Version int16
|
Version int16
|
||||||
Attr Attribute
|
Attr Attribute
|
||||||
Localentry uint8
|
Localentry uint8
|
||||||
|
|
@ -150,7 +150,7 @@ type Reloc struct {
|
||||||
Siz uint8 // number of bytes to rewrite, 1, 2, or 4
|
Siz uint8 // number of bytes to rewrite, 1, 2, or 4
|
||||||
Done uint8 // set to 1 when relocation is complete
|
Done uint8 // set to 1 when relocation is complete
|
||||||
Variant RelocVariant // variation on Type
|
Variant RelocVariant // variation on Type
|
||||||
Type obj.RelocType // the relocation type
|
Type objabi.RelocType // the relocation type
|
||||||
Add int64 // addend
|
Add int64 // addend
|
||||||
Xadd int64 // addend passed to external linker
|
Xadd int64 // addend passed to external linker
|
||||||
Sym *Symbol // symbol the relocation addresses
|
Sym *Symbol // symbol the relocation addresses
|
||||||
|
|
|
||||||
|
|
@ -5,7 +5,7 @@
|
||||||
package ld
|
package ld
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"cmd/internal/obj"
|
"cmd/internal/objabi"
|
||||||
"cmd/internal/sys"
|
"cmd/internal/sys"
|
||||||
"sort"
|
"sort"
|
||||||
"strings"
|
"strings"
|
||||||
|
|
@ -302,31 +302,31 @@ func (ctxt *Link) domacho() {
|
||||||
// empirically, string table must begin with " \x00".
|
// empirically, string table must begin with " \x00".
|
||||||
s := ctxt.Syms.Lookup(".machosymstr", 0)
|
s := ctxt.Syms.Lookup(".machosymstr", 0)
|
||||||
|
|
||||||
s.Type = obj.SMACHOSYMSTR
|
s.Type = objabi.SMACHOSYMSTR
|
||||||
s.Attr |= AttrReachable
|
s.Attr |= AttrReachable
|
||||||
Adduint8(ctxt, s, ' ')
|
Adduint8(ctxt, s, ' ')
|
||||||
Adduint8(ctxt, s, '\x00')
|
Adduint8(ctxt, s, '\x00')
|
||||||
|
|
||||||
s = ctxt.Syms.Lookup(".machosymtab", 0)
|
s = ctxt.Syms.Lookup(".machosymtab", 0)
|
||||||
s.Type = obj.SMACHOSYMTAB
|
s.Type = objabi.SMACHOSYMTAB
|
||||||
s.Attr |= AttrReachable
|
s.Attr |= AttrReachable
|
||||||
|
|
||||||
if Linkmode != LinkExternal {
|
if Linkmode != LinkExternal {
|
||||||
s := ctxt.Syms.Lookup(".plt", 0) // will be __symbol_stub
|
s := ctxt.Syms.Lookup(".plt", 0) // will be __symbol_stub
|
||||||
s.Type = obj.SMACHOPLT
|
s.Type = objabi.SMACHOPLT
|
||||||
s.Attr |= AttrReachable
|
s.Attr |= AttrReachable
|
||||||
|
|
||||||
s = ctxt.Syms.Lookup(".got", 0) // will be __nl_symbol_ptr
|
s = ctxt.Syms.Lookup(".got", 0) // will be __nl_symbol_ptr
|
||||||
s.Type = obj.SMACHOGOT
|
s.Type = objabi.SMACHOGOT
|
||||||
s.Attr |= AttrReachable
|
s.Attr |= AttrReachable
|
||||||
s.Align = 4
|
s.Align = 4
|
||||||
|
|
||||||
s = ctxt.Syms.Lookup(".linkedit.plt", 0) // indirect table for .plt
|
s = ctxt.Syms.Lookup(".linkedit.plt", 0) // indirect table for .plt
|
||||||
s.Type = obj.SMACHOINDIRECTPLT
|
s.Type = objabi.SMACHOINDIRECTPLT
|
||||||
s.Attr |= AttrReachable
|
s.Attr |= AttrReachable
|
||||||
|
|
||||||
s = ctxt.Syms.Lookup(".linkedit.got", 0) // indirect table for .got
|
s = ctxt.Syms.Lookup(".linkedit.got", 0) // indirect table for .got
|
||||||
s.Type = obj.SMACHOINDIRECTGOT
|
s.Type = objabi.SMACHOINDIRECTGOT
|
||||||
s.Attr |= AttrReachable
|
s.Attr |= AttrReachable
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
@ -603,7 +603,7 @@ func Asmbmacho(ctxt *Link) {
|
||||||
}
|
}
|
||||||
|
|
||||||
func symkind(s *Symbol) int {
|
func symkind(s *Symbol) int {
|
||||||
if s.Type == obj.SDYNIMPORT {
|
if s.Type == objabi.SDYNIMPORT {
|
||||||
return SymKindUndef
|
return SymKindUndef
|
||||||
}
|
}
|
||||||
if s.Attr.CgoExport() {
|
if s.Attr.CgoExport() {
|
||||||
|
|
@ -659,7 +659,7 @@ func (x machoscmp) Less(i, j int) bool {
|
||||||
func machogenasmsym(ctxt *Link) {
|
func machogenasmsym(ctxt *Link) {
|
||||||
genasmsym(ctxt, addsym)
|
genasmsym(ctxt, addsym)
|
||||||
for _, s := range ctxt.Syms.Allsym {
|
for _, s := range ctxt.Syms.Allsym {
|
||||||
if s.Type == obj.SDYNIMPORT || s.Type == obj.SHOSTOBJ {
|
if s.Type == objabi.SDYNIMPORT || s.Type == objabi.SHOSTOBJ {
|
||||||
if s.Attr.Reachable() {
|
if s.Attr.Reachable() {
|
||||||
addsym(ctxt, s, "", DataSym, 0, nil)
|
addsym(ctxt, s, "", DataSym, 0, nil)
|
||||||
}
|
}
|
||||||
|
|
@ -704,7 +704,7 @@ func machoShouldExport(ctxt *Link, s *Symbol) bool {
|
||||||
if strings.HasPrefix(s.Name, "go.link.pkghash") {
|
if strings.HasPrefix(s.Name, "go.link.pkghash") {
|
||||||
return true
|
return true
|
||||||
}
|
}
|
||||||
return s.Type >= obj.SELFSECT // only writable sections
|
return s.Type >= objabi.SELFSECT // only writable sections
|
||||||
}
|
}
|
||||||
|
|
||||||
func machosymtab(ctxt *Link) {
|
func machosymtab(ctxt *Link) {
|
||||||
|
|
@ -732,7 +732,7 @@ func machosymtab(ctxt *Link) {
|
||||||
// replace "·" as ".", because DTrace cannot handle it.
|
// replace "·" as ".", because DTrace cannot handle it.
|
||||||
Addstring(symstr, strings.Replace(s.Extname, "·", ".", -1))
|
Addstring(symstr, strings.Replace(s.Extname, "·", ".", -1))
|
||||||
|
|
||||||
if s.Type == obj.SDYNIMPORT || s.Type == obj.SHOSTOBJ {
|
if s.Type == objabi.SDYNIMPORT || s.Type == objabi.SHOSTOBJ {
|
||||||
Adduint8(ctxt, symtab, 0x01) // type N_EXT, external symbol
|
Adduint8(ctxt, symtab, 0x01) // type N_EXT, external symbol
|
||||||
Adduint8(ctxt, symtab, 0) // no section
|
Adduint8(ctxt, symtab, 0) // no section
|
||||||
Adduint16(ctxt, symtab, 0) // desc
|
Adduint16(ctxt, symtab, 0) // desc
|
||||||
|
|
|
||||||
|
|
@ -32,7 +32,7 @@ package ld
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"bufio"
|
"bufio"
|
||||||
"cmd/internal/obj"
|
"cmd/internal/objabi"
|
||||||
"cmd/internal/sys"
|
"cmd/internal/sys"
|
||||||
"flag"
|
"flag"
|
||||||
"log"
|
"log"
|
||||||
|
|
@ -114,21 +114,21 @@ func Main() {
|
||||||
}
|
}
|
||||||
|
|
||||||
// TODO(matloob): define these above and then check flag values here
|
// TODO(matloob): define these above and then check flag values here
|
||||||
if SysArch.Family == sys.AMD64 && obj.GOOS == "plan9" {
|
if SysArch.Family == sys.AMD64 && objabi.GOOS == "plan9" {
|
||||||
flag.BoolVar(&Flag8, "8", false, "use 64-bit addresses in symbol table")
|
flag.BoolVar(&Flag8, "8", false, "use 64-bit addresses in symbol table")
|
||||||
}
|
}
|
||||||
obj.Flagfn1("B", "add an ELF NT_GNU_BUILD_ID `note` when using ELF", addbuildinfo)
|
objabi.Flagfn1("B", "add an ELF NT_GNU_BUILD_ID `note` when using ELF", addbuildinfo)
|
||||||
obj.Flagfn1("L", "add specified `directory` to library path", func(a string) { Lflag(ctxt, a) })
|
objabi.Flagfn1("L", "add specified `directory` to library path", func(a string) { Lflag(ctxt, a) })
|
||||||
obj.Flagfn0("V", "print version and exit", doversion)
|
objabi.Flagfn0("V", "print version and exit", doversion)
|
||||||
obj.Flagfn1("X", "add string value `definition` of the form importpath.name=value", func(s string) { addstrdata1(ctxt, s) })
|
objabi.Flagfn1("X", "add string value `definition` of the form importpath.name=value", func(s string) { addstrdata1(ctxt, s) })
|
||||||
obj.Flagcount("v", "print link trace", &ctxt.Debugvlog)
|
objabi.Flagcount("v", "print link trace", &ctxt.Debugvlog)
|
||||||
|
|
||||||
obj.Flagparse(usage)
|
objabi.Flagparse(usage)
|
||||||
|
|
||||||
switch *flagHeadtype {
|
switch *flagHeadtype {
|
||||||
case "":
|
case "":
|
||||||
case "windowsgui":
|
case "windowsgui":
|
||||||
Headtype = obj.Hwindows
|
Headtype = objabi.Hwindows
|
||||||
windowsgui = true
|
windowsgui = true
|
||||||
default:
|
default:
|
||||||
if err := Headtype.Set(*flagHeadtype); err != nil {
|
if err := Headtype.Set(*flagHeadtype); err != nil {
|
||||||
|
|
@ -148,7 +148,7 @@ func Main() {
|
||||||
|
|
||||||
if *flagOutfile == "" {
|
if *flagOutfile == "" {
|
||||||
*flagOutfile = "a.out"
|
*flagOutfile = "a.out"
|
||||||
if Headtype == obj.Hwindows {
|
if Headtype == objabi.Hwindows {
|
||||||
*flagOutfile += ".exe"
|
*flagOutfile += ".exe"
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
@ -157,8 +157,8 @@ func Main() {
|
||||||
|
|
||||||
libinit(ctxt) // creates outfile
|
libinit(ctxt) // creates outfile
|
||||||
|
|
||||||
if Headtype == obj.Hunknown {
|
if Headtype == objabi.Hunknown {
|
||||||
Headtype.Set(obj.GOOS)
|
Headtype.Set(objabi.GOOS)
|
||||||
}
|
}
|
||||||
|
|
||||||
ctxt.computeTLSOffset()
|
ctxt.computeTLSOffset()
|
||||||
|
|
@ -200,11 +200,11 @@ func Main() {
|
||||||
ctxt.callgraph()
|
ctxt.callgraph()
|
||||||
|
|
||||||
ctxt.doelf()
|
ctxt.doelf()
|
||||||
if Headtype == obj.Hdarwin {
|
if Headtype == objabi.Hdarwin {
|
||||||
ctxt.domacho()
|
ctxt.domacho()
|
||||||
}
|
}
|
||||||
ctxt.dostkcheck()
|
ctxt.dostkcheck()
|
||||||
if Headtype == obj.Hwindows {
|
if Headtype == objabi.Hwindows {
|
||||||
ctxt.dope()
|
ctxt.dope()
|
||||||
}
|
}
|
||||||
ctxt.addexport()
|
ctxt.addexport()
|
||||||
|
|
@ -223,7 +223,7 @@ func Main() {
|
||||||
ctxt.hostlink()
|
ctxt.hostlink()
|
||||||
ctxt.archive()
|
ctxt.archive()
|
||||||
if ctxt.Debugvlog != 0 {
|
if ctxt.Debugvlog != 0 {
|
||||||
ctxt.Logf("%5.2f cpu time\n", obj.Cputime())
|
ctxt.Logf("%5.2f cpu time\n", Cputime())
|
||||||
ctxt.Logf("%d symbols\n", len(ctxt.Syms.Allsym))
|
ctxt.Logf("%d symbols\n", len(ctxt.Syms.Allsym))
|
||||||
ctxt.Logf("%d liveness data\n", liveness)
|
ctxt.Logf("%d liveness data\n", liveness)
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -5,119 +5,13 @@
|
||||||
package ld
|
package ld
|
||||||
|
|
||||||
// Reading of Go object files.
|
// Reading of Go object files.
|
||||||
//
|
|
||||||
// Originally, Go object files were Plan 9 object files, but no longer.
|
|
||||||
// Now they are more like standard object files, in that each symbol is defined
|
|
||||||
// by an associated memory image (bytes) and a list of relocations to apply
|
|
||||||
// during linking. We do not (yet?) use a standard file format, however.
|
|
||||||
// For now, the format is chosen to be as simple as possible to read and write.
|
|
||||||
// It may change for reasons of efficiency, or we may even switch to a
|
|
||||||
// standard file format if there are compelling benefits to doing so.
|
|
||||||
// See golang.org/s/go13linker for more background.
|
|
||||||
//
|
|
||||||
// The file format is:
|
|
||||||
//
|
|
||||||
// - magic header: "\x00\x00go19ld"
|
|
||||||
// - byte 1 - version number
|
|
||||||
// - sequence of strings giving dependencies (imported packages)
|
|
||||||
// - empty string (marks end of sequence)
|
|
||||||
// - sequence of symbol references used by the defined symbols
|
|
||||||
// - byte 0xff (marks end of sequence)
|
|
||||||
// - sequence of integer lengths:
|
|
||||||
// - total data length
|
|
||||||
// - total number of relocations
|
|
||||||
// - total number of pcdata
|
|
||||||
// - total number of automatics
|
|
||||||
// - total number of funcdata
|
|
||||||
// - total number of files
|
|
||||||
// - data, the content of the defined symbols
|
|
||||||
// - sequence of defined symbols
|
|
||||||
// - byte 0xff (marks end of sequence)
|
|
||||||
// - magic footer: "\xff\xffgo19ld"
|
|
||||||
//
|
|
||||||
// All integers are stored in a zigzag varint format.
|
|
||||||
// See golang.org/s/go12symtab for a definition.
|
|
||||||
//
|
|
||||||
// Data blocks and strings are both stored as an integer
|
|
||||||
// followed by that many bytes.
|
|
||||||
//
|
|
||||||
// A symbol reference is a string name followed by a version.
|
|
||||||
//
|
|
||||||
// A symbol points to other symbols using an index into the symbol
|
|
||||||
// reference sequence. Index 0 corresponds to a nil Object* pointer.
|
|
||||||
// In the symbol layout described below "symref index" stands for this
|
|
||||||
// index.
|
|
||||||
//
|
|
||||||
// Each symbol is laid out as the following fields (taken from Object*):
|
|
||||||
//
|
|
||||||
// - byte 0xfe (sanity check for synchronization)
|
|
||||||
// - type [int]
|
|
||||||
// - name & version [symref index]
|
|
||||||
// - flags [int]
|
|
||||||
// 1<<0 dupok
|
|
||||||
// 1<<1 local
|
|
||||||
// 1<<2 add to typelink table
|
|
||||||
// - size [int]
|
|
||||||
// - gotype [symref index]
|
|
||||||
// - p [data block]
|
|
||||||
// - nr [int]
|
|
||||||
// - r [nr relocations, sorted by off]
|
|
||||||
//
|
|
||||||
// If type == STEXT, there are a few more fields:
|
|
||||||
//
|
|
||||||
// - args [int]
|
|
||||||
// - locals [int]
|
|
||||||
// - nosplit [int]
|
|
||||||
// - flags [int]
|
|
||||||
// 1<<0 leaf
|
|
||||||
// 1<<1 C function
|
|
||||||
// 1<<2 function may call reflect.Type.Method
|
|
||||||
// - nlocal [int]
|
|
||||||
// - local [nlocal automatics]
|
|
||||||
// - pcln [pcln table]
|
|
||||||
//
|
|
||||||
// Each relocation has the encoding:
|
|
||||||
//
|
|
||||||
// - off [int]
|
|
||||||
// - siz [int]
|
|
||||||
// - type [int]
|
|
||||||
// - add [int]
|
|
||||||
// - sym [symref index]
|
|
||||||
//
|
|
||||||
// Each local has the encoding:
|
|
||||||
//
|
|
||||||
// - asym [symref index]
|
|
||||||
// - offset [int]
|
|
||||||
// - type [int]
|
|
||||||
// - gotype [symref index]
|
|
||||||
//
|
|
||||||
// The pcln table has the encoding:
|
|
||||||
//
|
|
||||||
// - pcsp [data block]
|
|
||||||
// - pcfile [data block]
|
|
||||||
// - pcline [data block]
|
|
||||||
// - pcinline [data block]
|
|
||||||
// - npcdata [int]
|
|
||||||
// - pcdata [npcdata data blocks]
|
|
||||||
// - nfuncdata [int]
|
|
||||||
// - funcdata [nfuncdata symref index]
|
|
||||||
// - funcdatasym [nfuncdata ints]
|
|
||||||
// - nfile [int]
|
|
||||||
// - file [nfile symref index]
|
|
||||||
// - ninlinedcall [int]
|
|
||||||
// - inlinedcall [ninlinedcall int symref int symref]
|
|
||||||
//
|
|
||||||
// The file layout and meaning of type integers are architecture-independent.
|
|
||||||
//
|
|
||||||
// TODO(rsc): The file format is good for a first pass but needs work.
|
|
||||||
// - There are SymID in the object file that should really just be strings.
|
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"bufio"
|
"bufio"
|
||||||
"bytes"
|
"bytes"
|
||||||
"cmd/internal/bio"
|
"cmd/internal/bio"
|
||||||
"cmd/internal/dwarf"
|
"cmd/internal/dwarf"
|
||||||
"cmd/internal/obj"
|
"cmd/internal/objabi"
|
||||||
"crypto/sha1"
|
"crypto/sha1"
|
||||||
"encoding/base64"
|
"encoding/base64"
|
||||||
"io"
|
"io"
|
||||||
|
|
@ -264,7 +158,7 @@ func (r *objReader) readSym() {
|
||||||
if c, err := r.rd.ReadByte(); c != symPrefix || err != nil {
|
if c, err := r.rd.ReadByte(); c != symPrefix || err != nil {
|
||||||
log.Fatalln("readSym out of sync")
|
log.Fatalln("readSym out of sync")
|
||||||
}
|
}
|
||||||
t := obj.SymKind(r.readInt())
|
t := objabi.SymKind(r.readInt())
|
||||||
s := r.readSymIndex()
|
s := r.readSymIndex()
|
||||||
flags := r.readInt()
|
flags := r.readInt()
|
||||||
dupok := flags&1 != 0
|
dupok := flags&1 != 0
|
||||||
|
|
@ -278,8 +172,8 @@ func (r *objReader) readSym() {
|
||||||
isdup := false
|
isdup := false
|
||||||
|
|
||||||
var dup *Symbol
|
var dup *Symbol
|
||||||
if s.Type != 0 && s.Type != obj.SXREF {
|
if s.Type != 0 && s.Type != objabi.SXREF {
|
||||||
if (t == obj.SDATA || t == obj.SBSS || t == obj.SNOPTRBSS) && len(data) == 0 && nreloc == 0 {
|
if (t == objabi.SDATA || t == objabi.SBSS || t == objabi.SNOPTRBSS) && len(data) == 0 && nreloc == 0 {
|
||||||
if s.Size < int64(size) {
|
if s.Size < int64(size) {
|
||||||
s.Size = int64(size)
|
s.Size = int64(size)
|
||||||
}
|
}
|
||||||
|
|
@ -289,10 +183,10 @@ func (r *objReader) readSym() {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
if (s.Type == obj.SDATA || s.Type == obj.SBSS || s.Type == obj.SNOPTRBSS) && len(s.P) == 0 && len(s.R) == 0 {
|
if (s.Type == objabi.SDATA || s.Type == objabi.SBSS || s.Type == objabi.SNOPTRBSS) && len(s.P) == 0 && len(s.R) == 0 {
|
||||||
goto overwrite
|
goto overwrite
|
||||||
}
|
}
|
||||||
if s.Type != obj.SBSS && s.Type != obj.SNOPTRBSS && !dupok && !s.Attr.DuplicateOK() {
|
if s.Type != objabi.SBSS && s.Type != objabi.SNOPTRBSS && !dupok && !s.Attr.DuplicateOK() {
|
||||||
log.Fatalf("duplicate symbol %s (types %d and %d) in %s and %s", s.Name, s.Type, t, s.File, r.pn)
|
log.Fatalf("duplicate symbol %s (types %d and %d) in %s and %s", s.Name, s.Type, t, s.File, r.pn)
|
||||||
}
|
}
|
||||||
if len(s.P) > 0 {
|
if len(s.P) > 0 {
|
||||||
|
|
@ -307,13 +201,13 @@ overwrite:
|
||||||
if dupok {
|
if dupok {
|
||||||
s.Attr |= AttrDuplicateOK
|
s.Attr |= AttrDuplicateOK
|
||||||
}
|
}
|
||||||
if t == obj.SXREF {
|
if t == objabi.SXREF {
|
||||||
log.Fatalf("bad sxref")
|
log.Fatalf("bad sxref")
|
||||||
}
|
}
|
||||||
if t == 0 {
|
if t == 0 {
|
||||||
log.Fatalf("missing type for %s in %s", s.Name, r.pn)
|
log.Fatalf("missing type for %s in %s", s.Name, r.pn)
|
||||||
}
|
}
|
||||||
if t == obj.SBSS && (s.Type == obj.SRODATA || s.Type == obj.SNOPTRBSS) {
|
if t == objabi.SBSS && (s.Type == objabi.SRODATA || s.Type == objabi.SNOPTRBSS) {
|
||||||
t = s.Type
|
t = s.Type
|
||||||
}
|
}
|
||||||
s.Type = t
|
s.Type = t
|
||||||
|
|
@ -339,14 +233,14 @@ overwrite:
|
||||||
s.R[i] = Reloc{
|
s.R[i] = Reloc{
|
||||||
Off: r.readInt32(),
|
Off: r.readInt32(),
|
||||||
Siz: r.readUint8(),
|
Siz: r.readUint8(),
|
||||||
Type: obj.RelocType(r.readInt32()),
|
Type: objabi.RelocType(r.readInt32()),
|
||||||
Add: r.readInt64(),
|
Add: r.readInt64(),
|
||||||
Sym: r.readSymIndex(),
|
Sym: r.readSymIndex(),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if s.Type == obj.STEXT {
|
if s.Type == objabi.STEXT {
|
||||||
s.FuncInfo = new(FuncInfo)
|
s.FuncInfo = new(FuncInfo)
|
||||||
pc := s.FuncInfo
|
pc := s.FuncInfo
|
||||||
|
|
||||||
|
|
@ -432,7 +326,7 @@ overwrite:
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if s.Type == obj.SDWARFINFO {
|
if s.Type == objabi.SDWARFINFO {
|
||||||
r.patchDWARFName(s)
|
r.patchDWARFName(s)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
@ -495,7 +389,7 @@ func (r *objReader) readRef() {
|
||||||
if err != nil {
|
if err != nil {
|
||||||
log.Panicf("failed to parse $-symbol %s: %v", s.Name, err)
|
log.Panicf("failed to parse $-symbol %s: %v", s.Name, err)
|
||||||
}
|
}
|
||||||
s.Type = obj.SRODATA
|
s.Type = objabi.SRODATA
|
||||||
s.Attr |= AttrLocal
|
s.Attr |= AttrLocal
|
||||||
switch s.Name[:5] {
|
switch s.Name[:5] {
|
||||||
case "$f32.":
|
case "$f32.":
|
||||||
|
|
|
||||||
|
|
@ -5,7 +5,7 @@
|
||||||
package ld
|
package ld
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"cmd/internal/obj"
|
"cmd/internal/objabi"
|
||||||
"cmd/internal/src"
|
"cmd/internal/src"
|
||||||
"log"
|
"log"
|
||||||
"os"
|
"os"
|
||||||
|
|
@ -111,10 +111,10 @@ func ftabaddstring(ctxt *Link, ftab *Symbol, s string) int32 {
|
||||||
|
|
||||||
// numberfile assigns a file number to the file if it hasn't been assigned already.
|
// numberfile assigns a file number to the file if it hasn't been assigned already.
|
||||||
func numberfile(ctxt *Link, file *Symbol) {
|
func numberfile(ctxt *Link, file *Symbol) {
|
||||||
if file.Type != obj.SFILEPATH {
|
if file.Type != objabi.SFILEPATH {
|
||||||
ctxt.Filesyms = append(ctxt.Filesyms, file)
|
ctxt.Filesyms = append(ctxt.Filesyms, file)
|
||||||
file.Value = int64(len(ctxt.Filesyms))
|
file.Value = int64(len(ctxt.Filesyms))
|
||||||
file.Type = obj.SFILEPATH
|
file.Type = objabi.SFILEPATH
|
||||||
path := file.Name[len(src.FileSymPrefix):]
|
path := file.Name[len(src.FileSymPrefix):]
|
||||||
file.Name = expandGoroot(path)
|
file.Name = expandGoroot(path)
|
||||||
}
|
}
|
||||||
|
|
@ -175,12 +175,12 @@ func container(s *Symbol) int {
|
||||||
if s == nil {
|
if s == nil {
|
||||||
return 0
|
return 0
|
||||||
}
|
}
|
||||||
if Buildmode == BuildmodePlugin && Headtype == obj.Hdarwin && onlycsymbol(s) {
|
if Buildmode == BuildmodePlugin && Headtype == objabi.Hdarwin && onlycsymbol(s) {
|
||||||
return 1
|
return 1
|
||||||
}
|
}
|
||||||
// We want to generate func table entries only for the "lowest level" symbols,
|
// We want to generate func table entries only for the "lowest level" symbols,
|
||||||
// not containers of subsymbols.
|
// not containers of subsymbols.
|
||||||
if s.Type&obj.SCONTAINER != 0 {
|
if s.Type&objabi.SCONTAINER != 0 {
|
||||||
return 1
|
return 1
|
||||||
}
|
}
|
||||||
return 0
|
return 0
|
||||||
|
|
@ -201,7 +201,7 @@ var pclntabLastFunc *Symbol
|
||||||
func (ctxt *Link) pclntab() {
|
func (ctxt *Link) pclntab() {
|
||||||
funcdataBytes := int64(0)
|
funcdataBytes := int64(0)
|
||||||
ftab := ctxt.Syms.Lookup("runtime.pclntab", 0)
|
ftab := ctxt.Syms.Lookup("runtime.pclntab", 0)
|
||||||
ftab.Type = obj.SPCLNTAB
|
ftab.Type = objabi.SPCLNTAB
|
||||||
ftab.Attr |= AttrReachable
|
ftab.Attr |= AttrReachable
|
||||||
|
|
||||||
// See golang.org/s/go12symtab for the format. Briefly:
|
// See golang.org/s/go12symtab for the format. Briefly:
|
||||||
|
|
@ -215,7 +215,7 @@ func (ctxt *Link) pclntab() {
|
||||||
// Find container symbols, mark them with SCONTAINER
|
// Find container symbols, mark them with SCONTAINER
|
||||||
for _, s := range ctxt.Textp {
|
for _, s := range ctxt.Textp {
|
||||||
if s.Outer != nil {
|
if s.Outer != nil {
|
||||||
s.Outer.Type |= obj.SCONTAINER
|
s.Outer.Type |= objabi.SCONTAINER
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -260,17 +260,17 @@ func (ctxt *Link) pclntab() {
|
||||||
}
|
}
|
||||||
|
|
||||||
if len(pcln.InlTree) > 0 {
|
if len(pcln.InlTree) > 0 {
|
||||||
if len(pcln.Pcdata) <= obj.PCDATA_InlTreeIndex {
|
if len(pcln.Pcdata) <= objabi.PCDATA_InlTreeIndex {
|
||||||
// Create inlining pcdata table.
|
// Create inlining pcdata table.
|
||||||
pcdata := make([]Pcdata, obj.PCDATA_InlTreeIndex+1)
|
pcdata := make([]Pcdata, objabi.PCDATA_InlTreeIndex+1)
|
||||||
copy(pcdata, pcln.Pcdata)
|
copy(pcdata, pcln.Pcdata)
|
||||||
pcln.Pcdata = pcdata
|
pcln.Pcdata = pcdata
|
||||||
}
|
}
|
||||||
|
|
||||||
if len(pcln.Funcdataoff) <= obj.FUNCDATA_InlTree {
|
if len(pcln.Funcdataoff) <= objabi.FUNCDATA_InlTree {
|
||||||
// Create inline tree funcdata.
|
// Create inline tree funcdata.
|
||||||
funcdata := make([]*Symbol, obj.FUNCDATA_InlTree+1)
|
funcdata := make([]*Symbol, objabi.FUNCDATA_InlTree+1)
|
||||||
funcdataoff := make([]int64, obj.FUNCDATA_InlTree+1)
|
funcdataoff := make([]int64, objabi.FUNCDATA_InlTree+1)
|
||||||
copy(funcdata, pcln.Funcdata)
|
copy(funcdata, pcln.Funcdata)
|
||||||
copy(funcdataoff, pcln.Funcdataoff)
|
copy(funcdataoff, pcln.Funcdataoff)
|
||||||
pcln.Funcdata = funcdata
|
pcln.Funcdata = funcdata
|
||||||
|
|
@ -334,7 +334,7 @@ func (ctxt *Link) pclntab() {
|
||||||
|
|
||||||
if len(pcln.InlTree) > 0 {
|
if len(pcln.InlTree) > 0 {
|
||||||
inlTreeSym := ctxt.Syms.Lookup("inltree."+s.Name, 0)
|
inlTreeSym := ctxt.Syms.Lookup("inltree."+s.Name, 0)
|
||||||
inlTreeSym.Type = obj.SRODATA
|
inlTreeSym.Type = objabi.SRODATA
|
||||||
inlTreeSym.Attr |= AttrReachable | AttrDuplicateOK
|
inlTreeSym.Attr |= AttrReachable | AttrDuplicateOK
|
||||||
|
|
||||||
for i, call := range pcln.InlTree {
|
for i, call := range pcln.InlTree {
|
||||||
|
|
@ -352,8 +352,8 @@ func (ctxt *Link) pclntab() {
|
||||||
setuint32(ctxt, inlTreeSym, int64(i*16+12), uint32(nameoff))
|
setuint32(ctxt, inlTreeSym, int64(i*16+12), uint32(nameoff))
|
||||||
}
|
}
|
||||||
|
|
||||||
pcln.Funcdata[obj.FUNCDATA_InlTree] = inlTreeSym
|
pcln.Funcdata[objabi.FUNCDATA_InlTree] = inlTreeSym
|
||||||
pcln.Pcdata[obj.PCDATA_InlTreeIndex] = pcln.Pcinline
|
pcln.Pcdata[objabi.PCDATA_InlTreeIndex] = pcln.Pcinline
|
||||||
}
|
}
|
||||||
|
|
||||||
// pcdata
|
// pcdata
|
||||||
|
|
@ -416,14 +416,14 @@ func (ctxt *Link) pclntab() {
|
||||||
ftab.Size = int64(len(ftab.P))
|
ftab.Size = int64(len(ftab.P))
|
||||||
|
|
||||||
if ctxt.Debugvlog != 0 {
|
if ctxt.Debugvlog != 0 {
|
||||||
ctxt.Logf("%5.2f pclntab=%d bytes, funcdata total %d bytes\n", obj.Cputime(), ftab.Size, funcdataBytes)
|
ctxt.Logf("%5.2f pclntab=%d bytes, funcdata total %d bytes\n", Cputime(), ftab.Size, funcdataBytes)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
func expandGoroot(s string) string {
|
func expandGoroot(s string) string {
|
||||||
const n = len("$GOROOT")
|
const n = len("$GOROOT")
|
||||||
if len(s) >= n+1 && s[:n] == "$GOROOT" && (s[n] == '/' || s[n] == '\\') {
|
if len(s) >= n+1 && s[:n] == "$GOROOT" && (s[n] == '/' || s[n] == '\\') {
|
||||||
root := obj.GOROOT
|
root := objabi.GOROOT
|
||||||
if final := os.Getenv("GOROOT_FINAL"); final != "" {
|
if final := os.Getenv("GOROOT_FINAL"); final != "" {
|
||||||
root = final
|
root = final
|
||||||
}
|
}
|
||||||
|
|
@ -443,7 +443,7 @@ const (
|
||||||
// function for a pc. See src/runtime/symtab.go:findfunc for details.
|
// function for a pc. See src/runtime/symtab.go:findfunc for details.
|
||||||
func (ctxt *Link) findfunctab() {
|
func (ctxt *Link) findfunctab() {
|
||||||
t := ctxt.Syms.Lookup("runtime.findfunctab", 0)
|
t := ctxt.Syms.Lookup("runtime.findfunctab", 0)
|
||||||
t.Type = obj.SRODATA
|
t.Type = objabi.SRODATA
|
||||||
t.Attr |= AttrReachable
|
t.Attr |= AttrReachable
|
||||||
t.Attr |= AttrLocal
|
t.Attr |= AttrLocal
|
||||||
|
|
||||||
|
|
|
||||||
Some files were not shown because too many files have changed in this diff Show more
Loading…
Add table
Add a link
Reference in a new issue