]> Cypherpunks.ru repositories - gostls13.git/blob - src/cmd/link/internal/ld/lib.go
[dev.boringcrypto] all: merge master (2f0da6d) into dev.boringcrypto
[gostls13.git] / src / cmd / link / internal / ld / lib.go
1 // Inferno utils/8l/asm.c
2 // https://bitbucket.org/inferno-os/inferno-os/src/master/utils/8l/asm.c
3 //
4 //      Copyright © 1994-1999 Lucent Technologies Inc.  All rights reserved.
5 //      Portions Copyright © 1995-1997 C H Forsyth (forsyth@terzarima.net)
6 //      Portions Copyright © 1997-1999 Vita Nuova Limited
7 //      Portions Copyright © 2000-2007 Vita Nuova Holdings Limited (www.vitanuova.com)
8 //      Portions Copyright © 2004,2006 Bruce Ellis
9 //      Portions Copyright © 2005-2007 C H Forsyth (forsyth@terzarima.net)
10 //      Revisions Copyright © 2000-2007 Lucent Technologies Inc. and others
11 //      Portions Copyright © 2009 The Go Authors. All rights reserved.
12 //
13 // Permission is hereby granted, free of charge, to any person obtaining a copy
14 // of this software and associated documentation files (the "Software"), to deal
15 // in the Software without restriction, including without limitation the rights
16 // to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
17 // copies of the Software, and to permit persons to whom the Software is
18 // furnished to do so, subject to the following conditions:
19 //
20 // The above copyright notice and this permission notice shall be included in
21 // all copies or substantial portions of the Software.
22 //
23 // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
24 // IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
25 // FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL THE
26 // AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
27 // LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
28 // OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
29 // THE SOFTWARE.
30
31 package ld
32
33 import (
34         "bytes"
35         "cmd/internal/bio"
36         "cmd/internal/goobj"
37         "cmd/internal/obj"
38         "cmd/internal/objabi"
39         "cmd/internal/sys"
40         "cmd/link/internal/loadelf"
41         "cmd/link/internal/loader"
42         "cmd/link/internal/loadmacho"
43         "cmd/link/internal/loadpe"
44         "cmd/link/internal/loadxcoff"
45         "cmd/link/internal/sym"
46         "crypto/sha1"
47         "debug/elf"
48         "debug/macho"
49         "encoding/base64"
50         "encoding/binary"
51         "fmt"
52         exec "internal/execabs"
53         "io"
54         "io/ioutil"
55         "log"
56         "os"
57         "path/filepath"
58         "runtime"
59         "sort"
60         "strings"
61         "sync"
62 )
63
64 // Data layout and relocation.
65
66 // Derived from Inferno utils/6l/l.h
67 // https://bitbucket.org/inferno-os/inferno-os/src/master/utils/6l/l.h
68 //
69 //      Copyright © 1994-1999 Lucent Technologies Inc.  All rights reserved.
70 //      Portions Copyright © 1995-1997 C H Forsyth (forsyth@terzarima.net)
71 //      Portions Copyright © 1997-1999 Vita Nuova Limited
72 //      Portions Copyright © 2000-2007 Vita Nuova Holdings Limited (www.vitanuova.com)
73 //      Portions Copyright © 2004,2006 Bruce Ellis
74 //      Portions Copyright © 2005-2007 C H Forsyth (forsyth@terzarima.net)
75 //      Revisions Copyright © 2000-2007 Lucent Technologies Inc. and others
76 //      Portions Copyright © 2009 The Go Authors. All rights reserved.
77 //
78 // Permission is hereby granted, free of charge, to any person obtaining a copy
79 // of this software and associated documentation files (the "Software"), to deal
80 // in the Software without restriction, including without limitation the rights
81 // to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
82 // copies of the Software, and to permit persons to whom the Software is
83 // furnished to do so, subject to the following conditions:
84 //
85 // The above copyright notice and this permission notice shall be included in
86 // all copies or substantial portions of the Software.
87 //
88 // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
89 // IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
90 // FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL THE
91 // AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
92 // LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
93 // OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
94 // THE SOFTWARE.
95
96 // ArchSyms holds a number of architecture specific symbols used during
97 // relocation.  Rather than allowing them universal access to all symbols,
98 // we keep a subset for relocation application.
99 type ArchSyms struct {
100         Rel     loader.Sym
101         Rela    loader.Sym
102         RelPLT  loader.Sym
103         RelaPLT loader.Sym
104
105         LinkEditGOT loader.Sym
106         LinkEditPLT loader.Sym
107
108         TOC    loader.Sym
109         DotTOC []loader.Sym // for each version
110
111         GOT    loader.Sym
112         PLT    loader.Sym
113         GOTPLT loader.Sym
114
115         Tlsg      loader.Sym
116         Tlsoffset int
117
118         Dynamic loader.Sym
119         DynSym  loader.Sym
120         DynStr  loader.Sym
121 }
122
123 // mkArchSym is a helper for setArchSyms, to set up a special symbol.
124 func (ctxt *Link) mkArchSym(name string, ver int, ls *loader.Sym) {
125         *ls = ctxt.loader.LookupOrCreateSym(name, ver)
126         ctxt.loader.SetAttrReachable(*ls, true)
127 }
128
129 // mkArchVecSym is similar to  setArchSyms, but operates on elements within
130 // a slice, where each element corresponds to some symbol version.
131 func (ctxt *Link) mkArchSymVec(name string, ver int, ls []loader.Sym) {
132         ls[ver] = ctxt.loader.LookupOrCreateSym(name, ver)
133         ctxt.loader.SetAttrReachable(ls[ver], true)
134 }
135
136 // setArchSyms sets up the ArchSyms structure, and must be called before
137 // relocations are applied.
138 func (ctxt *Link) setArchSyms() {
139         ctxt.mkArchSym(".got", 0, &ctxt.GOT)
140         ctxt.mkArchSym(".plt", 0, &ctxt.PLT)
141         ctxt.mkArchSym(".got.plt", 0, &ctxt.GOTPLT)
142         ctxt.mkArchSym(".dynamic", 0, &ctxt.Dynamic)
143         ctxt.mkArchSym(".dynsym", 0, &ctxt.DynSym)
144         ctxt.mkArchSym(".dynstr", 0, &ctxt.DynStr)
145
146         if ctxt.IsPPC64() {
147                 ctxt.mkArchSym("TOC", 0, &ctxt.TOC)
148
149                 // NB: note the +2 below for DotTOC2 compared to the +1 for
150                 // DocTOC. This is because loadlibfull() creates an additional
151                 // syms version during conversion of loader.Sym symbols to
152                 // *sym.Symbol symbols. Symbols that are assigned this final
153                 // version are not going to have TOC references, so it should
154                 // be ok for them to inherit an invalid .TOC. symbol.
155                 // TODO: revisit the +2, now that loadlibfull is gone.
156                 ctxt.DotTOC = make([]loader.Sym, ctxt.MaxVersion()+2)
157                 for i := 0; i <= ctxt.MaxVersion(); i++ {
158                         if i >= 2 && i < sym.SymVerStatic { // these versions are not used currently
159                                 continue
160                         }
161                         ctxt.mkArchSymVec(".TOC.", i, ctxt.DotTOC)
162                 }
163         }
164         if ctxt.IsElf() {
165                 ctxt.mkArchSym(".rel", 0, &ctxt.Rel)
166                 ctxt.mkArchSym(".rela", 0, &ctxt.Rela)
167                 ctxt.mkArchSym(".rel.plt", 0, &ctxt.RelPLT)
168                 ctxt.mkArchSym(".rela.plt", 0, &ctxt.RelaPLT)
169         }
170         if ctxt.IsDarwin() {
171                 ctxt.mkArchSym(".linkedit.got", 0, &ctxt.LinkEditGOT)
172                 ctxt.mkArchSym(".linkedit.plt", 0, &ctxt.LinkEditPLT)
173         }
174 }
175
176 type Arch struct {
177         Funcalign      int
178         Maxalign       int
179         Minalign       int
180         Dwarfregsp     int
181         Dwarfreglr     int
182         Androiddynld   string
183         Linuxdynld     string
184         Freebsddynld   string
185         Netbsddynld    string
186         Openbsddynld   string
187         Dragonflydynld string
188         Solarisdynld   string
189
190         // Empty spaces between codeblocks will be padded with this value.
191         // For example an architecture might want to pad with a trap instruction to
192         // catch wayward programs. Architectures that do not define a padding value
193         // are padded with zeros.
194         CodePad []byte
195
196         // Set to true to write all text blocks in with CodeBlkWrite
197         WriteTextBlocks bool
198
199         // Plan 9 variables.
200         Plan9Magic  uint32
201         Plan9_64Bit bool
202
203         Adddynrel func(*Target, *loader.Loader, *ArchSyms, loader.Sym, loader.Reloc, int) bool
204         Archinit  func(*Link)
205         // Archreloc is an arch-specific hook that assists in relocation processing
206         // (invoked by 'relocsym'); it handles target-specific relocation tasks.
207         // Here "rel" is the current relocation being examined, "sym" is the symbol
208         // containing the chunk of data to which the relocation applies, and "off"
209         // is the contents of the to-be-relocated data item (from sym.P). Return
210         // value is the appropriately relocated value (to be written back to the
211         // same spot in sym.P), number of external _host_ relocations needed (i.e.
212         // ELF/Mach-O/etc. relocations, not Go relocations, this must match Elfreloc1,
213         // etc.), and a boolean indicating success/failure (a failing value indicates
214         // a fatal error).
215         Archreloc func(*Target, *loader.Loader, *ArchSyms, loader.Reloc, loader.Sym,
216                 int64) (relocatedOffset int64, nExtReloc int, ok bool)
217         // Archrelocvariant is a second arch-specific hook used for
218         // relocation processing; it handles relocations where r.Type is
219         // insufficient to describe the relocation (r.Variant !=
220         // sym.RV_NONE). Here "rel" is the relocation being applied, "sym"
221         // is the symbol containing the chunk of data to which the
222         // relocation applies, and "off" is the contents of the
223         // to-be-relocated data item (from sym.P). Return is an updated
224         // offset value.
225         Archrelocvariant func(target *Target, ldr *loader.Loader, rel loader.Reloc,
226                 rv sym.RelocVariant, sym loader.Sym, offset int64) (relocatedOffset int64)
227
228         // Generate a trampoline for a call from s to rs if necessary. ri is
229         // index of the relocation.
230         Trampoline func(ctxt *Link, ldr *loader.Loader, ri int, rs, s loader.Sym)
231
232         // Assembling the binary breaks into two phases, writing the code/data/
233         // dwarf information (which is rather generic), and some more architecture
234         // specific work like setting up the elf headers/dynamic relocations, etc.
235         // The phases are called "Asmb" and "Asmb2". Asmb2 needs to be defined for
236         // every architecture, but only if architecture has an Asmb function will
237         // it be used for assembly.  Otherwise a generic assembly Asmb function is
238         // used.
239         Asmb  func(*Link, *loader.Loader)
240         Asmb2 func(*Link, *loader.Loader)
241
242         // Extreloc is an arch-specific hook that converts a Go relocation to an
243         // external relocation. Return the external relocation and whether it is
244         // needed.
245         Extreloc func(*Target, *loader.Loader, loader.Reloc, loader.Sym) (loader.ExtReloc, bool)
246
247         Elfreloc1      func(*Link, *OutBuf, *loader.Loader, loader.Sym, loader.ExtReloc, int, int64) bool
248         ElfrelocSize   uint32 // size of an ELF relocation record, must match Elfreloc1.
249         Elfsetupplt    func(ctxt *Link, plt, gotplt *loader.SymbolBuilder, dynamic loader.Sym)
250         Gentext        func(*Link, *loader.Loader) // Generate text before addressing has been performed.
251         Machoreloc1    func(*sys.Arch, *OutBuf, *loader.Loader, loader.Sym, loader.ExtReloc, int64) bool
252         MachorelocSize uint32 // size of an Mach-O relocation record, must match Machoreloc1.
253         PEreloc1       func(*sys.Arch, *OutBuf, *loader.Loader, loader.Sym, loader.ExtReloc, int64) bool
254         Xcoffreloc1    func(*sys.Arch, *OutBuf, *loader.Loader, loader.Sym, loader.ExtReloc, int64) bool
255
256         // Generate additional symbols for the native symbol table just prior to
257         // code generation.
258         GenSymsLate func(*Link, *loader.Loader)
259
260         // TLSIEtoLE converts a TLS Initial Executable relocation to
261         // a TLS Local Executable relocation.
262         //
263         // This is possible when a TLS IE relocation refers to a local
264         // symbol in an executable, which is typical when internally
265         // linking PIE binaries.
266         TLSIEtoLE func(P []byte, off, size int)
267
268         // optional override for assignAddress
269         AssignAddress func(ldr *loader.Loader, sect *sym.Section, n int, s loader.Sym, va uint64, isTramp bool) (*sym.Section, int, uint64)
270 }
271
272 var (
273         thearch Arch
274         lcSize  int32
275         rpath   Rpath
276         spSize  int32
277         symSize int32
278 )
279
280 const (
281         MINFUNC = 16 // minimum size for a function
282 )
283
284 // DynlinkingGo reports whether we are producing Go code that can live
285 // in separate shared libraries linked together at runtime.
286 func (ctxt *Link) DynlinkingGo() bool {
287         if !ctxt.Loaded {
288                 panic("DynlinkingGo called before all symbols loaded")
289         }
290         return ctxt.BuildMode == BuildModeShared || ctxt.linkShared || ctxt.BuildMode == BuildModePlugin || ctxt.canUsePlugins
291 }
292
293 // CanUsePlugins reports whether a plugins can be used
294 func (ctxt *Link) CanUsePlugins() bool {
295         if !ctxt.Loaded {
296                 panic("CanUsePlugins called before all symbols loaded")
297         }
298         return ctxt.canUsePlugins
299 }
300
301 // NeedCodeSign reports whether we need to code-sign the output binary.
302 func (ctxt *Link) NeedCodeSign() bool {
303         return ctxt.IsDarwin() && ctxt.IsARM64()
304 }
305
306 var (
307         dynlib          []string
308         ldflag          []string
309         havedynamic     int
310         Funcalign       int
311         iscgo           bool
312         elfglobalsymndx int
313         interpreter     string
314
315         debug_s bool // backup old value of debug['s']
316         HEADR   int32
317
318         nerrors  int
319         liveness int64
320
321         // See -strictdups command line flag.
322         checkStrictDups   int // 0=off 1=warning 2=error
323         strictDupMsgCount int
324 )
325
326 var (
327         Segtext      sym.Segment
328         Segrodata    sym.Segment
329         Segrelrodata sym.Segment
330         Segdata      sym.Segment
331         Segdwarf     sym.Segment
332
333         Segments = []*sym.Segment{&Segtext, &Segrodata, &Segrelrodata, &Segdata, &Segdwarf}
334 )
335
336 const pkgdef = "__.PKGDEF"
337
338 var (
339         // Set if we see an object compiled by the host compiler that is not
340         // from a package that is known to support internal linking mode.
341         externalobj = false
342         theline     string
343 )
344
345 func Lflag(ctxt *Link, arg string) {
346         ctxt.Libdir = append(ctxt.Libdir, arg)
347 }
348
349 /*
350  * Unix doesn't like it when we write to a running (or, sometimes,
351  * recently run) binary, so remove the output file before writing it.
352  * On Windows 7, remove() can force a subsequent create() to fail.
353  * S_ISREG() does not exist on Plan 9.
354  */
355 func mayberemoveoutfile() {
356         if fi, err := os.Lstat(*flagOutfile); err == nil && !fi.Mode().IsRegular() {
357                 return
358         }
359         os.Remove(*flagOutfile)
360 }
361
362 func libinit(ctxt *Link) {
363         Funcalign = thearch.Funcalign
364
365         // add goroot to the end of the libdir list.
366         suffix := ""
367
368         suffixsep := ""
369         if *flagInstallSuffix != "" {
370                 suffixsep = "_"
371                 suffix = *flagInstallSuffix
372         } else if *flagRace {
373                 suffixsep = "_"
374                 suffix = "race"
375         } else if *flagMsan {
376                 suffixsep = "_"
377                 suffix = "msan"
378         }
379
380         Lflag(ctxt, filepath.Join(objabi.GOROOT, "pkg", fmt.Sprintf("%s_%s%s%s", objabi.GOOS, objabi.GOARCH, suffixsep, suffix)))
381
382         mayberemoveoutfile()
383
384         if err := ctxt.Out.Open(*flagOutfile); err != nil {
385                 Exitf("cannot create %s: %v", *flagOutfile, err)
386         }
387
388         if *flagEntrySymbol == "" {
389                 switch ctxt.BuildMode {
390                 case BuildModeCShared, BuildModeCArchive:
391                         *flagEntrySymbol = fmt.Sprintf("_rt0_%s_%s_lib", objabi.GOARCH, objabi.GOOS)
392                 case BuildModeExe, BuildModePIE:
393                         *flagEntrySymbol = fmt.Sprintf("_rt0_%s_%s", objabi.GOARCH, objabi.GOOS)
394                 case BuildModeShared, BuildModePlugin:
395                         // No *flagEntrySymbol for -buildmode=shared and plugin
396                 default:
397                         Errorf(nil, "unknown *flagEntrySymbol for buildmode %v", ctxt.BuildMode)
398                 }
399         }
400 }
401
402 func exitIfErrors() {
403         if nerrors != 0 || checkStrictDups > 1 && strictDupMsgCount > 0 {
404                 mayberemoveoutfile()
405                 Exit(2)
406         }
407
408 }
409
410 func errorexit() {
411         exitIfErrors()
412         Exit(0)
413 }
414
415 func loadinternal(ctxt *Link, name string) *sym.Library {
416         zerofp := goobj.FingerprintType{}
417         if ctxt.linkShared && ctxt.PackageShlib != nil {
418                 if shlib := ctxt.PackageShlib[name]; shlib != "" {
419                         return addlibpath(ctxt, "internal", "internal", "", name, shlib, zerofp)
420                 }
421         }
422         if ctxt.PackageFile != nil {
423                 if pname := ctxt.PackageFile[name]; pname != "" {
424                         return addlibpath(ctxt, "internal", "internal", pname, name, "", zerofp)
425                 }
426                 ctxt.Logf("loadinternal: cannot find %s\n", name)
427                 return nil
428         }
429
430         for _, libdir := range ctxt.Libdir {
431                 if ctxt.linkShared {
432                         shlibname := filepath.Join(libdir, name+".shlibname")
433                         if ctxt.Debugvlog != 0 {
434                                 ctxt.Logf("searching for %s.a in %s\n", name, shlibname)
435                         }
436                         if _, err := os.Stat(shlibname); err == nil {
437                                 return addlibpath(ctxt, "internal", "internal", "", name, shlibname, zerofp)
438                         }
439                 }
440                 pname := filepath.Join(libdir, name+".a")
441                 if ctxt.Debugvlog != 0 {
442                         ctxt.Logf("searching for %s.a in %s\n", name, pname)
443                 }
444                 if _, err := os.Stat(pname); err == nil {
445                         return addlibpath(ctxt, "internal", "internal", pname, name, "", zerofp)
446                 }
447         }
448
449         ctxt.Logf("warning: unable to find %s.a\n", name)
450         return nil
451 }
452
453 // extld returns the current external linker.
454 func (ctxt *Link) extld() string {
455         if *flagExtld == "" {
456                 *flagExtld = "gcc"
457         }
458         return *flagExtld
459 }
460
461 // findLibPathCmd uses cmd command to find gcc library libname.
462 // It returns library full path if found, or "none" if not found.
463 func (ctxt *Link) findLibPathCmd(cmd, libname string) string {
464         extld := ctxt.extld()
465         args := hostlinkArchArgs(ctxt.Arch)
466         args = append(args, cmd)
467         if ctxt.Debugvlog != 0 {
468                 ctxt.Logf("%s %v\n", extld, args)
469         }
470         out, err := exec.Command(extld, args...).Output()
471         if err != nil {
472                 if ctxt.Debugvlog != 0 {
473                         ctxt.Logf("not using a %s file because compiler failed\n%v\n%s\n", libname, err, out)
474                 }
475                 return "none"
476         }
477         return strings.TrimSpace(string(out))
478 }
479
480 // findLibPath searches for library libname.
481 // It returns library full path if found, or "none" if not found.
482 func (ctxt *Link) findLibPath(libname string) string {
483         return ctxt.findLibPathCmd("--print-file-name="+libname, libname)
484 }
485
486 func (ctxt *Link) loadlib() {
487         var flags uint32
488         switch *FlagStrictDups {
489         case 0:
490                 // nothing to do
491         case 1, 2:
492                 flags |= loader.FlagStrictDups
493         default:
494                 log.Fatalf("invalid -strictdups flag value %d", *FlagStrictDups)
495         }
496         if !*flagAbiWrap || ctxt.linkShared {
497                 // Use ABI aliases if ABI wrappers are not used.
498                 // TODO: for now we still use ABI aliases in shared linkage, even if
499                 // the wrapper is enabled.
500                 flags |= loader.FlagUseABIAlias
501         }
502         elfsetstring1 := func(str string, off int) { elfsetstring(ctxt, 0, str, off) }
503         ctxt.loader = loader.NewLoader(flags, elfsetstring1, &ctxt.ErrorReporter.ErrorReporter)
504         ctxt.ErrorReporter.SymName = func(s loader.Sym) string {
505                 return ctxt.loader.SymName(s)
506         }
507
508         ctxt.cgo_export_static = make(map[string]bool)
509         ctxt.cgo_export_dynamic = make(map[string]bool)
510
511         // ctxt.Library grows during the loop, so not a range loop.
512         i := 0
513         for ; i < len(ctxt.Library); i++ {
514                 lib := ctxt.Library[i]
515                 if lib.Shlib == "" {
516                         if ctxt.Debugvlog > 1 {
517                                 ctxt.Logf("autolib: %s (from %s)\n", lib.File, lib.Objref)
518                         }
519                         loadobjfile(ctxt, lib)
520                 }
521         }
522
523         // load internal packages, if not already
524         if *flagRace {
525                 loadinternal(ctxt, "runtime/race")
526         }
527         if *flagMsan {
528                 loadinternal(ctxt, "runtime/msan")
529         }
530         loadinternal(ctxt, "runtime")
531         for ; i < len(ctxt.Library); i++ {
532                 lib := ctxt.Library[i]
533                 if lib.Shlib == "" {
534                         loadobjfile(ctxt, lib)
535                 }
536         }
537         // At this point, the Go objects are "preloaded". Not all the symbols are
538         // added to the symbol table (only defined package symbols are). Looking
539         // up symbol by name may not get expected result.
540
541         iscgo = ctxt.LibraryByPkg["runtime/cgo"] != nil
542         ctxt.canUsePlugins = ctxt.LibraryByPkg["plugin"] != nil
543
544         // We now have enough information to determine the link mode.
545         determineLinkMode(ctxt)
546
547         if ctxt.LinkMode == LinkExternal && !iscgo && !(objabi.GOOS == "darwin" && ctxt.BuildMode != BuildModePlugin && ctxt.Arch.Family == sys.AMD64) {
548                 // This indicates a user requested -linkmode=external.
549                 // The startup code uses an import of runtime/cgo to decide
550                 // whether to initialize the TLS.  So give it one. This could
551                 // be handled differently but it's an unusual case.
552                 if lib := loadinternal(ctxt, "runtime/cgo"); lib != nil && lib.Shlib == "" {
553                         if ctxt.BuildMode == BuildModeShared || ctxt.linkShared {
554                                 Exitf("cannot implicitly include runtime/cgo in a shared library")
555                         }
556                         loadobjfile(ctxt, lib)
557                 }
558         }
559
560         // Add non-package symbols and references of externally defined symbols.
561         ctxt.loader.LoadSyms(ctxt.Arch)
562
563         // Load symbols from shared libraries, after all Go object symbols are loaded.
564         for _, lib := range ctxt.Library {
565                 if lib.Shlib != "" {
566                         if ctxt.Debugvlog > 1 {
567                                 ctxt.Logf("autolib: %s (from %s)\n", lib.Shlib, lib.Objref)
568                         }
569                         ldshlibsyms(ctxt, lib.Shlib)
570                 }
571         }
572
573         // Process cgo directives (has to be done before host object loading).
574         ctxt.loadcgodirectives()
575
576         // Conditionally load host objects, or setup for external linking.
577         hostobjs(ctxt)
578         hostlinksetup(ctxt)
579
580         if ctxt.LinkMode == LinkInternal && len(hostobj) != 0 {
581                 // If we have any undefined symbols in external
582                 // objects, try to read them from the libgcc file.
583                 any := false
584                 undefs := ctxt.loader.UndefinedRelocTargets(1)
585                 if len(undefs) > 0 {
586                         any = true
587                 }
588                 if any {
589                         if *flagLibGCC == "" {
590                                 *flagLibGCC = ctxt.findLibPathCmd("--print-libgcc-file-name", "libgcc")
591                         }
592                         if runtime.GOOS == "openbsd" && *flagLibGCC == "libgcc.a" {
593                                 // On OpenBSD `clang --print-libgcc-file-name` returns "libgcc.a".
594                                 // In this case we fail to load libgcc.a and can encounter link
595                                 // errors - see if we can find libcompiler_rt.a instead.
596                                 *flagLibGCC = ctxt.findLibPathCmd("--print-file-name=libcompiler_rt.a", "libcompiler_rt")
597                         }
598                         if *flagLibGCC != "none" {
599                                 hostArchive(ctxt, *flagLibGCC)
600                         }
601                         if ctxt.HeadType == objabi.Hwindows {
602                                 if p := ctxt.findLibPath("libmingwex.a"); p != "none" {
603                                         hostArchive(ctxt, p)
604                                 }
605                                 if p := ctxt.findLibPath("libmingw32.a"); p != "none" {
606                                         hostArchive(ctxt, p)
607                                 }
608                                 // Link libmsvcrt.a to resolve '__acrt_iob_func' symbol
609                                 // (see https://golang.org/issue/23649 for details).
610                                 if p := ctxt.findLibPath("libmsvcrt.a"); p != "none" {
611                                         hostArchive(ctxt, p)
612                                 }
613                                 // TODO: maybe do something similar to peimporteddlls to collect all lib names
614                                 // and try link them all to final exe just like libmingwex.a and libmingw32.a:
615                                 /*
616                                         for:
617                                         #cgo windows LDFLAGS: -lmsvcrt -lm
618                                         import:
619                                         libmsvcrt.a libm.a
620                                 */
621                         }
622                 }
623         }
624
625         // We've loaded all the code now.
626         ctxt.Loaded = true
627
628         importcycles()
629
630         strictDupMsgCount = ctxt.loader.NStrictDupMsgs()
631 }
632
633 // setupdynexp constructs ctxt.dynexp, a list of loader.Sym.
634 func setupdynexp(ctxt *Link) {
635         dynexpMap := ctxt.cgo_export_dynamic
636         if ctxt.LinkMode == LinkExternal {
637                 dynexpMap = ctxt.cgo_export_static
638         }
639         d := make([]loader.Sym, 0, len(dynexpMap))
640         for exp := range dynexpMap {
641                 s := ctxt.loader.LookupOrCreateSym(exp, 0)
642                 d = append(d, s)
643                 // sanity check
644                 if !ctxt.loader.AttrReachable(s) {
645                         panic("dynexp entry not reachable")
646                 }
647         }
648         sort.Slice(d, func(i, j int) bool {
649                 return ctxt.loader.SymName(d[i]) < ctxt.loader.SymName(d[j])
650         })
651
652         // Resolve ABI aliases in the list of cgo-exported functions.
653         // This is necessary because we load the ABI0 symbol for all
654         // cgo exports.
655         for i, s := range d {
656                 if ctxt.loader.SymType(s) != sym.SABIALIAS {
657                         continue
658                 }
659                 t := ctxt.loader.ResolveABIAlias(s)
660                 ctxt.loader.CopyAttributes(s, t)
661                 ctxt.loader.SetSymExtname(t, ctxt.loader.SymExtname(s))
662                 d[i] = t
663         }
664         ctxt.dynexp = d
665
666         ctxt.cgo_export_static = nil
667         ctxt.cgo_export_dynamic = nil
668 }
669
670 // loadcgodirectives reads the previously discovered cgo directives, creating
671 // symbols in preparation for host object loading or use later in the link.
672 func (ctxt *Link) loadcgodirectives() {
673         l := ctxt.loader
674         hostObjSyms := make(map[loader.Sym]struct{})
675         for _, d := range ctxt.cgodata {
676                 setCgoAttr(ctxt, ctxt.loader.LookupOrCreateSym, d.file, d.pkg, d.directives, hostObjSyms)
677         }
678         ctxt.cgodata = nil
679
680         if ctxt.LinkMode == LinkInternal {
681                 // Drop all the cgo_import_static declarations.
682                 // Turns out we won't be needing them.
683                 for symIdx := range hostObjSyms {
684                         if l.SymType(symIdx) == sym.SHOSTOBJ {
685                                 // If a symbol was marked both
686                                 // cgo_import_static and cgo_import_dynamic,
687                                 // then we want to make it cgo_import_dynamic
688                                 // now.
689                                 su := l.MakeSymbolUpdater(symIdx)
690                                 if l.SymExtname(symIdx) != "" && l.SymDynimplib(symIdx) != "" && !(l.AttrCgoExportStatic(symIdx) || l.AttrCgoExportDynamic(symIdx)) {
691                                         su.SetType(sym.SDYNIMPORT)
692                                 } else {
693                                         su.SetType(0)
694                                 }
695                         }
696                 }
697         }
698 }
699
700 // Set up flags and special symbols depending on the platform build mode.
701 // This version works with loader.Loader.
702 func (ctxt *Link) linksetup() {
703         switch ctxt.BuildMode {
704         case BuildModeCShared, BuildModePlugin:
705                 symIdx := ctxt.loader.LookupOrCreateSym("runtime.islibrary", 0)
706                 sb := ctxt.loader.MakeSymbolUpdater(symIdx)
707                 sb.SetType(sym.SNOPTRDATA)
708                 sb.AddUint8(1)
709         case BuildModeCArchive:
710                 symIdx := ctxt.loader.LookupOrCreateSym("runtime.isarchive", 0)
711                 sb := ctxt.loader.MakeSymbolUpdater(symIdx)
712                 sb.SetType(sym.SNOPTRDATA)
713                 sb.AddUint8(1)
714         }
715
716         // Recalculate pe parameters now that we have ctxt.LinkMode set.
717         if ctxt.HeadType == objabi.Hwindows {
718                 Peinit(ctxt)
719         }
720
721         if ctxt.HeadType == objabi.Hdarwin && ctxt.LinkMode == LinkExternal {
722                 *FlagTextAddr = 0
723         }
724
725         // If there are no dynamic libraries needed, gcc disables dynamic linking.
726         // Because of this, glibc's dynamic ELF loader occasionally (like in version 2.13)
727         // assumes that a dynamic binary always refers to at least one dynamic library.
728         // Rather than be a source of test cases for glibc, disable dynamic linking
729         // the same way that gcc would.
730         //
731         // Exception: on OS X, programs such as Shark only work with dynamic
732         // binaries, so leave it enabled on OS X (Mach-O) binaries.
733         // Also leave it enabled on Solaris which doesn't support
734         // statically linked binaries.
735         if ctxt.BuildMode == BuildModeExe {
736                 if havedynamic == 0 && ctxt.HeadType != objabi.Hdarwin && ctxt.HeadType != objabi.Hsolaris {
737                         *FlagD = true
738                 }
739         }
740
741         if ctxt.LinkMode == LinkExternal && ctxt.Arch.Family == sys.PPC64 && objabi.GOOS != "aix" {
742                 toc := ctxt.loader.LookupOrCreateSym(".TOC.", 0)
743                 sb := ctxt.loader.MakeSymbolUpdater(toc)
744                 sb.SetType(sym.SDYNIMPORT)
745         }
746
747         // The Android Q linker started to complain about underalignment of the our TLS
748         // section. We don't actually use the section on android, so don't
749         // generate it.
750         if objabi.GOOS != "android" {
751                 tlsg := ctxt.loader.LookupOrCreateSym("runtime.tlsg", 0)
752                 sb := ctxt.loader.MakeSymbolUpdater(tlsg)
753
754                 // runtime.tlsg is used for external linking on platforms that do not define
755                 // a variable to hold g in assembly (currently only intel).
756                 if sb.Type() == 0 {
757                         sb.SetType(sym.STLSBSS)
758                         sb.SetSize(int64(ctxt.Arch.PtrSize))
759                 } else if sb.Type() != sym.SDYNIMPORT {
760                         Errorf(nil, "runtime declared tlsg variable %v", sb.Type())
761                 }
762                 ctxt.loader.SetAttrReachable(tlsg, true)
763                 ctxt.Tlsg = tlsg
764         }
765
766         var moduledata loader.Sym
767         var mdsb *loader.SymbolBuilder
768         if ctxt.BuildMode == BuildModePlugin {
769                 moduledata = ctxt.loader.LookupOrCreateSym("local.pluginmoduledata", 0)
770                 mdsb = ctxt.loader.MakeSymbolUpdater(moduledata)
771                 ctxt.loader.SetAttrLocal(moduledata, true)
772         } else {
773                 moduledata = ctxt.loader.LookupOrCreateSym("runtime.firstmoduledata", 0)
774                 mdsb = ctxt.loader.MakeSymbolUpdater(moduledata)
775         }
776         if mdsb.Type() != 0 && mdsb.Type() != sym.SDYNIMPORT {
777                 // If the module (toolchain-speak for "executable or shared
778                 // library") we are linking contains the runtime package, it
779                 // will define the runtime.firstmoduledata symbol and we
780                 // truncate it back to 0 bytes so we can define its entire
781                 // contents in symtab.go:symtab().
782                 mdsb.SetSize(0)
783
784                 // In addition, on ARM, the runtime depends on the linker
785                 // recording the value of GOARM.
786                 if ctxt.Arch.Family == sys.ARM {
787                         goarm := ctxt.loader.LookupOrCreateSym("runtime.goarm", 0)
788                         sb := ctxt.loader.MakeSymbolUpdater(goarm)
789                         sb.SetType(sym.SDATA)
790                         sb.SetSize(0)
791                         sb.AddUint8(uint8(objabi.GOARM))
792                 }
793         } else {
794                 // If OTOH the module does not contain the runtime package,
795                 // create a local symbol for the moduledata.
796                 moduledata = ctxt.loader.LookupOrCreateSym("local.moduledata", 0)
797                 mdsb = ctxt.loader.MakeSymbolUpdater(moduledata)
798                 ctxt.loader.SetAttrLocal(moduledata, true)
799         }
800         // In all cases way we mark the moduledata as noptrdata to hide it from
801         // the GC.
802         mdsb.SetType(sym.SNOPTRDATA)
803         ctxt.loader.SetAttrReachable(moduledata, true)
804         ctxt.Moduledata = moduledata
805
806         if ctxt.Arch == sys.Arch386 && ctxt.HeadType != objabi.Hwindows {
807                 if (ctxt.BuildMode == BuildModeCArchive && ctxt.IsELF) || ctxt.BuildMode == BuildModeCShared || ctxt.BuildMode == BuildModePIE || ctxt.DynlinkingGo() {
808                         got := ctxt.loader.LookupOrCreateSym("_GLOBAL_OFFSET_TABLE_", 0)
809                         sb := ctxt.loader.MakeSymbolUpdater(got)
810                         sb.SetType(sym.SDYNIMPORT)
811                         ctxt.loader.SetAttrReachable(got, true)
812                 }
813         }
814
815         // DWARF-gen and other phases require that the unit Textp slices
816         // be populated, so that it can walk the functions in each unit.
817         // Call into the loader to do this (requires that we collect the
818         // set of internal libraries first). NB: might be simpler if we
819         // moved isRuntimeDepPkg to cmd/internal and then did the test in
820         // loader.AssignTextSymbolOrder.
821         ctxt.Library = postorder(ctxt.Library)
822         intlibs := []bool{}
823         for _, lib := range ctxt.Library {
824                 intlibs = append(intlibs, isRuntimeDepPkg(lib.Pkg))
825         }
826         ctxt.Textp = ctxt.loader.AssignTextSymbolOrder(ctxt.Library, intlibs, ctxt.Textp)
827 }
828
829 // mangleTypeSym shortens the names of symbols that represent Go types
830 // if they are visible in the symbol table.
831 //
832 // As the names of these symbols are derived from the string of
833 // the type, they can run to many kilobytes long. So we shorten
834 // them using a SHA-1 when the name appears in the final binary.
835 // This also removes characters that upset external linkers.
836 //
837 // These are the symbols that begin with the prefix 'type.' and
838 // contain run-time type information used by the runtime and reflect
839 // packages. All Go binaries contain these symbols, but only
840 // those programs loaded dynamically in multiple parts need these
841 // symbols to have entries in the symbol table.
842 func (ctxt *Link) mangleTypeSym() {
843         if ctxt.BuildMode != BuildModeShared && !ctxt.linkShared && ctxt.BuildMode != BuildModePlugin && !ctxt.CanUsePlugins() {
844                 return
845         }
846
847         ldr := ctxt.loader
848         for s := loader.Sym(1); s < loader.Sym(ldr.NSym()); s++ {
849                 if !ldr.AttrReachable(s) && !ctxt.linkShared {
850                         // If -linkshared, the GCProg generation code may need to reach
851                         // out to the shared library for the type descriptor's data, even
852                         // the type descriptor itself is not actually needed at run time
853                         // (therefore not reachable). We still need to mangle its name,
854                         // so it is consistent with the one stored in the shared library.
855                         continue
856                 }
857                 name := ldr.SymName(s)
858                 newName := typeSymbolMangle(name)
859                 if newName != name {
860                         ldr.SetSymExtname(s, newName)
861
862                         // When linking against a shared library, the Go object file may
863                         // have reference to the original symbol name whereas the shared
864                         // library provides a symbol with the mangled name. We need to
865                         // copy the payload of mangled to original.
866                         // XXX maybe there is a better way to do this.
867                         dup := ldr.Lookup(newName, ldr.SymVersion(s))
868                         if dup != 0 {
869                                 st := ldr.SymType(s)
870                                 dt := ldr.SymType(dup)
871                                 if st == sym.Sxxx && dt != sym.Sxxx {
872                                         ldr.CopySym(dup, s)
873                                 }
874                         }
875                 }
876         }
877 }
878
879 // typeSymbolMangle mangles the given symbol name into something shorter.
880 //
881 // Keep the type.. prefix, which parts of the linker (like the
882 // DWARF generator) know means the symbol is not decodable.
883 // Leave type.runtime. symbols alone, because other parts of
884 // the linker manipulates them.
885 func typeSymbolMangle(name string) string {
886         if !strings.HasPrefix(name, "type.") {
887                 return name
888         }
889         if strings.HasPrefix(name, "type.runtime.") {
890                 return name
891         }
892         if len(name) <= 14 && !strings.Contains(name, "@") { // Issue 19529
893                 return name
894         }
895         hash := sha1.Sum([]byte(name))
896         prefix := "type."
897         if name[5] == '.' {
898                 prefix = "type.."
899         }
900         return prefix + base64.StdEncoding.EncodeToString(hash[:6])
901 }
902
903 /*
904  * look for the next file in an archive.
905  * adapted from libmach.
906  */
907 func nextar(bp *bio.Reader, off int64, a *ArHdr) int64 {
908         if off&1 != 0 {
909                 off++
910         }
911         bp.MustSeek(off, 0)
912         var buf [SAR_HDR]byte
913         if n, err := io.ReadFull(bp, buf[:]); err != nil {
914                 if n == 0 && err != io.EOF {
915                         return -1
916                 }
917                 return 0
918         }
919
920         a.name = artrim(buf[0:16])
921         a.date = artrim(buf[16:28])
922         a.uid = artrim(buf[28:34])
923         a.gid = artrim(buf[34:40])
924         a.mode = artrim(buf[40:48])
925         a.size = artrim(buf[48:58])
926         a.fmag = artrim(buf[58:60])
927
928         arsize := atolwhex(a.size)
929         if arsize&1 != 0 {
930                 arsize++
931         }
932         return arsize + SAR_HDR
933 }
934
935 func loadobjfile(ctxt *Link, lib *sym.Library) {
936         pkg := objabi.PathToPrefix(lib.Pkg)
937
938         if ctxt.Debugvlog > 1 {
939                 ctxt.Logf("ldobj: %s (%s)\n", lib.File, pkg)
940         }
941         f, err := bio.Open(lib.File)
942         if err != nil {
943                 Exitf("cannot open file %s: %v", lib.File, err)
944         }
945         defer f.Close()
946         defer func() {
947                 if pkg == "main" && !lib.Main {
948                         Exitf("%s: not package main", lib.File)
949                 }
950         }()
951
952         for i := 0; i < len(ARMAG); i++ {
953                 if c, err := f.ReadByte(); err == nil && c == ARMAG[i] {
954                         continue
955                 }
956
957                 /* load it as a regular file */
958                 l := f.MustSeek(0, 2)
959                 f.MustSeek(0, 0)
960                 ldobj(ctxt, f, lib, l, lib.File, lib.File)
961                 return
962         }
963
964         /*
965          * load all the object files from the archive now.
966          * this gives us sequential file access and keeps us
967          * from needing to come back later to pick up more
968          * objects.  it breaks the usual C archive model, but
969          * this is Go, not C.  the common case in Go is that
970          * we need to load all the objects, and then we throw away
971          * the individual symbols that are unused.
972          *
973          * loading every object will also make it possible to
974          * load foreign objects not referenced by __.PKGDEF.
975          */
976         var arhdr ArHdr
977         off := f.Offset()
978         for {
979                 l := nextar(f, off, &arhdr)
980                 if l == 0 {
981                         break
982                 }
983                 if l < 0 {
984                         Exitf("%s: malformed archive", lib.File)
985                 }
986                 off += l
987
988                 // __.PKGDEF isn't a real Go object file, and it's
989                 // absent in -linkobj builds anyway. Skipping it
990                 // ensures consistency between -linkobj and normal
991                 // build modes.
992                 if arhdr.name == pkgdef {
993                         continue
994                 }
995
996                 // Skip other special (non-object-file) sections that
997                 // build tools may have added. Such sections must have
998                 // short names so that the suffix is not truncated.
999                 if len(arhdr.name) < 16 {
1000                         if ext := filepath.Ext(arhdr.name); ext != ".o" && ext != ".syso" {
1001                                 continue
1002                         }
1003                 }
1004
1005                 pname := fmt.Sprintf("%s(%s)", lib.File, arhdr.name)
1006                 l = atolwhex(arhdr.size)
1007                 ldobj(ctxt, f, lib, l, pname, lib.File)
1008         }
1009 }
1010
1011 type Hostobj struct {
1012         ld     func(*Link, *bio.Reader, string, int64, string)
1013         pkg    string
1014         pn     string
1015         file   string
1016         off    int64
1017         length int64
1018 }
1019
1020 var hostobj []Hostobj
1021
1022 // These packages can use internal linking mode.
1023 // Others trigger external mode.
1024 var internalpkg = []string{
1025         "crypto/internal/boring",
1026         "crypto/x509",
1027         "net",
1028         "os/user",
1029         "runtime/cgo",
1030         "runtime/race",
1031         "runtime/msan",
1032 }
1033
1034 func ldhostobj(ld func(*Link, *bio.Reader, string, int64, string), headType objabi.HeadType, f *bio.Reader, pkg string, length int64, pn string, file string) *Hostobj {
1035         isinternal := false
1036         for _, intpkg := range internalpkg {
1037                 if pkg == intpkg {
1038                         isinternal = true
1039                         break
1040                 }
1041         }
1042
1043         // DragonFly declares errno with __thread, which results in a symbol
1044         // type of R_386_TLS_GD or R_X86_64_TLSGD. The Go linker does not
1045         // currently know how to handle TLS relocations, hence we have to
1046         // force external linking for any libraries that link in code that
1047         // uses errno. This can be removed if the Go linker ever supports
1048         // these relocation types.
1049         if headType == objabi.Hdragonfly {
1050                 if pkg == "net" || pkg == "os/user" {
1051                         isinternal = false
1052                 }
1053         }
1054
1055         if !isinternal {
1056                 externalobj = true
1057         }
1058
1059         hostobj = append(hostobj, Hostobj{})
1060         h := &hostobj[len(hostobj)-1]
1061         h.ld = ld
1062         h.pkg = pkg
1063         h.pn = pn
1064         h.file = file
1065         h.off = f.Offset()
1066         h.length = length
1067         return h
1068 }
1069
1070 func hostobjs(ctxt *Link) {
1071         if ctxt.LinkMode != LinkInternal {
1072                 return
1073         }
1074         var h *Hostobj
1075
1076         for i := 0; i < len(hostobj); i++ {
1077                 h = &hostobj[i]
1078                 f, err := bio.Open(h.file)
1079                 if err != nil {
1080                         Exitf("cannot reopen %s: %v", h.pn, err)
1081                 }
1082
1083                 f.MustSeek(h.off, 0)
1084                 h.ld(ctxt, f, h.pkg, h.length, h.pn)
1085                 f.Close()
1086         }
1087 }
1088
1089 func hostlinksetup(ctxt *Link) {
1090         if ctxt.LinkMode != LinkExternal {
1091                 return
1092         }
1093
1094         // For external link, record that we need to tell the external linker -s,
1095         // and turn off -s internally: the external linker needs the symbol
1096         // information for its final link.
1097         debug_s = *FlagS
1098         *FlagS = false
1099
1100         // create temporary directory and arrange cleanup
1101         if *flagTmpdir == "" {
1102                 dir, err := ioutil.TempDir("", "go-link-")
1103                 if err != nil {
1104                         log.Fatal(err)
1105                 }
1106                 *flagTmpdir = dir
1107                 ownTmpDir = true
1108                 AtExit(func() {
1109                         ctxt.Out.Close()
1110                         os.RemoveAll(*flagTmpdir)
1111                 })
1112         }
1113
1114         // change our output to temporary object file
1115         if err := ctxt.Out.Close(); err != nil {
1116                 Exitf("error closing output file")
1117         }
1118         mayberemoveoutfile()
1119
1120         p := filepath.Join(*flagTmpdir, "go.o")
1121         if err := ctxt.Out.Open(p); err != nil {
1122                 Exitf("cannot create %s: %v", p, err)
1123         }
1124 }
1125
1126 // hostobjCopy creates a copy of the object files in hostobj in a
1127 // temporary directory.
1128 func hostobjCopy() (paths []string) {
1129         var wg sync.WaitGroup
1130         sema := make(chan struct{}, runtime.NumCPU()) // limit open file descriptors
1131         for i, h := range hostobj {
1132                 h := h
1133                 dst := filepath.Join(*flagTmpdir, fmt.Sprintf("%06d.o", i))
1134                 paths = append(paths, dst)
1135
1136                 wg.Add(1)
1137                 go func() {
1138                         sema <- struct{}{}
1139                         defer func() {
1140                                 <-sema
1141                                 wg.Done()
1142                         }()
1143                         f, err := os.Open(h.file)
1144                         if err != nil {
1145                                 Exitf("cannot reopen %s: %v", h.pn, err)
1146                         }
1147                         defer f.Close()
1148                         if _, err := f.Seek(h.off, 0); err != nil {
1149                                 Exitf("cannot seek %s: %v", h.pn, err)
1150                         }
1151
1152                         w, err := os.Create(dst)
1153                         if err != nil {
1154                                 Exitf("cannot create %s: %v", dst, err)
1155                         }
1156                         if _, err := io.CopyN(w, f, h.length); err != nil {
1157                                 Exitf("cannot write %s: %v", dst, err)
1158                         }
1159                         if err := w.Close(); err != nil {
1160                                 Exitf("cannot close %s: %v", dst, err)
1161                         }
1162                 }()
1163         }
1164         wg.Wait()
1165         return paths
1166 }
1167
1168 // writeGDBLinkerScript creates gcc linker script file in temp
1169 // directory. writeGDBLinkerScript returns created file path.
1170 // The script is used to work around gcc bug
1171 // (see https://golang.org/issue/20183 for details).
1172 func writeGDBLinkerScript() string {
1173         name := "fix_debug_gdb_scripts.ld"
1174         path := filepath.Join(*flagTmpdir, name)
1175         src := `SECTIONS
1176 {
1177   .debug_gdb_scripts BLOCK(__section_alignment__) (NOLOAD) :
1178   {
1179     *(.debug_gdb_scripts)
1180   }
1181 }
1182 INSERT AFTER .debug_types;
1183 `
1184         err := ioutil.WriteFile(path, []byte(src), 0666)
1185         if err != nil {
1186                 Errorf(nil, "WriteFile %s failed: %v", name, err)
1187         }
1188         return path
1189 }
1190
1191 // archive builds a .a archive from the hostobj object files.
1192 func (ctxt *Link) archive() {
1193         if ctxt.BuildMode != BuildModeCArchive {
1194                 return
1195         }
1196
1197         exitIfErrors()
1198
1199         if *flagExtar == "" {
1200                 *flagExtar = "ar"
1201         }
1202
1203         mayberemoveoutfile()
1204
1205         // Force the buffer to flush here so that external
1206         // tools will see a complete file.
1207         if err := ctxt.Out.Close(); err != nil {
1208                 Exitf("error closing %v", *flagOutfile)
1209         }
1210
1211         argv := []string{*flagExtar, "-q", "-c", "-s"}
1212         if ctxt.HeadType == objabi.Haix {
1213                 argv = append(argv, "-X64")
1214         }
1215         argv = append(argv, *flagOutfile)
1216         argv = append(argv, filepath.Join(*flagTmpdir, "go.o"))
1217         argv = append(argv, hostobjCopy()...)
1218
1219         if ctxt.Debugvlog != 0 {
1220                 ctxt.Logf("archive: %s\n", strings.Join(argv, " "))
1221         }
1222
1223         // If supported, use syscall.Exec() to invoke the archive command,
1224         // which should be the final remaining step needed for the link.
1225         // This will reduce peak RSS for the link (and speed up linking of
1226         // large applications), since when the archive command runs we
1227         // won't be holding onto all of the linker's live memory.
1228         if syscallExecSupported && !ownTmpDir {
1229                 runAtExitFuncs()
1230                 ctxt.execArchive(argv)
1231                 panic("should not get here")
1232         }
1233
1234         // Otherwise invoke 'ar' in the usual way (fork + exec).
1235         if out, err := exec.Command(argv[0], argv[1:]...).CombinedOutput(); err != nil {
1236                 Exitf("running %s failed: %v\n%s", argv[0], err, out)
1237         }
1238 }
1239
1240 func (ctxt *Link) hostlink() {
1241         if ctxt.LinkMode != LinkExternal || nerrors > 0 {
1242                 return
1243         }
1244         if ctxt.BuildMode == BuildModeCArchive {
1245                 return
1246         }
1247
1248         var argv []string
1249         argv = append(argv, ctxt.extld())
1250         argv = append(argv, hostlinkArchArgs(ctxt.Arch)...)
1251
1252         if *FlagS || debug_s {
1253                 if ctxt.HeadType == objabi.Hdarwin {
1254                         // Recent versions of macOS print
1255                         //      ld: warning: option -s is obsolete and being ignored
1256                         // so do not pass any arguments.
1257                 } else {
1258                         argv = append(argv, "-s")
1259                 }
1260         }
1261
1262         // On darwin, whether to combine DWARF into executable.
1263         // Only macOS supports unmapped segments such as our __DWARF segment.
1264         combineDwarf := ctxt.IsDarwin() && !*FlagS && !*FlagW && !debug_s && machoPlatform == PLATFORM_MACOS
1265
1266         switch ctxt.HeadType {
1267         case objabi.Hdarwin:
1268                 if combineDwarf {
1269                         // Leave room for DWARF combining.
1270                         // -headerpad is incompatible with -fembed-bitcode.
1271                         argv = append(argv, "-Wl,-headerpad,1144")
1272                 }
1273                 if ctxt.DynlinkingGo() && objabi.GOOS != "ios" {
1274                         // -flat_namespace is deprecated on iOS.
1275                         // It is useful for supporting plugins. We don't support plugins on iOS.
1276                         argv = append(argv, "-Wl,-flat_namespace")
1277                 }
1278                 if !combineDwarf {
1279                         argv = append(argv, "-Wl,-S") // suppress STAB (symbolic debugging) symbols
1280                 }
1281         case objabi.Hopenbsd:
1282                 argv = append(argv, "-Wl,-nopie")
1283                 argv = append(argv, "-pthread")
1284         case objabi.Hwindows:
1285                 if windowsgui {
1286                         argv = append(argv, "-mwindows")
1287                 } else {
1288                         argv = append(argv, "-mconsole")
1289                 }
1290                 // Mark as having awareness of terminal services, to avoid
1291                 // ancient compatibility hacks.
1292                 argv = append(argv, "-Wl,--tsaware")
1293
1294                 // Enable DEP
1295                 argv = append(argv, "-Wl,--nxcompat")
1296
1297                 argv = append(argv, fmt.Sprintf("-Wl,--major-os-version=%d", PeMinimumTargetMajorVersion))
1298                 argv = append(argv, fmt.Sprintf("-Wl,--minor-os-version=%d", PeMinimumTargetMinorVersion))
1299                 argv = append(argv, fmt.Sprintf("-Wl,--major-subsystem-version=%d", PeMinimumTargetMajorVersion))
1300                 argv = append(argv, fmt.Sprintf("-Wl,--minor-subsystem-version=%d", PeMinimumTargetMinorVersion))
1301         case objabi.Haix:
1302                 argv = append(argv, "-pthread")
1303                 // prevent ld to reorder .text functions to keep the same
1304                 // first/last functions for moduledata.
1305                 argv = append(argv, "-Wl,-bnoobjreorder")
1306                 // mcmodel=large is needed for every gcc generated files, but
1307                 // ld still need -bbigtoc in order to allow larger TOC.
1308                 argv = append(argv, "-mcmodel=large")
1309                 argv = append(argv, "-Wl,-bbigtoc")
1310         }
1311
1312         // Enable ASLR on Windows.
1313         addASLRargs := func(argv []string) []string {
1314                 // Enable ASLR.
1315                 argv = append(argv, "-Wl,--dynamicbase")
1316                 // enable high-entropy ASLR on 64-bit.
1317                 if ctxt.Arch.PtrSize >= 8 {
1318                         argv = append(argv, "-Wl,--high-entropy-va")
1319                 }
1320                 return argv
1321         }
1322
1323         switch ctxt.BuildMode {
1324         case BuildModeExe:
1325                 if ctxt.HeadType == objabi.Hdarwin {
1326                         if machoPlatform == PLATFORM_MACOS && ctxt.IsAMD64() {
1327                                 argv = append(argv, "-Wl,-no_pie")
1328                                 argv = append(argv, "-Wl,-pagezero_size,4000000")
1329                         }
1330                 }
1331         case BuildModePIE:
1332                 switch ctxt.HeadType {
1333                 case objabi.Hdarwin, objabi.Haix:
1334                 case objabi.Hwindows:
1335                         argv = addASLRargs(argv)
1336                 default:
1337                         // ELF.
1338                         if ctxt.UseRelro() {
1339                                 argv = append(argv, "-Wl,-z,relro")
1340                         }
1341                         argv = append(argv, "-pie")
1342                 }
1343         case BuildModeCShared:
1344                 if ctxt.HeadType == objabi.Hdarwin {
1345                         argv = append(argv, "-dynamiclib")
1346                 } else {
1347                         // ELF.
1348                         argv = append(argv, "-Wl,-Bsymbolic")
1349                         if ctxt.UseRelro() {
1350                                 argv = append(argv, "-Wl,-z,relro")
1351                         }
1352                         argv = append(argv, "-shared")
1353                         if ctxt.HeadType == objabi.Hwindows {
1354                                 if *flagAslr {
1355                                         argv = addASLRargs(argv)
1356                                 }
1357                         } else {
1358                                 // Pass -z nodelete to mark the shared library as
1359                                 // non-closeable: a dlclose will do nothing.
1360                                 argv = append(argv, "-Wl,-z,nodelete")
1361                         }
1362                 }
1363         case BuildModeShared:
1364                 if ctxt.UseRelro() {
1365                         argv = append(argv, "-Wl,-z,relro")
1366                 }
1367                 argv = append(argv, "-shared")
1368         case BuildModePlugin:
1369                 if ctxt.HeadType == objabi.Hdarwin {
1370                         argv = append(argv, "-dynamiclib")
1371                 } else {
1372                         if ctxt.UseRelro() {
1373                                 argv = append(argv, "-Wl,-z,relro")
1374                         }
1375                         argv = append(argv, "-shared")
1376                 }
1377         }
1378
1379         var altLinker string
1380         if ctxt.IsELF && ctxt.DynlinkingGo() {
1381                 // We force all symbol resolution to be done at program startup
1382                 // because lazy PLT resolution can use large amounts of stack at
1383                 // times we cannot allow it to do so.
1384                 argv = append(argv, "-Wl,-znow")
1385
1386                 // Do not let the host linker generate COPY relocations. These
1387                 // can move symbols out of sections that rely on stable offsets
1388                 // from the beginning of the section (like sym.STYPE).
1389                 argv = append(argv, "-Wl,-znocopyreloc")
1390
1391                 if objabi.GOOS == "android" {
1392                         // Use lld to avoid errors from default linker (issue #38838)
1393                         altLinker = "lld"
1394                 }
1395
1396                 if ctxt.Arch.InFamily(sys.ARM, sys.ARM64) && objabi.GOOS == "linux" {
1397                         // On ARM, the GNU linker will generate COPY relocations
1398                         // even with -znocopyreloc set.
1399                         // https://sourceware.org/bugzilla/show_bug.cgi?id=19962
1400                         //
1401                         // On ARM64, the GNU linker will fail instead of
1402                         // generating COPY relocations.
1403                         //
1404                         // In both cases, switch to gold.
1405                         altLinker = "gold"
1406
1407                         // If gold is not installed, gcc will silently switch
1408                         // back to ld.bfd. So we parse the version information
1409                         // and provide a useful error if gold is missing.
1410                         cmd := exec.Command(*flagExtld, "-fuse-ld=gold", "-Wl,--version")
1411                         if out, err := cmd.CombinedOutput(); err == nil {
1412                                 if !bytes.Contains(out, []byte("GNU gold")) {
1413                                         log.Fatalf("ARM external linker must be gold (issue #15696), but is not: %s", out)
1414                                 }
1415                         }
1416                 }
1417         }
1418         if ctxt.Arch.Family == sys.ARM64 && objabi.GOOS == "freebsd" {
1419                 // Switch to ld.bfd on freebsd/arm64.
1420                 altLinker = "bfd"
1421
1422                 // Provide a useful error if ld.bfd is missing.
1423                 cmd := exec.Command(*flagExtld, "-fuse-ld=bfd", "-Wl,--version")
1424                 if out, err := cmd.CombinedOutput(); err == nil {
1425                         if !bytes.Contains(out, []byte("GNU ld")) {
1426                                 log.Fatalf("ARM64 external linker must be ld.bfd (issue #35197), please install devel/binutils")
1427                         }
1428                 }
1429         }
1430         if altLinker != "" {
1431                 argv = append(argv, "-fuse-ld="+altLinker)
1432         }
1433
1434         if ctxt.IsELF && len(buildinfo) > 0 {
1435                 argv = append(argv, fmt.Sprintf("-Wl,--build-id=0x%x", buildinfo))
1436         }
1437
1438         // On Windows, given -o foo, GCC will append ".exe" to produce
1439         // "foo.exe".  We have decided that we want to honor the -o
1440         // option. To make this work, we append a '.' so that GCC
1441         // will decide that the file already has an extension. We
1442         // only want to do this when producing a Windows output file
1443         // on a Windows host.
1444         outopt := *flagOutfile
1445         if objabi.GOOS == "windows" && runtime.GOOS == "windows" && filepath.Ext(outopt) == "" {
1446                 outopt += "."
1447         }
1448         argv = append(argv, "-o")
1449         argv = append(argv, outopt)
1450
1451         if rpath.val != "" {
1452                 argv = append(argv, fmt.Sprintf("-Wl,-rpath,%s", rpath.val))
1453         }
1454
1455         // Force global symbols to be exported for dlopen, etc.
1456         if ctxt.IsELF {
1457                 argv = append(argv, "-rdynamic")
1458         }
1459         if ctxt.HeadType == objabi.Haix {
1460                 fileName := xcoffCreateExportFile(ctxt)
1461                 argv = append(argv, "-Wl,-bE:"+fileName)
1462         }
1463
1464         if strings.Contains(argv[0], "clang") {
1465                 argv = append(argv, "-Qunused-arguments")
1466         }
1467
1468         const compressDWARF = "-Wl,--compress-debug-sections=zlib-gnu"
1469         if ctxt.compressDWARF && linkerFlagSupported(ctxt.Arch, argv[0], altLinker, compressDWARF) {
1470                 argv = append(argv, compressDWARF)
1471         }
1472
1473         argv = append(argv, filepath.Join(*flagTmpdir, "go.o"))
1474         argv = append(argv, hostobjCopy()...)
1475         if ctxt.HeadType == objabi.Haix {
1476                 // We want to have C files after Go files to remove
1477                 // trampolines csects made by ld.
1478                 argv = append(argv, "-nostartfiles")
1479                 argv = append(argv, "/lib/crt0_64.o")
1480
1481                 extld := ctxt.extld()
1482                 // Get starting files.
1483                 getPathFile := func(file string) string {
1484                         args := []string{"-maix64", "--print-file-name=" + file}
1485                         out, err := exec.Command(extld, args...).CombinedOutput()
1486                         if err != nil {
1487                                 log.Fatalf("running %s failed: %v\n%s", extld, err, out)
1488                         }
1489                         return strings.Trim(string(out), "\n")
1490                 }
1491                 argv = append(argv, getPathFile("crtcxa.o"))
1492                 argv = append(argv, getPathFile("crtdbase.o"))
1493         }
1494
1495         if ctxt.linkShared {
1496                 seenDirs := make(map[string]bool)
1497                 seenLibs := make(map[string]bool)
1498                 addshlib := func(path string) {
1499                         dir, base := filepath.Split(path)
1500                         if !seenDirs[dir] {
1501                                 argv = append(argv, "-L"+dir)
1502                                 if !rpath.set {
1503                                         argv = append(argv, "-Wl,-rpath="+dir)
1504                                 }
1505                                 seenDirs[dir] = true
1506                         }
1507                         base = strings.TrimSuffix(base, ".so")
1508                         base = strings.TrimPrefix(base, "lib")
1509                         if !seenLibs[base] {
1510                                 argv = append(argv, "-l"+base)
1511                                 seenLibs[base] = true
1512                         }
1513                 }
1514                 for _, shlib := range ctxt.Shlibs {
1515                         addshlib(shlib.Path)
1516                         for _, dep := range shlib.Deps {
1517                                 if dep == "" {
1518                                         continue
1519                                 }
1520                                 libpath := findshlib(ctxt, dep)
1521                                 if libpath != "" {
1522                                         addshlib(libpath)
1523                                 }
1524                         }
1525                 }
1526         }
1527
1528         // clang, unlike GCC, passes -rdynamic to the linker
1529         // even when linking with -static, causing a linker
1530         // error when using GNU ld. So take out -rdynamic if
1531         // we added it. We do it in this order, rather than
1532         // only adding -rdynamic later, so that -*extldflags
1533         // can override -rdynamic without using -static.
1534         checkStatic := func(arg string) {
1535                 if ctxt.IsELF && arg == "-static" {
1536                         for i := range argv {
1537                                 if argv[i] == "-rdynamic" {
1538                                         argv[i] = "-static"
1539                                 }
1540                         }
1541                 }
1542         }
1543
1544         for _, p := range ldflag {
1545                 argv = append(argv, p)
1546                 checkStatic(p)
1547         }
1548
1549         // When building a program with the default -buildmode=exe the
1550         // gc compiler generates code requires DT_TEXTREL in a
1551         // position independent executable (PIE). On systems where the
1552         // toolchain creates PIEs by default, and where DT_TEXTREL
1553         // does not work, the resulting programs will not run. See
1554         // issue #17847. To avoid this problem pass -no-pie to the
1555         // toolchain if it is supported.
1556         if ctxt.BuildMode == BuildModeExe && !ctxt.linkShared && !(ctxt.IsDarwin() && ctxt.IsARM64()) {
1557                 // GCC uses -no-pie, clang uses -nopie.
1558                 for _, nopie := range []string{"-no-pie", "-nopie"} {
1559                         if linkerFlagSupported(ctxt.Arch, argv[0], altLinker, nopie) {
1560                                 argv = append(argv, nopie)
1561                                 break
1562                         }
1563                 }
1564         }
1565
1566         for _, p := range strings.Fields(*flagExtldflags) {
1567                 argv = append(argv, p)
1568                 checkStatic(p)
1569         }
1570         if ctxt.HeadType == objabi.Hwindows {
1571                 // Determine which linker we're using. Add in the extldflags in
1572                 // case used has specified "-fuse-ld=...".
1573                 cmd := exec.Command(*flagExtld, *flagExtldflags, "-Wl,--version")
1574                 usingLLD := false
1575                 if out, err := cmd.CombinedOutput(); err == nil {
1576                         if bytes.Contains(out, []byte("LLD ")) {
1577                                 usingLLD = true
1578                         }
1579                 }
1580
1581                 // use gcc linker script to work around gcc bug
1582                 // (see https://golang.org/issue/20183 for details).
1583                 if !usingLLD {
1584                         p := writeGDBLinkerScript()
1585                         argv = append(argv, "-Wl,-T,"+p)
1586                 }
1587                 // libmingw32 and libmingwex have some inter-dependencies,
1588                 // so must use linker groups.
1589                 argv = append(argv, "-Wl,--start-group", "-lmingwex", "-lmingw32", "-Wl,--end-group")
1590                 argv = append(argv, peimporteddlls()...)
1591         }
1592
1593         if ctxt.Debugvlog != 0 {
1594                 ctxt.Logf("host link:")
1595                 for _, v := range argv {
1596                         ctxt.Logf(" %q", v)
1597                 }
1598                 ctxt.Logf("\n")
1599         }
1600
1601         out, err := exec.Command(argv[0], argv[1:]...).CombinedOutput()
1602         if err != nil {
1603                 Exitf("running %s failed: %v\n%s", argv[0], err, out)
1604         }
1605
1606         // Filter out useless linker warnings caused by bugs outside Go.
1607         // See also cmd/go/internal/work/exec.go's gccld method.
1608         var save [][]byte
1609         var skipLines int
1610         for _, line := range bytes.SplitAfter(out, []byte("\n")) {
1611                 // golang.org/issue/26073 - Apple Xcode bug
1612                 if bytes.Contains(line, []byte("ld: warning: text-based stub file")) {
1613                         continue
1614                 }
1615
1616                 if skipLines > 0 {
1617                         skipLines--
1618                         continue
1619                 }
1620
1621                 // Remove TOC overflow warning on AIX.
1622                 if bytes.Contains(line, []byte("ld: 0711-783")) {
1623                         skipLines = 2
1624                         continue
1625                 }
1626
1627                 save = append(save, line)
1628         }
1629         out = bytes.Join(save, nil)
1630
1631         if len(out) > 0 {
1632                 // always print external output even if the command is successful, so that we don't
1633                 // swallow linker warnings (see https://golang.org/issue/17935).
1634                 ctxt.Logf("%s", out)
1635         }
1636
1637         if combineDwarf {
1638                 dsym := filepath.Join(*flagTmpdir, "go.dwarf")
1639                 if out, err := exec.Command("xcrun", "dsymutil", "-f", *flagOutfile, "-o", dsym).CombinedOutput(); err != nil {
1640                         Exitf("%s: running dsymutil failed: %v\n%s", os.Args[0], err, out)
1641                 }
1642                 // Remove STAB (symbolic debugging) symbols after we are done with them (by dsymutil).
1643                 // They contain temporary file paths and make the build not reproducible.
1644                 if out, err := exec.Command("xcrun", "strip", "-S", *flagOutfile).CombinedOutput(); err != nil {
1645                         Exitf("%s: running strip failed: %v\n%s", os.Args[0], err, out)
1646                 }
1647                 // Skip combining if `dsymutil` didn't generate a file. See #11994.
1648                 if _, err := os.Stat(dsym); os.IsNotExist(err) {
1649                         return
1650                 }
1651                 // For os.Rename to work reliably, must be in same directory as outfile.
1652                 combinedOutput := *flagOutfile + "~"
1653                 exef, err := os.Open(*flagOutfile)
1654                 if err != nil {
1655                         Exitf("%s: combining dwarf failed: %v", os.Args[0], err)
1656                 }
1657                 defer exef.Close()
1658                 exem, err := macho.NewFile(exef)
1659                 if err != nil {
1660                         Exitf("%s: parsing Mach-O header failed: %v", os.Args[0], err)
1661                 }
1662                 if err := machoCombineDwarf(ctxt, exef, exem, dsym, combinedOutput); err != nil {
1663                         Exitf("%s: combining dwarf failed: %v", os.Args[0], err)
1664                 }
1665                 os.Remove(*flagOutfile)
1666                 if err := os.Rename(combinedOutput, *flagOutfile); err != nil {
1667                         Exitf("%s: %v", os.Args[0], err)
1668                 }
1669         }
1670         if ctxt.NeedCodeSign() {
1671                 err := machoCodeSign(ctxt, *flagOutfile)
1672                 if err != nil {
1673                         Exitf("%s: code signing failed: %v", os.Args[0], err)
1674                 }
1675         }
1676 }
1677
1678 var createTrivialCOnce sync.Once
1679
1680 func linkerFlagSupported(arch *sys.Arch, linker, altLinker, flag string) bool {
1681         createTrivialCOnce.Do(func() {
1682                 src := filepath.Join(*flagTmpdir, "trivial.c")
1683                 if err := ioutil.WriteFile(src, []byte("int main() { return 0; }"), 0666); err != nil {
1684                         Errorf(nil, "WriteFile trivial.c failed: %v", err)
1685                 }
1686         })
1687
1688         flagsWithNextArgSkip := []string{
1689                 "-F",
1690                 "-l",
1691                 "-L",
1692                 "-framework",
1693                 "-Wl,-framework",
1694                 "-Wl,-rpath",
1695                 "-Wl,-undefined",
1696         }
1697         flagsWithNextArgKeep := []string{
1698                 "-arch",
1699                 "-isysroot",
1700                 "--sysroot",
1701                 "-target",
1702         }
1703         prefixesToKeep := []string{
1704                 "-f",
1705                 "-m",
1706                 "-p",
1707                 "-Wl,",
1708                 "-arch",
1709                 "-isysroot",
1710                 "--sysroot",
1711                 "-target",
1712         }
1713
1714         flags := hostlinkArchArgs(arch)
1715         keep := false
1716         skip := false
1717         extldflags := strings.Fields(*flagExtldflags)
1718         for _, f := range append(extldflags, ldflag...) {
1719                 if keep {
1720                         flags = append(flags, f)
1721                         keep = false
1722                 } else if skip {
1723                         skip = false
1724                 } else if f == "" || f[0] != '-' {
1725                 } else if contains(flagsWithNextArgSkip, f) {
1726                         skip = true
1727                 } else if contains(flagsWithNextArgKeep, f) {
1728                         flags = append(flags, f)
1729                         keep = true
1730                 } else {
1731                         for _, p := range prefixesToKeep {
1732                                 if strings.HasPrefix(f, p) {
1733                                         flags = append(flags, f)
1734                                         break
1735                                 }
1736                         }
1737                 }
1738         }
1739
1740         if altLinker != "" {
1741                 flags = append(flags, "-fuse-ld="+altLinker)
1742         }
1743         flags = append(flags, flag, "trivial.c")
1744
1745         cmd := exec.Command(linker, flags...)
1746         cmd.Dir = *flagTmpdir
1747         cmd.Env = append([]string{"LC_ALL=C"}, os.Environ()...)
1748         out, err := cmd.CombinedOutput()
1749         // GCC says "unrecognized command line option ‘-no-pie’"
1750         // clang says "unknown argument: '-no-pie'"
1751         return err == nil && !bytes.Contains(out, []byte("unrecognized")) && !bytes.Contains(out, []byte("unknown"))
1752 }
1753
1754 // hostlinkArchArgs returns arguments to pass to the external linker
1755 // based on the architecture.
1756 func hostlinkArchArgs(arch *sys.Arch) []string {
1757         switch arch.Family {
1758         case sys.I386:
1759                 return []string{"-m32"}
1760         case sys.AMD64:
1761                 if objabi.GOOS == "darwin" {
1762                         return []string{"-arch", "x86_64", "-m64"}
1763                 }
1764                 return []string{"-m64"}
1765         case sys.S390X:
1766                 return []string{"-m64"}
1767         case sys.ARM:
1768                 return []string{"-marm"}
1769         case sys.ARM64:
1770                 if objabi.GOOS == "darwin" {
1771                         return []string{"-arch", "arm64"}
1772                 }
1773         case sys.MIPS64:
1774                 return []string{"-mabi=64"}
1775         case sys.MIPS:
1776                 return []string{"-mabi=32"}
1777         case sys.PPC64:
1778                 if objabi.GOOS == "aix" {
1779                         return []string{"-maix64"}
1780                 } else {
1781                         return []string{"-m64"}
1782                 }
1783
1784         }
1785         return nil
1786 }
1787
1788 // ldobj loads an input object. If it is a host object (an object
1789 // compiled by a non-Go compiler) it returns the Hostobj pointer. If
1790 // it is a Go object, it returns nil.
1791 func ldobj(ctxt *Link, f *bio.Reader, lib *sym.Library, length int64, pn string, file string) *Hostobj {
1792         pkg := objabi.PathToPrefix(lib.Pkg)
1793
1794         eof := f.Offset() + length
1795         start := f.Offset()
1796         c1 := bgetc(f)
1797         c2 := bgetc(f)
1798         c3 := bgetc(f)
1799         c4 := bgetc(f)
1800         f.MustSeek(start, 0)
1801
1802         unit := &sym.CompilationUnit{Lib: lib}
1803         lib.Units = append(lib.Units, unit)
1804
1805         magic := uint32(c1)<<24 | uint32(c2)<<16 | uint32(c3)<<8 | uint32(c4)
1806         if magic == 0x7f454c46 { // \x7F E L F
1807                 ldelf := func(ctxt *Link, f *bio.Reader, pkg string, length int64, pn string) {
1808                         textp, flags, err := loadelf.Load(ctxt.loader, ctxt.Arch, ctxt.IncVersion(), f, pkg, length, pn, ehdr.Flags)
1809                         if err != nil {
1810                                 Errorf(nil, "%v", err)
1811                                 return
1812                         }
1813                         ehdr.Flags = flags
1814                         ctxt.Textp = append(ctxt.Textp, textp...)
1815                 }
1816                 return ldhostobj(ldelf, ctxt.HeadType, f, pkg, length, pn, file)
1817         }
1818
1819         if magic&^1 == 0xfeedface || magic&^0x01000000 == 0xcefaedfe {
1820                 ldmacho := func(ctxt *Link, f *bio.Reader, pkg string, length int64, pn string) {
1821                         textp, err := loadmacho.Load(ctxt.loader, ctxt.Arch, ctxt.IncVersion(), f, pkg, length, pn)
1822                         if err != nil {
1823                                 Errorf(nil, "%v", err)
1824                                 return
1825                         }
1826                         ctxt.Textp = append(ctxt.Textp, textp...)
1827                 }
1828                 return ldhostobj(ldmacho, ctxt.HeadType, f, pkg, length, pn, file)
1829         }
1830
1831         if /* x86 */ c1 == 0x4c && c2 == 0x01 || /* x86_64 */ c1 == 0x64 && c2 == 0x86 || /* armv7 */ c1 == 0xc4 && c2 == 0x01 {
1832                 ldpe := func(ctxt *Link, f *bio.Reader, pkg string, length int64, pn string) {
1833                         textp, rsrc, err := loadpe.Load(ctxt.loader, ctxt.Arch, ctxt.IncVersion(), f, pkg, length, pn)
1834                         if err != nil {
1835                                 Errorf(nil, "%v", err)
1836                                 return
1837                         }
1838                         if len(rsrc) != 0 {
1839                                 setpersrc(ctxt, rsrc)
1840                         }
1841                         ctxt.Textp = append(ctxt.Textp, textp...)
1842                 }
1843                 return ldhostobj(ldpe, ctxt.HeadType, f, pkg, length, pn, file)
1844         }
1845
1846         if c1 == 0x01 && (c2 == 0xD7 || c2 == 0xF7) {
1847                 ldxcoff := func(ctxt *Link, f *bio.Reader, pkg string, length int64, pn string) {
1848                         textp, err := loadxcoff.Load(ctxt.loader, ctxt.Arch, ctxt.IncVersion(), f, pkg, length, pn)
1849                         if err != nil {
1850                                 Errorf(nil, "%v", err)
1851                                 return
1852                         }
1853                         ctxt.Textp = append(ctxt.Textp, textp...)
1854                 }
1855                 return ldhostobj(ldxcoff, ctxt.HeadType, f, pkg, length, pn, file)
1856         }
1857
1858         /* check the header */
1859         line, err := f.ReadString('\n')
1860         if err != nil {
1861                 Errorf(nil, "truncated object file: %s: %v", pn, err)
1862                 return nil
1863         }
1864
1865         if !strings.HasPrefix(line, "go object ") {
1866                 if strings.HasSuffix(pn, ".go") {
1867                         Exitf("%s: uncompiled .go source file", pn)
1868                         return nil
1869                 }
1870
1871                 if line == ctxt.Arch.Name {
1872                         // old header format: just $GOOS
1873                         Errorf(nil, "%s: stale object file", pn)
1874                         return nil
1875                 }
1876
1877                 Errorf(nil, "%s: not an object file", pn)
1878                 return nil
1879         }
1880
1881         // First, check that the basic GOOS, GOARCH, and Version match.
1882         t := fmt.Sprintf("%s %s %s ", objabi.GOOS, objabi.GOARCH, objabi.Version)
1883
1884         line = strings.TrimRight(line, "\n")
1885         if !strings.HasPrefix(line[10:]+" ", t) && !*flagF {
1886                 Errorf(nil, "%s: object is [%s] expected [%s]", pn, line[10:], t)
1887                 return nil
1888         }
1889
1890         // Second, check that longer lines match each other exactly,
1891         // so that the Go compiler and write additional information
1892         // that must be the same from run to run.
1893         if len(line) >= len(t)+10 {
1894                 if theline == "" {
1895                         theline = line[10:]
1896                 } else if theline != line[10:] {
1897                         Errorf(nil, "%s: object is [%s] expected [%s]", pn, line[10:], theline)
1898                         return nil
1899                 }
1900         }
1901
1902         // Skip over exports and other info -- ends with \n!\n.
1903         //
1904         // Note: It's possible for "\n!\n" to appear within the binary
1905         // package export data format. To avoid truncating the package
1906         // definition prematurely (issue 21703), we keep track of
1907         // how many "$$" delimiters we've seen.
1908
1909         import0 := f.Offset()
1910
1911         c1 = '\n' // the last line ended in \n
1912         c2 = bgetc(f)
1913         c3 = bgetc(f)
1914         markers := 0
1915         for {
1916                 if c1 == '\n' {
1917                         if markers%2 == 0 && c2 == '!' && c3 == '\n' {
1918                                 break
1919                         }
1920                         if c2 == '$' && c3 == '$' {
1921                                 markers++
1922                         }
1923                 }
1924
1925                 c1 = c2
1926                 c2 = c3
1927                 c3 = bgetc(f)
1928                 if c3 == -1 {
1929                         Errorf(nil, "truncated object file: %s", pn)
1930                         return nil
1931                 }
1932         }
1933
1934         import1 := f.Offset()
1935
1936         f.MustSeek(import0, 0)
1937         ldpkg(ctxt, f, lib, import1-import0-2, pn) // -2 for !\n
1938         f.MustSeek(import1, 0)
1939
1940         fingerprint := ctxt.loader.Preload(ctxt.IncVersion(), f, lib, unit, eof-f.Offset())
1941         if !fingerprint.IsZero() { // Assembly objects don't have fingerprints. Ignore them.
1942                 // Check fingerprint, to ensure the importing and imported packages
1943                 // have consistent view of symbol indices.
1944                 // Normally the go command should ensure this. But in case something
1945                 // goes wrong, it could lead to obscure bugs like run-time crash.
1946                 // Check it here to be sure.
1947                 if lib.Fingerprint.IsZero() { // Not yet imported. Update its fingerprint.
1948                         lib.Fingerprint = fingerprint
1949                 }
1950                 checkFingerprint(lib, fingerprint, lib.Srcref, lib.Fingerprint)
1951         }
1952
1953         addImports(ctxt, lib, pn)
1954         return nil
1955 }
1956
1957 func checkFingerprint(lib *sym.Library, libfp goobj.FingerprintType, src string, srcfp goobj.FingerprintType) {
1958         if libfp != srcfp {
1959                 Exitf("fingerprint mismatch: %s has %x, import from %s expecting %x", lib, libfp, src, srcfp)
1960         }
1961 }
1962
1963 func readelfsymboldata(ctxt *Link, f *elf.File, sym *elf.Symbol) []byte {
1964         data := make([]byte, sym.Size)
1965         sect := f.Sections[sym.Section]
1966         if sect.Type != elf.SHT_PROGBITS && sect.Type != elf.SHT_NOTE {
1967                 Errorf(nil, "reading %s from non-data section", sym.Name)
1968         }
1969         n, err := sect.ReadAt(data, int64(sym.Value-sect.Addr))
1970         if uint64(n) != sym.Size {
1971                 Errorf(nil, "reading contents of %s: %v", sym.Name, err)
1972         }
1973         return data
1974 }
1975
1976 func readwithpad(r io.Reader, sz int32) ([]byte, error) {
1977         data := make([]byte, Rnd(int64(sz), 4))
1978         _, err := io.ReadFull(r, data)
1979         if err != nil {
1980                 return nil, err
1981         }
1982         data = data[:sz]
1983         return data, nil
1984 }
1985
1986 func readnote(f *elf.File, name []byte, typ int32) ([]byte, error) {
1987         for _, sect := range f.Sections {
1988                 if sect.Type != elf.SHT_NOTE {
1989                         continue
1990                 }
1991                 r := sect.Open()
1992                 for {
1993                         var namesize, descsize, noteType int32
1994                         err := binary.Read(r, f.ByteOrder, &namesize)
1995                         if err != nil {
1996                                 if err == io.EOF {
1997                                         break
1998                                 }
1999                                 return nil, fmt.Errorf("read namesize failed: %v", err)
2000                         }
2001                         err = binary.Read(r, f.ByteOrder, &descsize)
2002                         if err != nil {
2003                                 return nil, fmt.Errorf("read descsize failed: %v", err)
2004                         }
2005                         err = binary.Read(r, f.ByteOrder, &noteType)
2006                         if err != nil {
2007                                 return nil, fmt.Errorf("read type failed: %v", err)
2008                         }
2009                         noteName, err := readwithpad(r, namesize)
2010                         if err != nil {
2011                                 return nil, fmt.Errorf("read name failed: %v", err)
2012                         }
2013                         desc, err := readwithpad(r, descsize)
2014                         if err != nil {
2015                                 return nil, fmt.Errorf("read desc failed: %v", err)
2016                         }
2017                         if string(name) == string(noteName) && typ == noteType {
2018                                 return desc, nil
2019                         }
2020                 }
2021         }
2022         return nil, nil
2023 }
2024
2025 func findshlib(ctxt *Link, shlib string) string {
2026         if filepath.IsAbs(shlib) {
2027                 return shlib
2028         }
2029         for _, libdir := range ctxt.Libdir {
2030                 libpath := filepath.Join(libdir, shlib)
2031                 if _, err := os.Stat(libpath); err == nil {
2032                         return libpath
2033                 }
2034         }
2035         Errorf(nil, "cannot find shared library: %s", shlib)
2036         return ""
2037 }
2038
2039 func ldshlibsyms(ctxt *Link, shlib string) {
2040         var libpath string
2041         if filepath.IsAbs(shlib) {
2042                 libpath = shlib
2043                 shlib = filepath.Base(shlib)
2044         } else {
2045                 libpath = findshlib(ctxt, shlib)
2046                 if libpath == "" {
2047                         return
2048                 }
2049         }
2050         for _, processedlib := range ctxt.Shlibs {
2051                 if processedlib.Path == libpath {
2052                         return
2053                 }
2054         }
2055         if ctxt.Debugvlog > 1 {
2056                 ctxt.Logf("ldshlibsyms: found library with name %s at %s\n", shlib, libpath)
2057         }
2058
2059         f, err := elf.Open(libpath)
2060         if err != nil {
2061                 Errorf(nil, "cannot open shared library: %s", libpath)
2062                 return
2063         }
2064         // Keep the file open as decodetypeGcprog needs to read from it.
2065         // TODO: fix. Maybe mmap the file.
2066         //defer f.Close()
2067
2068         hash, err := readnote(f, ELF_NOTE_GO_NAME, ELF_NOTE_GOABIHASH_TAG)
2069         if err != nil {
2070                 Errorf(nil, "cannot read ABI hash from shared library %s: %v", libpath, err)
2071                 return
2072         }
2073
2074         depsbytes, err := readnote(f, ELF_NOTE_GO_NAME, ELF_NOTE_GODEPS_TAG)
2075         if err != nil {
2076                 Errorf(nil, "cannot read dep list from shared library %s: %v", libpath, err)
2077                 return
2078         }
2079         var deps []string
2080         for _, dep := range strings.Split(string(depsbytes), "\n") {
2081                 if dep == "" {
2082                         continue
2083                 }
2084                 if !filepath.IsAbs(dep) {
2085                         // If the dep can be interpreted as a path relative to the shlib
2086                         // in which it was found, do that. Otherwise, we will leave it
2087                         // to be resolved by libdir lookup.
2088                         abs := filepath.Join(filepath.Dir(libpath), dep)
2089                         if _, err := os.Stat(abs); err == nil {
2090                                 dep = abs
2091                         }
2092                 }
2093                 deps = append(deps, dep)
2094         }
2095
2096         syms, err := f.DynamicSymbols()
2097         if err != nil {
2098                 Errorf(nil, "cannot read symbols from shared library: %s", libpath)
2099                 return
2100         }
2101
2102         // collect text symbol ABI versions.
2103         symabi := make(map[string]int) // map (unmangled) symbol name to version
2104         if *flagAbiWrap {
2105                 for _, elfsym := range syms {
2106                         if elf.ST_TYPE(elfsym.Info) != elf.STT_FUNC {
2107                                 continue
2108                         }
2109                         // Demangle the name. Keep in sync with symtab.go:putelfsym.
2110                         if strings.HasSuffix(elfsym.Name, ".abiinternal") {
2111                                 // ABIInternal symbol has mangled name, so the primary symbol is ABI0.
2112                                 symabi[strings.TrimSuffix(elfsym.Name, ".abiinternal")] = 0
2113                         }
2114                         if strings.HasSuffix(elfsym.Name, ".abi0") {
2115                                 // ABI0 symbol has mangled name, so the primary symbol is ABIInternal.
2116                                 symabi[strings.TrimSuffix(elfsym.Name, ".abi0")] = sym.SymVerABIInternal
2117                         }
2118                 }
2119         }
2120
2121         for _, elfsym := range syms {
2122                 if elf.ST_TYPE(elfsym.Info) == elf.STT_NOTYPE || elf.ST_TYPE(elfsym.Info) == elf.STT_SECTION {
2123                         continue
2124                 }
2125
2126                 // Symbols whose names start with "type." are compiler
2127                 // generated, so make functions with that prefix internal.
2128                 ver := 0
2129                 symname := elfsym.Name // (unmangled) symbol name
2130                 if elf.ST_TYPE(elfsym.Info) == elf.STT_FUNC && strings.HasPrefix(elfsym.Name, "type.") {
2131                         ver = sym.SymVerABIInternal
2132                 } else if *flagAbiWrap && elf.ST_TYPE(elfsym.Info) == elf.STT_FUNC {
2133                         if strings.HasSuffix(elfsym.Name, ".abiinternal") {
2134                                 ver = sym.SymVerABIInternal
2135                                 symname = strings.TrimSuffix(elfsym.Name, ".abiinternal")
2136                         } else if strings.HasSuffix(elfsym.Name, ".abi0") {
2137                                 ver = 0
2138                                 symname = strings.TrimSuffix(elfsym.Name, ".abi0")
2139                         } else if abi, ok := symabi[elfsym.Name]; ok {
2140                                 ver = abi
2141                         }
2142                 }
2143
2144                 l := ctxt.loader
2145                 s := l.LookupOrCreateSym(symname, ver)
2146
2147                 // Because loadlib above loads all .a files before loading
2148                 // any shared libraries, any non-dynimport symbols we find
2149                 // that duplicate symbols already loaded should be ignored
2150                 // (the symbols from the .a files "win").
2151                 if l.SymType(s) != 0 && l.SymType(s) != sym.SDYNIMPORT {
2152                         continue
2153                 }
2154                 su := l.MakeSymbolUpdater(s)
2155                 su.SetType(sym.SDYNIMPORT)
2156                 l.SetSymElfType(s, elf.ST_TYPE(elfsym.Info))
2157                 su.SetSize(int64(elfsym.Size))
2158                 if elfsym.Section != elf.SHN_UNDEF {
2159                         // Set .File for the library that actually defines the symbol.
2160                         l.SetSymPkg(s, libpath)
2161
2162                         // The decodetype_* functions in decodetype.go need access to
2163                         // the type data.
2164                         sname := l.SymName(s)
2165                         if strings.HasPrefix(sname, "type.") && !strings.HasPrefix(sname, "type..") {
2166                                 su.SetData(readelfsymboldata(ctxt, f, &elfsym))
2167                         }
2168                 }
2169
2170                 if symname != elfsym.Name {
2171                         l.SetSymExtname(s, elfsym.Name)
2172                 }
2173
2174                 // For function symbols, we don't know what ABI is
2175                 // available, so alias it under both ABIs.
2176                 //
2177                 // TODO(austin): This is almost certainly wrong once
2178                 // the ABIs are actually different. We might have to
2179                 // mangle Go function names in the .so to include the
2180                 // ABI.
2181                 if elf.ST_TYPE(elfsym.Info) == elf.STT_FUNC && ver == 0 {
2182                         if *flagAbiWrap {
2183                                 if _, ok := symabi[symname]; ok {
2184                                         continue // only use alias for functions w/o ABI wrappers
2185                                 }
2186                         }
2187                         alias := ctxt.loader.LookupOrCreateSym(symname, sym.SymVerABIInternal)
2188                         if l.SymType(alias) != 0 {
2189                                 continue
2190                         }
2191                         su := l.MakeSymbolUpdater(alias)
2192                         su.SetType(sym.SABIALIAS)
2193                         r, _ := su.AddRel(0) // type doesn't matter
2194                         r.SetSym(s)
2195                 }
2196         }
2197         ctxt.Shlibs = append(ctxt.Shlibs, Shlib{Path: libpath, Hash: hash, Deps: deps, File: f})
2198 }
2199
2200 func addsection(ldr *loader.Loader, arch *sys.Arch, seg *sym.Segment, name string, rwx int) *sym.Section {
2201         sect := ldr.NewSection()
2202         sect.Rwx = uint8(rwx)
2203         sect.Name = name
2204         sect.Seg = seg
2205         sect.Align = int32(arch.PtrSize) // everything is at least pointer-aligned
2206         seg.Sections = append(seg.Sections, sect)
2207         return sect
2208 }
2209
2210 type chain struct {
2211         sym   loader.Sym
2212         up    *chain
2213         limit int // limit on entry to sym
2214 }
2215
2216 func haslinkregister(ctxt *Link) bool {
2217         return ctxt.FixedFrameSize() != 0
2218 }
2219
2220 func callsize(ctxt *Link) int {
2221         if haslinkregister(ctxt) {
2222                 return 0
2223         }
2224         return ctxt.Arch.RegSize
2225 }
2226
2227 type stkChk struct {
2228         ldr       *loader.Loader
2229         ctxt      *Link
2230         morestack loader.Sym
2231         done      loader.Bitmap
2232 }
2233
2234 // Walk the call tree and check that there is always enough stack space
2235 // for the call frames, especially for a chain of nosplit functions.
2236 func (ctxt *Link) dostkcheck() {
2237         ldr := ctxt.loader
2238         sc := stkChk{
2239                 ldr:       ldr,
2240                 ctxt:      ctxt,
2241                 morestack: ldr.Lookup("runtime.morestack", 0),
2242                 done:      loader.MakeBitmap(ldr.NSym()),
2243         }
2244
2245         // Every splitting function ensures that there are at least StackLimit
2246         // bytes available below SP when the splitting prologue finishes.
2247         // If the splitting function calls F, then F begins execution with
2248         // at least StackLimit - callsize() bytes available.
2249         // Check that every function behaves correctly with this amount
2250         // of stack, following direct calls in order to piece together chains
2251         // of non-splitting functions.
2252         var ch chain
2253         ch.limit = objabi.StackLimit - callsize(ctxt)
2254         if objabi.GOARCH == "arm64" {
2255                 // need extra 8 bytes below SP to save FP
2256                 ch.limit -= 8
2257         }
2258
2259         // Check every function, but do the nosplit functions in a first pass,
2260         // to make the printed failure chains as short as possible.
2261         for _, s := range ctxt.Textp {
2262                 if ldr.IsNoSplit(s) {
2263                         ch.sym = s
2264                         sc.check(&ch, 0)
2265                 }
2266         }
2267
2268         for _, s := range ctxt.Textp {
2269                 if !ldr.IsNoSplit(s) {
2270                         ch.sym = s
2271                         sc.check(&ch, 0)
2272                 }
2273         }
2274 }
2275
2276 func (sc *stkChk) check(up *chain, depth int) int {
2277         limit := up.limit
2278         s := up.sym
2279         ldr := sc.ldr
2280         ctxt := sc.ctxt
2281
2282         // Don't duplicate work: only need to consider each
2283         // function at top of safe zone once.
2284         top := limit == objabi.StackLimit-callsize(ctxt)
2285         if top {
2286                 if sc.done.Has(s) {
2287                         return 0
2288                 }
2289                 sc.done.Set(s)
2290         }
2291
2292         if depth > 500 {
2293                 sc.ctxt.Errorf(s, "nosplit stack check too deep")
2294                 sc.broke(up, 0)
2295                 return -1
2296         }
2297
2298         if ldr.AttrExternal(s) {
2299                 // external function.
2300                 // should never be called directly.
2301                 // onlyctxt.Diagnose the direct caller.
2302                 // TODO(mwhudson): actually think about this.
2303                 // TODO(khr): disabled for now. Calls to external functions can only happen on the g0 stack.
2304                 // See the trampolines in src/runtime/sys_darwin_$ARCH.go.
2305                 //if depth == 1 && ldr.SymType(s) != sym.SXREF && !ctxt.DynlinkingGo() &&
2306                 //      ctxt.BuildMode != BuildModeCArchive && ctxt.BuildMode != BuildModePIE && ctxt.BuildMode != BuildModeCShared && ctxt.BuildMode != BuildModePlugin {
2307                 //      Errorf(s, "call to external function")
2308                 //}
2309                 return -1
2310         }
2311         info := ldr.FuncInfo(s)
2312         if !info.Valid() { // external function. see above.
2313                 return -1
2314         }
2315
2316         if limit < 0 {
2317                 sc.broke(up, limit)
2318                 return -1
2319         }
2320
2321         // morestack looks like it calls functions,
2322         // but it switches the stack pointer first.
2323         if s == sc.morestack {
2324                 return 0
2325         }
2326
2327         var ch chain
2328         ch.up = up
2329
2330         if !ldr.IsNoSplit(s) {
2331                 // Ensure we have enough stack to call morestack.
2332                 ch.limit = limit - callsize(ctxt)
2333                 ch.sym = sc.morestack
2334                 if sc.check(&ch, depth+1) < 0 {
2335                         return -1
2336                 }
2337                 if !top {
2338                         return 0
2339                 }
2340                 // Raise limit to allow frame.
2341                 locals := info.Locals()
2342                 limit = objabi.StackLimit + int(locals) + int(ctxt.FixedFrameSize())
2343         }
2344
2345         // Walk through sp adjustments in function, consuming relocs.
2346         relocs := ldr.Relocs(s)
2347         var ch1 chain
2348         pcsp := obj.NewPCIter(uint32(ctxt.Arch.MinLC))
2349         ri := 0
2350         for pcsp.Init(ldr.Data(info.Pcsp())); !pcsp.Done; pcsp.Next() {
2351                 // pcsp.value is in effect for [pcsp.pc, pcsp.nextpc).
2352
2353                 // Check stack size in effect for this span.
2354                 if int32(limit)-pcsp.Value < 0 {
2355                         sc.broke(up, int(int32(limit)-pcsp.Value))
2356                         return -1
2357                 }
2358
2359                 // Process calls in this span.
2360                 for ; ri < relocs.Count(); ri++ {
2361                         r := relocs.At(ri)
2362                         if uint32(r.Off()) >= pcsp.NextPC {
2363                                 break
2364                         }
2365                         t := r.Type()
2366                         switch {
2367                         case t.IsDirectCall():
2368                                 ch.limit = int(int32(limit) - pcsp.Value - int32(callsize(ctxt)))
2369                                 ch.sym = r.Sym()
2370                                 if sc.check(&ch, depth+1) < 0 {
2371                                         return -1
2372                                 }
2373
2374                         // Indirect call. Assume it is a call to a splitting function,
2375                         // so we have to make sure it can call morestack.
2376                         // Arrange the data structures to report both calls, so that
2377                         // if there is an error, stkprint shows all the steps involved.
2378                         case t == objabi.R_CALLIND:
2379                                 ch.limit = int(int32(limit) - pcsp.Value - int32(callsize(ctxt)))
2380                                 ch.sym = 0
2381                                 ch1.limit = ch.limit - callsize(ctxt) // for morestack in called prologue
2382                                 ch1.up = &ch
2383                                 ch1.sym = sc.morestack
2384                                 if sc.check(&ch1, depth+2) < 0 {
2385                                         return -1
2386                                 }
2387                         }
2388                 }
2389         }
2390
2391         return 0
2392 }
2393
2394 func (sc *stkChk) broke(ch *chain, limit int) {
2395         sc.ctxt.Errorf(ch.sym, "nosplit stack overflow")
2396         sc.print(ch, limit)
2397 }
2398
2399 func (sc *stkChk) print(ch *chain, limit int) {
2400         ldr := sc.ldr
2401         ctxt := sc.ctxt
2402         var name string
2403         if ch.sym != 0 {
2404                 name = ldr.SymName(ch.sym)
2405                 if ldr.IsNoSplit(ch.sym) {
2406                         name += " (nosplit)"
2407                 }
2408         } else {
2409                 name = "function pointer"
2410         }
2411
2412         if ch.up == nil {
2413                 // top of chain. ch.sym != 0.
2414                 if ldr.IsNoSplit(ch.sym) {
2415                         fmt.Printf("\t%d\tassumed on entry to %s\n", ch.limit, name)
2416                 } else {
2417                         fmt.Printf("\t%d\tguaranteed after split check in %s\n", ch.limit, name)
2418                 }
2419         } else {
2420                 sc.print(ch.up, ch.limit+callsize(ctxt))
2421                 if !haslinkregister(ctxt) {
2422                         fmt.Printf("\t%d\ton entry to %s\n", ch.limit, name)
2423                 }
2424         }
2425
2426         if ch.limit != limit {
2427                 fmt.Printf("\t%d\tafter %s uses %d\n", limit, name, ch.limit-limit)
2428         }
2429 }
2430
2431 func usage() {
2432         fmt.Fprintf(os.Stderr, "usage: link [options] main.o\n")
2433         objabi.Flagprint(os.Stderr)
2434         Exit(2)
2435 }
2436
2437 type SymbolType int8 // TODO: after genasmsym is gone, maybe rename to plan9typeChar or something
2438
2439 const (
2440         // see also https://9p.io/magic/man2html/1/nm
2441         TextSym      SymbolType = 'T'
2442         DataSym      SymbolType = 'D'
2443         BSSSym       SymbolType = 'B'
2444         UndefinedSym SymbolType = 'U'
2445         TLSSym       SymbolType = 't'
2446         FrameSym     SymbolType = 'm'
2447         ParamSym     SymbolType = 'p'
2448         AutoSym      SymbolType = 'a'
2449
2450         // Deleted auto (not a real sym, just placeholder for type)
2451         DeletedAutoSym = 'x'
2452 )
2453
2454 // defineInternal defines a symbol used internally by the go runtime.
2455 func (ctxt *Link) defineInternal(p string, t sym.SymKind) loader.Sym {
2456         s := ctxt.loader.CreateSymForUpdate(p, 0)
2457         s.SetType(t)
2458         s.SetSpecial(true)
2459         s.SetLocal(true)
2460         return s.Sym()
2461 }
2462
2463 func (ctxt *Link) xdefine(p string, t sym.SymKind, v int64) loader.Sym {
2464         s := ctxt.defineInternal(p, t)
2465         ctxt.loader.SetSymValue(s, v)
2466         return s
2467 }
2468
2469 func datoff(ldr *loader.Loader, s loader.Sym, addr int64) int64 {
2470         if uint64(addr) >= Segdata.Vaddr {
2471                 return int64(uint64(addr) - Segdata.Vaddr + Segdata.Fileoff)
2472         }
2473         if uint64(addr) >= Segtext.Vaddr {
2474                 return int64(uint64(addr) - Segtext.Vaddr + Segtext.Fileoff)
2475         }
2476         ldr.Errorf(s, "invalid datoff %#x", addr)
2477         return 0
2478 }
2479
2480 func Entryvalue(ctxt *Link) int64 {
2481         a := *flagEntrySymbol
2482         if a[0] >= '0' && a[0] <= '9' {
2483                 return atolwhex(a)
2484         }
2485         ldr := ctxt.loader
2486         s := ldr.Lookup(a, 0)
2487         st := ldr.SymType(s)
2488         if st == 0 {
2489                 return *FlagTextAddr
2490         }
2491         if !ctxt.IsAIX() && st != sym.STEXT {
2492                 ldr.Errorf(s, "entry not text")
2493         }
2494         return ldr.SymValue(s)
2495 }
2496
2497 func (ctxt *Link) callgraph() {
2498         if !*FlagC {
2499                 return
2500         }
2501
2502         ldr := ctxt.loader
2503         for _, s := range ctxt.Textp {
2504                 relocs := ldr.Relocs(s)
2505                 for i := 0; i < relocs.Count(); i++ {
2506                         r := relocs.At(i)
2507                         rs := r.Sym()
2508                         if rs == 0 {
2509                                 continue
2510                         }
2511                         if r.Type().IsDirectCall() && (ldr.SymType(rs) == sym.STEXT || ldr.SymType(rs) == sym.SABIALIAS) {
2512                                 ctxt.Logf("%s calls %s\n", ldr.SymName(s), ldr.SymName(rs))
2513                         }
2514                 }
2515         }
2516 }
2517
2518 func Rnd(v int64, r int64) int64 {
2519         if r <= 0 {
2520                 return v
2521         }
2522         v += r - 1
2523         c := v % r
2524         if c < 0 {
2525                 c += r
2526         }
2527         v -= c
2528         return v
2529 }
2530
2531 func bgetc(r *bio.Reader) int {
2532         c, err := r.ReadByte()
2533         if err != nil {
2534                 if err != io.EOF {
2535                         log.Fatalf("reading input: %v", err)
2536                 }
2537                 return -1
2538         }
2539         return int(c)
2540 }
2541
2542 type markKind uint8 // for postorder traversal
2543 const (
2544         _ markKind = iota
2545         visiting
2546         visited
2547 )
2548
2549 func postorder(libs []*sym.Library) []*sym.Library {
2550         order := make([]*sym.Library, 0, len(libs)) // hold the result
2551         mark := make(map[*sym.Library]markKind, len(libs))
2552         for _, lib := range libs {
2553                 dfs(lib, mark, &order)
2554         }
2555         return order
2556 }
2557
2558 func dfs(lib *sym.Library, mark map[*sym.Library]markKind, order *[]*sym.Library) {
2559         if mark[lib] == visited {
2560                 return
2561         }
2562         if mark[lib] == visiting {
2563                 panic("found import cycle while visiting " + lib.Pkg)
2564         }
2565         mark[lib] = visiting
2566         for _, i := range lib.Imports {
2567                 dfs(i, mark, order)
2568         }
2569         mark[lib] = visited
2570         *order = append(*order, lib)
2571 }
2572
2573 func ElfSymForReloc(ctxt *Link, s loader.Sym) int32 {
2574         // If putelfsym created a local version of this symbol, use that in all
2575         // relocations.
2576         les := ctxt.loader.SymLocalElfSym(s)
2577         if les != 0 {
2578                 return les
2579         } else {
2580                 return ctxt.loader.SymElfSym(s)
2581         }
2582 }
2583
2584 func AddGotSym(target *Target, ldr *loader.Loader, syms *ArchSyms, s loader.Sym, elfRelocTyp uint32) {
2585         if ldr.SymGot(s) >= 0 {
2586                 return
2587         }
2588
2589         Adddynsym(ldr, target, syms, s)
2590         got := ldr.MakeSymbolUpdater(syms.GOT)
2591         ldr.SetGot(s, int32(got.Size()))
2592         got.AddUint(target.Arch, 0)
2593
2594         if target.IsElf() {
2595                 if target.Arch.PtrSize == 8 {
2596                         rela := ldr.MakeSymbolUpdater(syms.Rela)
2597                         rela.AddAddrPlus(target.Arch, got.Sym(), int64(ldr.SymGot(s)))
2598                         rela.AddUint64(target.Arch, elf.R_INFO(uint32(ldr.SymDynid(s)), elfRelocTyp))
2599                         rela.AddUint64(target.Arch, 0)
2600                 } else {
2601                         rel := ldr.MakeSymbolUpdater(syms.Rel)
2602                         rel.AddAddrPlus(target.Arch, got.Sym(), int64(ldr.SymGot(s)))
2603                         rel.AddUint32(target.Arch, elf.R_INFO32(uint32(ldr.SymDynid(s)), elfRelocTyp))
2604                 }
2605         } else if target.IsDarwin() {
2606                 leg := ldr.MakeSymbolUpdater(syms.LinkEditGOT)
2607                 leg.AddUint32(target.Arch, uint32(ldr.SymDynid(s)))
2608                 if target.IsPIE() && target.IsInternal() {
2609                         // Mach-O relocations are a royal pain to lay out.
2610                         // They use a compact stateful bytecode representation.
2611                         // Here we record what are needed and encode them later.
2612                         MachoAddBind(int64(ldr.SymGot(s)), s)
2613                 }
2614         } else {
2615                 ldr.Errorf(s, "addgotsym: unsupported binary format")
2616         }
2617 }