github.com/mh-cbon/go@v0.0.0-20160603070303-9e112a3fe4c0/src/cmd/internal/objfile/goobj.go (about)

     1  // Copyright 2013 The Go Authors. All rights reserved.
     2  // Use of this source code is governed by a BSD-style
     3  // license that can be found in the LICENSE file.
     4  
     5  // Parsing of Go intermediate object files and archives.
     6  
     7  package objfile
     8  
     9  import (
    10  	"cmd/internal/goobj"
    11  	"debug/dwarf"
    12  	"errors"
    13  	"fmt"
    14  	"os"
    15  )
    16  
    17  type goobjFile struct {
    18  	goobj *goobj.Package
    19  }
    20  
    21  func openGoobj(r *os.File) (rawFile, error) {
    22  	f, err := goobj.Parse(r, `""`)
    23  	if err != nil {
    24  		return nil, err
    25  	}
    26  	return &goobjFile{f}, nil
    27  }
    28  
    29  func goobjName(id goobj.SymID) string {
    30  	if id.Version == 0 {
    31  		return id.Name
    32  	}
    33  	return fmt.Sprintf("%s<%d>", id.Name, id.Version)
    34  }
    35  
    36  func (f *goobjFile) symbols() ([]Sym, error) {
    37  	seen := make(map[goobj.SymID]bool)
    38  
    39  	var syms []Sym
    40  	for _, s := range f.goobj.Syms {
    41  		seen[s.SymID] = true
    42  		sym := Sym{Addr: uint64(s.Data.Offset), Name: goobjName(s.SymID), Size: int64(s.Size), Type: s.Type.Name, Code: '?'}
    43  		switch s.Kind {
    44  		case goobj.STEXT, goobj.SELFRXSECT:
    45  			sym.Code = 'T'
    46  		case goobj.STYPE, goobj.SSTRING, goobj.SGOSTRING, goobj.SGOFUNC, goobj.SRODATA, goobj.SFUNCTAB, goobj.STYPELINK, goobj.SITABLINK, goobj.SSYMTAB, goobj.SPCLNTAB, goobj.SELFROSECT:
    47  			sym.Code = 'R'
    48  		case goobj.SMACHOPLT, goobj.SELFSECT, goobj.SMACHO, goobj.SMACHOGOT, goobj.SNOPTRDATA, goobj.SINITARR, goobj.SDATA, goobj.SWINDOWS:
    49  			sym.Code = 'D'
    50  		case goobj.SBSS, goobj.SNOPTRBSS, goobj.STLSBSS:
    51  			sym.Code = 'B'
    52  		case goobj.SXREF, goobj.SMACHOSYMSTR, goobj.SMACHOSYMTAB, goobj.SMACHOINDIRECTPLT, goobj.SMACHOINDIRECTGOT, goobj.SFILE, goobj.SFILEPATH, goobj.SCONST, goobj.SDYNIMPORT, goobj.SHOSTOBJ:
    53  			sym.Code = 'X' // should not see
    54  		}
    55  		if s.Version != 0 {
    56  			sym.Code += 'a' - 'A'
    57  		}
    58  		syms = append(syms, sym)
    59  	}
    60  
    61  	for _, s := range f.goobj.Syms {
    62  		for _, r := range s.Reloc {
    63  			if !seen[r.Sym] {
    64  				seen[r.Sym] = true
    65  				sym := Sym{Name: goobjName(r.Sym), Code: 'U'}
    66  				if s.Version != 0 {
    67  					// should not happen but handle anyway
    68  					sym.Code = 'u'
    69  				}
    70  				syms = append(syms, sym)
    71  			}
    72  		}
    73  	}
    74  
    75  	return syms, nil
    76  }
    77  
    78  // pcln does not make sense for Go object files, because each
    79  // symbol has its own individual pcln table, so there is no global
    80  // space of addresses to map.
    81  func (f *goobjFile) pcln() (textStart uint64, symtab, pclntab []byte, err error) {
    82  	return 0, nil, nil, fmt.Errorf("pcln not available in go object file")
    83  }
    84  
    85  // text does not make sense for Go object files, because
    86  // each function has a separate section.
    87  func (f *goobjFile) text() (textStart uint64, text []byte, err error) {
    88  	return 0, nil, fmt.Errorf("text not available in go object file")
    89  }
    90  
    91  // goarch makes sense but is not exposed in debug/goobj's API,
    92  // and we don't need it yet for any users of internal/objfile.
    93  func (f *goobjFile) goarch() string {
    94  	return "GOARCH unimplemented for debug/goobj files"
    95  }
    96  
    97  func (f *goobjFile) loadAddress() (uint64, error) {
    98  	return 0, fmt.Errorf("unknown load address")
    99  }
   100  
   101  func (f *goobjFile) dwarf() (*dwarf.Data, error) {
   102  	return nil, errors.New("no DWARF data in go object file")
   103  }