github.com/q45/go@v0.0.0-20151101211701-a4fb8c13db3f/src/cmd/link/internal/ld/link.go (about)

     1  // Derived from Inferno utils/6l/l.h and related files.
     2  // http://code.google.com/p/inferno-os/source/browse/utils/6l/l.h
     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  	"cmd/internal/obj"
    35  	"debug/elf"
    36  	"encoding/binary"
    37  	"fmt"
    38  )
    39  
    40  type LSym struct {
    41  	Name       string
    42  	Extname    string
    43  	Type       int16
    44  	Version    int16
    45  	Dupok      uint8
    46  	Cfunc      uint8
    47  	External   uint8
    48  	Nosplit    uint8
    49  	Reachable  bool
    50  	Cgoexport  uint8
    51  	Special    uint8
    52  	Stkcheck   uint8
    53  	Hide       uint8
    54  	Leaf       uint8
    55  	Localentry uint8
    56  	Onlist     uint8
    57  	// ElfType is set for symbols read from shared libraries by ldshlibsyms. It
    58  	// is not set for symbols defined by the packages being linked or by symbols
    59  	// read by ldelf (and so is left as elf.STT_NOTYPE).
    60  	ElfType     elf.SymType
    61  	Dynid       int32
    62  	Plt         int32
    63  	Got         int32
    64  	Align       int32
    65  	Elfsym      int32
    66  	LocalElfsym int32
    67  	Args        int32
    68  	Locals      int32
    69  	Value       int64
    70  	Size        int64
    71  	Allsym      *LSym
    72  	Next        *LSym
    73  	Sub         *LSym
    74  	Outer       *LSym
    75  	Gotype      *LSym
    76  	Reachparent *LSym
    77  	Queue       *LSym
    78  	File        string
    79  	Dynimplib   string
    80  	Dynimpvers  string
    81  	Sect        *Section
    82  	Autom       *Auto
    83  	Pcln        *Pcln
    84  	P           []byte
    85  	R           []Reloc
    86  	Local       bool
    87  }
    88  
    89  func (s *LSym) String() string {
    90  	if s.Version == 0 {
    91  		return s.Name
    92  	}
    93  	return fmt.Sprintf("%s<%d>", s.Name, s.Version)
    94  }
    95  
    96  func (s *LSym) ElfsymForReloc() int32 {
    97  	// If putelfsym created a local version of this symbol, use that in all
    98  	// relocations.
    99  	if s.LocalElfsym != 0 {
   100  		return s.LocalElfsym
   101  	} else {
   102  		return s.Elfsym
   103  	}
   104  }
   105  
   106  type Reloc struct {
   107  	Off     int32
   108  	Siz     uint8
   109  	Done    uint8
   110  	Type    int32
   111  	Variant int32
   112  	Add     int64
   113  	Xadd    int64
   114  	Sym     *LSym
   115  	Xsym    *LSym
   116  }
   117  
   118  type Auto struct {
   119  	Asym    *LSym
   120  	Link    *Auto
   121  	Aoffset int32
   122  	Name    int16
   123  	Gotype  *LSym
   124  }
   125  
   126  type Shlib struct {
   127  	Path string
   128  	Hash []byte
   129  	Deps []string
   130  	File *elf.File
   131  }
   132  
   133  type Link struct {
   134  	Thechar    int32
   135  	Thestring  string
   136  	Goarm      int32
   137  	Headtype   int
   138  	Arch       *LinkArch
   139  	Debugasm   int32
   140  	Debugvlog  int32
   141  	Bso        *obj.Biobuf
   142  	Windows    int32
   143  	Goroot     string
   144  	Hash       map[symVer]*LSym
   145  	Allsym     *LSym
   146  	Nsymbol    int32
   147  	Tlsg       *LSym
   148  	Libdir     []string
   149  	Library    []*Library
   150  	Shlibs     []Shlib
   151  	Tlsoffset  int
   152  	Diag       func(string, ...interface{})
   153  	Cursym     *LSym
   154  	Version    int
   155  	Textp      *LSym
   156  	Etextp     *LSym
   157  	Nhistfile  int32
   158  	Filesyms   *LSym
   159  	Moduledata *LSym
   160  }
   161  
   162  // The smallest possible offset from the hardware stack pointer to a local
   163  // variable on the stack. Architectures that use a link register save its value
   164  // on the stack in the function prologue and so always have a pointer between
   165  // the hardware stack pointer and the local variable area.
   166  func (ctxt *Link) FixedFrameSize() int64 {
   167  	switch ctxt.Arch.Thechar {
   168  	case '6', '8':
   169  		return 0
   170  	default:
   171  		return int64(ctxt.Arch.Ptrsize)
   172  	}
   173  }
   174  
   175  type LinkArch struct {
   176  	ByteOrder binary.ByteOrder
   177  	Name      string
   178  	Thechar   int
   179  	Minlc     int
   180  	Ptrsize   int
   181  	Regsize   int
   182  }
   183  
   184  type Library struct {
   185  	Objref string
   186  	Srcref string
   187  	File   string
   188  	Pkg    string
   189  	Shlib  string
   190  	hash   []byte
   191  }
   192  
   193  type Pcln struct {
   194  	Pcsp        Pcdata
   195  	Pcfile      Pcdata
   196  	Pcline      Pcdata
   197  	Pcdata      []Pcdata
   198  	Npcdata     int
   199  	Funcdata    []*LSym
   200  	Funcdataoff []int64
   201  	Nfuncdata   int
   202  	File        []*LSym
   203  	Nfile       int
   204  	Mfile       int
   205  	Lastfile    *LSym
   206  	Lastindex   int
   207  }
   208  
   209  type Pcdata struct {
   210  	P []byte
   211  }
   212  
   213  type Pciter struct {
   214  	d       Pcdata
   215  	p       []byte
   216  	pc      uint32
   217  	nextpc  uint32
   218  	pcscale uint32
   219  	value   int32
   220  	start   int
   221  	done    int
   222  }
   223  
   224  // Reloc.variant
   225  const (
   226  	RV_NONE = iota
   227  	RV_POWER_LO
   228  	RV_POWER_HI
   229  	RV_POWER_HA
   230  	RV_POWER_DS
   231  	RV_CHECK_OVERFLOW = 1 << 8
   232  	RV_TYPE_MASK      = RV_CHECK_OVERFLOW - 1
   233  )
   234  
   235  // Pcdata iterator.
   236  //	for(pciterinit(ctxt, &it, &pcd); !it.done; pciternext(&it)) { it.value holds in [it.pc, it.nextpc) }
   237  
   238  // Link holds the context for writing object code from a compiler
   239  // to be linker input or for reading that input into the linker.
   240  
   241  // LinkArch is the definition of a single architecture.
   242  
   243  const (
   244  	LinkAuto = 0 + iota
   245  	LinkInternal
   246  	LinkExternal
   247  )