From: Russ Cox Date: Thu, 13 Oct 2016 19:27:04 +0000 (-0400) Subject: cmd/dist: use debug/pe directly for cmd/link X-Git-Tag: go1.8beta1~843 X-Git-Url: http://www.git.cypherpunks.su/?a=commitdiff_plain;h=237d7e34bc7579ec499a029191c33106dc5476a1;p=gostls13.git cmd/dist: use debug/pe directly for cmd/link Delete vendored copy. Change-Id: I06e9d3b709553a1a8d06275e99bd8f617aac5788 Reviewed-on: https://go-review.googlesource.com/31011 Reviewed-by: Ian Lance Taylor --- diff --git a/misc/nacl/testzip.proto b/misc/nacl/testzip.proto index 33218dde8b..561df80642 100644 --- a/misc/nacl/testzip.proto +++ b/misc/nacl/testzip.proto @@ -36,11 +36,6 @@ go src=.. gofmt_test.go testdata + - link - internal - pe - testdata - + vendor golang.org x diff --git a/src/cmd/dist/buildtool.go b/src/cmd/dist/buildtool.go index 136e45eeb4..d035bb2a7d 100644 --- a/src/cmd/dist/buildtool.go +++ b/src/cmd/dist/buildtool.go @@ -60,10 +60,10 @@ var bootstrapDirs = []string{ "cmd/link/internal/arm64", "cmd/link/internal/ld", "cmd/link/internal/mips64", - "cmd/link/internal/pe", "cmd/link/internal/ppc64", "cmd/link/internal/s390x", "cmd/link/internal/x86", + "debug/pe", "math/big", } diff --git a/src/cmd/link/internal/ld/ldpe.go b/src/cmd/link/internal/ld/ldpe.go index 9d9eedad24..f116c48a7f 100644 --- a/src/cmd/link/internal/ld/ldpe.go +++ b/src/cmd/link/internal/ld/ldpe.go @@ -8,7 +8,7 @@ import ( "cmd/internal/bio" "cmd/internal/obj" "cmd/internal/sys" - "cmd/link/internal/pe" + "debug/pe" "errors" "fmt" "io" diff --git a/src/cmd/link/internal/pe/file.go b/src/cmd/link/internal/pe/file.go deleted file mode 100644 index 6a1e1afdf2..0000000000 --- a/src/cmd/link/internal/pe/file.go +++ /dev/null @@ -1,343 +0,0 @@ -// Copyright 2009 The Go Authors. All rights reserved. -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. - -// Package pe implements access to PE (Microsoft Windows Portable Executable) files. -package pe - -import ( - "debug/dwarf" - "encoding/binary" - "fmt" - "io" - "os" -) - -// A File represents an open PE file. -type File struct { - FileHeader - OptionalHeader interface{} // of type *OptionalHeader32 or *OptionalHeader64 - Sections []*Section - Symbols []*Symbol // COFF symbols with auxiliary symbol records removed - COFFSymbols []COFFSymbol // all COFF symbols (including auxiliary symbol records) - StringTable StringTable - - closer io.Closer -} - -// Open opens the named file using os.Open and prepares it for use as a PE binary. -func Open(name string) (*File, error) { - f, err := os.Open(name) - if err != nil { - return nil, err - } - ff, err := NewFile(f) - if err != nil { - f.Close() - return nil, err - } - ff.closer = f - return ff, nil -} - -// Close closes the File. -// If the File was created using NewFile directly instead of Open, -// Close has no effect. -func (f *File) Close() error { - var err error - if f.closer != nil { - err = f.closer.Close() - f.closer = nil - } - return err -} - -var ( - sizeofOptionalHeader32 = uint16(binary.Size(OptionalHeader32{})) - sizeofOptionalHeader64 = uint16(binary.Size(OptionalHeader64{})) -) - -// TODO(brainman): add Load function, as a replacement for NewFile, that does not call removeAuxSymbols (for performance) - -// NewFile creates a new File for accessing a PE binary in an underlying reader. -func NewFile(r io.ReaderAt) (*File, error) { - f := new(File) - sr := io.NewSectionReader(r, 0, 1<<63-1) - - var dosheader [96]byte - if _, err := r.ReadAt(dosheader[0:], 0); err != nil { - return nil, err - } - var base int64 - if dosheader[0] == 'M' && dosheader[1] == 'Z' { - signoff := int64(binary.LittleEndian.Uint32(dosheader[0x3c:])) - var sign [4]byte - r.ReadAt(sign[:], signoff) - if !(sign[0] == 'P' && sign[1] == 'E' && sign[2] == 0 && sign[3] == 0) { - return nil, fmt.Errorf("Invalid PE COFF file signature of %v.", sign) - } - base = signoff + 4 - } else { - base = int64(0) - } - sr.Seek(base, os.SEEK_SET) - if err := binary.Read(sr, binary.LittleEndian, &f.FileHeader); err != nil { - return nil, err - } - switch f.FileHeader.Machine { - case IMAGE_FILE_MACHINE_UNKNOWN, IMAGE_FILE_MACHINE_AMD64, IMAGE_FILE_MACHINE_I386: - default: - return nil, fmt.Errorf("Unrecognised COFF file header machine value of 0x%x.", f.FileHeader.Machine) - } - - var err error - - // Read string table. - f.StringTable, err = readStringTable(&f.FileHeader, sr) - if err != nil { - return nil, err - } - - // Read symbol table. - f.COFFSymbols, err = readCOFFSymbols(&f.FileHeader, sr) - if err != nil { - return nil, err - } - f.Symbols, err = removeAuxSymbols(f.COFFSymbols, f.StringTable) - if err != nil { - return nil, err - } - - // Read optional header. - sr.Seek(base, os.SEEK_SET) - if err := binary.Read(sr, binary.LittleEndian, &f.FileHeader); err != nil { - return nil, err - } - var oh32 OptionalHeader32 - var oh64 OptionalHeader64 - switch f.FileHeader.SizeOfOptionalHeader { - case sizeofOptionalHeader32: - if err := binary.Read(sr, binary.LittleEndian, &oh32); err != nil { - return nil, err - } - if oh32.Magic != 0x10b { // PE32 - return nil, fmt.Errorf("pe32 optional header has unexpected Magic of 0x%x", oh32.Magic) - } - f.OptionalHeader = &oh32 - case sizeofOptionalHeader64: - if err := binary.Read(sr, binary.LittleEndian, &oh64); err != nil { - return nil, err - } - if oh64.Magic != 0x20b { // PE32+ - return nil, fmt.Errorf("pe32+ optional header has unexpected Magic of 0x%x", oh64.Magic) - } - f.OptionalHeader = &oh64 - } - - // Process sections. - f.Sections = make([]*Section, f.FileHeader.NumberOfSections) - for i := 0; i < int(f.FileHeader.NumberOfSections); i++ { - sh := new(SectionHeader32) - if err := binary.Read(sr, binary.LittleEndian, sh); err != nil { - return nil, err - } - name, err := sh.fullName(f.StringTable) - if err != nil { - return nil, err - } - s := new(Section) - s.SectionHeader = SectionHeader{ - Name: name, - VirtualSize: sh.VirtualSize, - VirtualAddress: sh.VirtualAddress, - Size: sh.SizeOfRawData, - Offset: sh.PointerToRawData, - PointerToRelocations: sh.PointerToRelocations, - PointerToLineNumbers: sh.PointerToLineNumbers, - NumberOfRelocations: sh.NumberOfRelocations, - NumberOfLineNumbers: sh.NumberOfLineNumbers, - Characteristics: sh.Characteristics, - } - r2 := r - if sh.PointerToRawData == 0 { // .bss must have all 0s - r2 = zeroReaderAt{} - } - s.sr = io.NewSectionReader(r2, int64(s.SectionHeader.Offset), int64(s.SectionHeader.Size)) - s.ReaderAt = s.sr - f.Sections[i] = s - } - for i := range f.Sections { - var err error - f.Sections[i].Relocs, err = readRelocs(&f.Sections[i].SectionHeader, sr) - if err != nil { - return nil, err - } - } - - return f, nil -} - -// zeroReaderAt is ReaderAt that reads 0s. -type zeroReaderAt struct{} - -// ReadAt writes len(p) 0s into p. -func (w zeroReaderAt) ReadAt(p []byte, off int64) (n int, err error) { - for i := range p { - p[i] = 0 - } - return len(p), nil -} - -// getString extracts a string from symbol string table. -func getString(section []byte, start int) (string, bool) { - if start < 0 || start >= len(section) { - return "", false - } - - for end := start; end < len(section); end++ { - if section[end] == 0 { - return string(section[start:end]), true - } - } - return "", false -} - -// Section returns the first section with the given name, or nil if no such -// section exists. -func (f *File) Section(name string) *Section { - for _, s := range f.Sections { - if s.Name == name { - return s - } - } - return nil -} - -func (f *File) DWARF() (*dwarf.Data, error) { - // There are many other DWARF sections, but these - // are the ones the debug/dwarf package uses. - // Don't bother loading others. - var names = [...]string{"abbrev", "info", "line", "ranges", "str"} - var dat [len(names)][]byte - for i, name := range names { - name = ".debug_" + name - s := f.Section(name) - if s == nil { - continue - } - b, err := s.Data() - if err != nil && uint32(len(b)) < s.Size { - return nil, err - } - if 0 < s.VirtualSize && s.VirtualSize < s.Size { - b = b[:s.VirtualSize] - } - dat[i] = b - } - - abbrev, info, line, ranges, str := dat[0], dat[1], dat[2], dat[3], dat[4] - return dwarf.New(abbrev, nil, nil, info, line, nil, ranges, str) -} - -// TODO(brainman): document ImportDirectory once we decide what to do with it. - -type ImportDirectory struct { - OriginalFirstThunk uint32 - TimeDateStamp uint32 - ForwarderChain uint32 - Name uint32 - FirstThunk uint32 - - dll string -} - -// ImportedSymbols returns the names of all symbols -// referred to by the binary f that are expected to be -// satisfied by other libraries at dynamic load time. -// It does not return weak symbols. -func (f *File) ImportedSymbols() ([]string, error) { - pe64 := f.Machine == IMAGE_FILE_MACHINE_AMD64 - ds := f.Section(".idata") - if ds == nil { - // not dynamic, so no libraries - return nil, nil - } - d, err := ds.Data() - if err != nil { - return nil, err - } - var ida []ImportDirectory - for len(d) > 0 { - var dt ImportDirectory - dt.OriginalFirstThunk = binary.LittleEndian.Uint32(d[0:4]) - dt.Name = binary.LittleEndian.Uint32(d[12:16]) - dt.FirstThunk = binary.LittleEndian.Uint32(d[16:20]) - d = d[20:] - if dt.OriginalFirstThunk == 0 { - break - } - ida = append(ida, dt) - } - // TODO(brainman): this needs to be rewritten - // ds.Data() return contets of .idata section. Why store in variable called "names"? - // Why we are retrieving it second time? We already have it in "d", and it is not modified anywhere. - // getString does not extracts a string from symbol string table (as getString doco says). - // Why ds.Data() called again and again in the loop? - // Needs test before rewrite. - names, _ := ds.Data() - var all []string - for _, dt := range ida { - dt.dll, _ = getString(names, int(dt.Name-ds.VirtualAddress)) - d, _ = ds.Data() - // seek to OriginalFirstThunk - d = d[dt.OriginalFirstThunk-ds.VirtualAddress:] - for len(d) > 0 { - if pe64 { // 64bit - va := binary.LittleEndian.Uint64(d[0:8]) - d = d[8:] - if va == 0 { - break - } - if va&0x8000000000000000 > 0 { // is Ordinal - // TODO add dynimport ordinal support. - } else { - fn, _ := getString(names, int(uint32(va)-ds.VirtualAddress+2)) - all = append(all, fn+":"+dt.dll) - } - } else { // 32bit - va := binary.LittleEndian.Uint32(d[0:4]) - d = d[4:] - if va == 0 { - break - } - if va&0x80000000 > 0 { // is Ordinal - // TODO add dynimport ordinal support. - //ord := va&0x0000FFFF - } else { - fn, _ := getString(names, int(va-ds.VirtualAddress+2)) - all = append(all, fn+":"+dt.dll) - } - } - } - } - - return all, nil -} - -// ImportedLibraries returns the names of all libraries -// referred to by the binary f that are expected to be -// linked with the binary at dynamic link time. -func (f *File) ImportedLibraries() ([]string, error) { - // TODO - // cgo -dynimport don't use this for windows PE, so just return. - return nil, nil -} - -// FormatError is unused. -// The type is retained for compatibility. -type FormatError struct { -} - -func (e *FormatError) Error() string { - return "unknown error" -} diff --git a/src/cmd/link/internal/pe/file_test.go b/src/cmd/link/internal/pe/file_test.go deleted file mode 100644 index 5a740c8705..0000000000 --- a/src/cmd/link/internal/pe/file_test.go +++ /dev/null @@ -1,417 +0,0 @@ -// Copyright 2009 The Go Authors. All rights reserved. -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. - -package pe - -import ( - "debug/dwarf" - "internal/testenv" - "io/ioutil" - "os" - "os/exec" - "path/filepath" - "reflect" - "runtime" - "testing" -) - -type fileTest struct { - file string - hdr FileHeader - opthdr interface{} - sections []*SectionHeader - symbols []*Symbol - hasNoDwarfInfo bool -} - -var fileTests = []fileTest{ - { - file: "testdata/gcc-386-mingw-obj", - hdr: FileHeader{0x014c, 0x000c, 0x0, 0x64a, 0x1e, 0x0, 0x104}, - sections: []*SectionHeader{ - {".text", 0, 0, 36, 500, 1440, 0, 3, 0, 0x60300020}, - {".data", 0, 0, 0, 0, 0, 0, 0, 0, 3224371264}, - {".bss", 0, 0, 0, 0, 0, 0, 0, 0, 3224371328}, - {".debug_abbrev", 0, 0, 137, 536, 0, 0, 0, 0, 0x42100000}, - {".debug_info", 0, 0, 418, 673, 1470, 0, 7, 0, 1108344832}, - {".debug_line", 0, 0, 128, 1091, 1540, 0, 1, 0, 1108344832}, - {".rdata", 0, 0, 16, 1219, 0, 0, 0, 0, 1076887616}, - {".debug_frame", 0, 0, 52, 1235, 1550, 0, 2, 0, 1110441984}, - {".debug_loc", 0, 0, 56, 1287, 0, 0, 0, 0, 1108344832}, - {".debug_pubnames", 0, 0, 27, 1343, 1570, 0, 1, 0, 1108344832}, - {".debug_pubtypes", 0, 0, 38, 1370, 1580, 0, 1, 0, 1108344832}, - {".debug_aranges", 0, 0, 32, 1408, 1590, 0, 2, 0, 1108344832}, - }, - symbols: []*Symbol{ - {".file", 0x0, -2, 0x0, 0x67}, - {"_main", 0x0, 1, 0x20, 0x2}, - {".text", 0x0, 1, 0x0, 0x3}, - {".data", 0x0, 2, 0x0, 0x3}, - {".bss", 0x0, 3, 0x0, 0x3}, - {".debug_abbrev", 0x0, 4, 0x0, 0x3}, - {".debug_info", 0x0, 5, 0x0, 0x3}, - {".debug_line", 0x0, 6, 0x0, 0x3}, - {".rdata", 0x0, 7, 0x0, 0x3}, - {".debug_frame", 0x0, 8, 0x0, 0x3}, - {".debug_loc", 0x0, 9, 0x0, 0x3}, - {".debug_pubnames", 0x0, 10, 0x0, 0x3}, - {".debug_pubtypes", 0x0, 11, 0x0, 0x3}, - {".debug_aranges", 0x0, 12, 0x0, 0x3}, - {"___main", 0x0, 0, 0x20, 0x2}, - {"_puts", 0x0, 0, 0x20, 0x2}, - }, - }, - { - file: "testdata/gcc-386-mingw-exec", - hdr: FileHeader{0x014c, 0x000f, 0x4c6a1b60, 0x3c00, 0x282, 0xe0, 0x107}, - opthdr: &OptionalHeader32{ - 0x10b, 0x2, 0x38, 0xe00, 0x1a00, 0x200, 0x1160, 0x1000, 0x2000, 0x400000, 0x1000, 0x200, 0x4, 0x0, 0x1, 0x0, 0x4, 0x0, 0x0, 0x10000, 0x400, 0x14abb, 0x3, 0x0, 0x200000, 0x1000, 0x100000, 0x1000, 0x0, 0x10, - [16]DataDirectory{ - {0x0, 0x0}, - {0x5000, 0x3c8}, - {0x0, 0x0}, - {0x0, 0x0}, - {0x0, 0x0}, - {0x0, 0x0}, - {0x0, 0x0}, - {0x0, 0x0}, - {0x0, 0x0}, - {0x7000, 0x18}, - {0x0, 0x0}, - {0x0, 0x0}, - {0x0, 0x0}, - {0x0, 0x0}, - {0x0, 0x0}, - {0x0, 0x0}, - }, - }, - sections: []*SectionHeader{ - {".text", 0xcd8, 0x1000, 0xe00, 0x400, 0x0, 0x0, 0x0, 0x0, 0x60500060}, - {".data", 0x10, 0x2000, 0x200, 0x1200, 0x0, 0x0, 0x0, 0x0, 0xc0300040}, - {".rdata", 0x120, 0x3000, 0x200, 0x1400, 0x0, 0x0, 0x0, 0x0, 0x40300040}, - {".bss", 0xdc, 0x4000, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0xc0400080}, - {".idata", 0x3c8, 0x5000, 0x400, 0x1600, 0x0, 0x0, 0x0, 0x0, 0xc0300040}, - {".CRT", 0x18, 0x6000, 0x200, 0x1a00, 0x0, 0x0, 0x0, 0x0, 0xc0300040}, - {".tls", 0x20, 0x7000, 0x200, 0x1c00, 0x0, 0x0, 0x0, 0x0, 0xc0300040}, - {".debug_aranges", 0x20, 0x8000, 0x200, 0x1e00, 0x0, 0x0, 0x0, 0x0, 0x42100000}, - {".debug_pubnames", 0x51, 0x9000, 0x200, 0x2000, 0x0, 0x0, 0x0, 0x0, 0x42100000}, - {".debug_pubtypes", 0x91, 0xa000, 0x200, 0x2200, 0x0, 0x0, 0x0, 0x0, 0x42100000}, - {".debug_info", 0xe22, 0xb000, 0x1000, 0x2400, 0x0, 0x0, 0x0, 0x0, 0x42100000}, - {".debug_abbrev", 0x157, 0xc000, 0x200, 0x3400, 0x0, 0x0, 0x0, 0x0, 0x42100000}, - {".debug_line", 0x144, 0xd000, 0x200, 0x3600, 0x0, 0x0, 0x0, 0x0, 0x42100000}, - {".debug_frame", 0x34, 0xe000, 0x200, 0x3800, 0x0, 0x0, 0x0, 0x0, 0x42300000}, - {".debug_loc", 0x38, 0xf000, 0x200, 0x3a00, 0x0, 0x0, 0x0, 0x0, 0x42100000}, - }, - }, - { - file: "testdata/gcc-386-mingw-no-symbols-exec", - hdr: FileHeader{0x14c, 0x8, 0x69676572, 0x0, 0x0, 0xe0, 0x30f}, - opthdr: &OptionalHeader32{0x10b, 0x2, 0x18, 0xe00, 0x1e00, 0x200, 0x1280, 0x1000, 0x2000, 0x400000, 0x1000, 0x200, 0x4, 0x0, 0x1, 0x0, 0x4, 0x0, 0x0, 0x9000, 0x400, 0x5306, 0x3, 0x0, 0x200000, 0x1000, 0x100000, 0x1000, 0x0, 0x10, - [16]DataDirectory{ - {0x0, 0x0}, - {0x6000, 0x378}, - {0x0, 0x0}, - {0x0, 0x0}, - {0x0, 0x0}, - {0x0, 0x0}, - {0x0, 0x0}, - {0x0, 0x0}, - {0x0, 0x0}, - {0x8004, 0x18}, - {0x0, 0x0}, - {0x0, 0x0}, - {0x60b8, 0x7c}, - {0x0, 0x0}, - {0x0, 0x0}, - {0x0, 0x0}, - }, - }, - sections: []*SectionHeader{ - {".text", 0xc64, 0x1000, 0xe00, 0x400, 0x0, 0x0, 0x0, 0x0, 0x60500060}, - {".data", 0x10, 0x2000, 0x200, 0x1200, 0x0, 0x0, 0x0, 0x0, 0xc0300040}, - {".rdata", 0x134, 0x3000, 0x200, 0x1400, 0x0, 0x0, 0x0, 0x0, 0x40300040}, - {".eh_fram", 0x3a0, 0x4000, 0x400, 0x1600, 0x0, 0x0, 0x0, 0x0, 0x40300040}, - {".bss", 0x60, 0x5000, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0xc0300080}, - {".idata", 0x378, 0x6000, 0x400, 0x1a00, 0x0, 0x0, 0x0, 0x0, 0xc0300040}, - {".CRT", 0x18, 0x7000, 0x200, 0x1e00, 0x0, 0x0, 0x0, 0x0, 0xc0300040}, - {".tls", 0x20, 0x8000, 0x200, 0x2000, 0x0, 0x0, 0x0, 0x0, 0xc0300040}, - }, - hasNoDwarfInfo: true, - }, - { - file: "testdata/gcc-amd64-mingw-obj", - hdr: FileHeader{0x8664, 0x6, 0x0, 0x198, 0x12, 0x0, 0x4}, - sections: []*SectionHeader{ - {".text", 0x0, 0x0, 0x30, 0x104, 0x15c, 0x0, 0x3, 0x0, 0x60500020}, - {".data", 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0xc0500040}, - {".bss", 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0xc0500080}, - {".rdata", 0x0, 0x0, 0x10, 0x134, 0x0, 0x0, 0x0, 0x0, 0x40500040}, - {".xdata", 0x0, 0x0, 0xc, 0x144, 0x0, 0x0, 0x0, 0x0, 0x40300040}, - {".pdata", 0x0, 0x0, 0xc, 0x150, 0x17a, 0x0, 0x3, 0x0, 0x40300040}, - }, - symbols: []*Symbol{ - {".file", 0x0, -2, 0x0, 0x67}, - {"main", 0x0, 1, 0x20, 0x2}, - {".text", 0x0, 1, 0x0, 0x3}, - {".data", 0x0, 2, 0x0, 0x3}, - {".bss", 0x0, 3, 0x0, 0x3}, - {".rdata", 0x0, 4, 0x0, 0x3}, - {".xdata", 0x0, 5, 0x0, 0x3}, - {".pdata", 0x0, 6, 0x0, 0x3}, - {"__main", 0x0, 0, 0x20, 0x2}, - {"puts", 0x0, 0, 0x20, 0x2}, - }, - hasNoDwarfInfo: true, - }, - { - file: "testdata/gcc-amd64-mingw-exec", - hdr: FileHeader{0x8664, 0x11, 0x53e4364f, 0x39600, 0x6fc, 0xf0, 0x27}, - opthdr: &OptionalHeader64{ - 0x20b, 0x2, 0x16, 0x6a00, 0x2400, 0x1600, 0x14e0, 0x1000, 0x400000, 0x1000, 0x200, 0x4, 0x0, 0x0, 0x0, 0x5, 0x2, 0x0, 0x45000, 0x600, 0x46f19, 0x3, 0x0, 0x200000, 0x1000, 0x100000, 0x1000, 0x0, 0x10, - [16]DataDirectory{ - {0x0, 0x0}, - {0xe000, 0x990}, - {0x0, 0x0}, - {0xa000, 0x498}, - {0x0, 0x0}, - {0x0, 0x0}, - {0x0, 0x0}, - {0x0, 0x0}, - {0x0, 0x0}, - {0x10000, 0x28}, - {0x0, 0x0}, - {0x0, 0x0}, - {0xe254, 0x218}, - {0x0, 0x0}, - {0x0, 0x0}, - {0x0, 0x0}, - }}, - sections: []*SectionHeader{ - {".text", 0x6860, 0x1000, 0x6a00, 0x600, 0x0, 0x0, 0x0, 0x0, 0x60500020}, - {".data", 0xe0, 0x8000, 0x200, 0x7000, 0x0, 0x0, 0x0, 0x0, 0xc0500040}, - {".rdata", 0x6b0, 0x9000, 0x800, 0x7200, 0x0, 0x0, 0x0, 0x0, 0x40600040}, - {".pdata", 0x498, 0xa000, 0x600, 0x7a00, 0x0, 0x0, 0x0, 0x0, 0x40300040}, - {".xdata", 0x488, 0xb000, 0x600, 0x8000, 0x0, 0x0, 0x0, 0x0, 0x40300040}, - {".bss", 0x1410, 0xc000, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0xc0600080}, - {".idata", 0x990, 0xe000, 0xa00, 0x8600, 0x0, 0x0, 0x0, 0x0, 0xc0300040}, - {".CRT", 0x68, 0xf000, 0x200, 0x9000, 0x0, 0x0, 0x0, 0x0, 0xc0400040}, - {".tls", 0x48, 0x10000, 0x200, 0x9200, 0x0, 0x0, 0x0, 0x0, 0xc0600040}, - {".debug_aranges", 0x600, 0x11000, 0x600, 0x9400, 0x0, 0x0, 0x0, 0x0, 0x42500040}, - {".debug_info", 0x1316e, 0x12000, 0x13200, 0x9a00, 0x0, 0x0, 0x0, 0x0, 0x42100040}, - {".debug_abbrev", 0x2ccb, 0x26000, 0x2e00, 0x1cc00, 0x0, 0x0, 0x0, 0x0, 0x42100040}, - {".debug_line", 0x3c4d, 0x29000, 0x3e00, 0x1fa00, 0x0, 0x0, 0x0, 0x0, 0x42100040}, - {".debug_frame", 0x18b8, 0x2d000, 0x1a00, 0x23800, 0x0, 0x0, 0x0, 0x0, 0x42400040}, - {".debug_str", 0x396, 0x2f000, 0x400, 0x25200, 0x0, 0x0, 0x0, 0x0, 0x42100040}, - {".debug_loc", 0x13240, 0x30000, 0x13400, 0x25600, 0x0, 0x0, 0x0, 0x0, 0x42100040}, - {".debug_ranges", 0xa70, 0x44000, 0xc00, 0x38a00, 0x0, 0x0, 0x0, 0x0, 0x42100040}, - }, - }, -} - -func isOptHdrEq(a, b interface{}) bool { - switch va := a.(type) { - case *OptionalHeader32: - vb, ok := b.(*OptionalHeader32) - if !ok { - return false - } - return *vb == *va - case *OptionalHeader64: - vb, ok := b.(*OptionalHeader64) - if !ok { - return false - } - return *vb == *va - case nil: - return b == nil - } - return false -} - -func TestOpen(t *testing.T) { - for i := range fileTests { - tt := &fileTests[i] - - f, err := Open(tt.file) - if err != nil { - t.Error(err) - continue - } - if !reflect.DeepEqual(f.FileHeader, tt.hdr) { - t.Errorf("open %s:\n\thave %#v\n\twant %#v\n", tt.file, f.FileHeader, tt.hdr) - continue - } - if !isOptHdrEq(tt.opthdr, f.OptionalHeader) { - t.Errorf("open %s:\n\thave %#v\n\twant %#v\n", tt.file, f.OptionalHeader, tt.opthdr) - continue - } - - for i, sh := range f.Sections { - if i >= len(tt.sections) { - break - } - have := &sh.SectionHeader - want := tt.sections[i] - if !reflect.DeepEqual(have, want) { - t.Errorf("open %s, section %d:\n\thave %#v\n\twant %#v\n", tt.file, i, have, want) - } - } - tn := len(tt.sections) - fn := len(f.Sections) - if tn != fn { - t.Errorf("open %s: len(Sections) = %d, want %d", tt.file, fn, tn) - } - for i, have := range f.Symbols { - if i >= len(tt.symbols) { - break - } - want := tt.symbols[i] - if !reflect.DeepEqual(have, want) { - t.Errorf("open %s, symbol %d:\n\thave %#v\n\twant %#v\n", tt.file, i, have, want) - } - } - if !tt.hasNoDwarfInfo { - _, err = f.DWARF() - if err != nil { - t.Errorf("fetching %s dwarf details failed: %v", tt.file, err) - } - } - } -} - -func TestOpenFailure(t *testing.T) { - filename := "file.go" // not a PE file - _, err := Open(filename) // don't crash - if err == nil { - t.Errorf("open %s: succeeded unexpectedly", filename) - } -} - -func TestDWARF(t *testing.T) { - if runtime.GOOS != "windows" { - t.Skip("skipping windows only test") - } - - tmpdir, err := ioutil.TempDir("", "TestDWARF") - if err != nil { - t.Fatal("TempDir failed: ", err) - } - defer os.RemoveAll(tmpdir) - - prog := ` -package main -func main() { -} -` - src := filepath.Join(tmpdir, "a.go") - exe := filepath.Join(tmpdir, "a.exe") - err = ioutil.WriteFile(src, []byte(prog), 0644) - output, err := exec.Command(testenv.GoToolPath(t), "build", "-o", exe, src).CombinedOutput() - if err != nil { - t.Fatalf("building test executable failed: %s %s", err, output) - } - - f, err := Open(exe) - if err != nil { - t.Fatal(err) - } - defer f.Close() - - d, err := f.DWARF() - if err != nil { - t.Fatal(err) - } - - // look for main.main - r := d.Reader() - for { - e, err := r.Next() - if err != nil { - t.Fatal("r.Next:", err) - } - if e == nil { - break - } - if e.Tag == dwarf.TagSubprogram { - for _, f := range e.Field { - if f.Attr == dwarf.AttrName && e.Val(dwarf.AttrName) == "main.main" { - return - } - } - } - } - t.Fatal("main.main not found") -} - -func TestBSSHasZeros(t *testing.T) { - testenv.MustHaveExec(t) - - if runtime.GOOS != "windows" { - t.Skip("skipping windows only test") - } - gccpath, err := exec.LookPath("gcc") - if err != nil { - t.Skip("skipping test: gcc is missing") - } - - tmpdir, err := ioutil.TempDir("", "TestBSSHasZeros") - if err != nil { - t.Fatal(err) - } - defer os.RemoveAll(tmpdir) - - srcpath := filepath.Join(tmpdir, "a.c") - src := ` -#include - -int zero = 0; - -int -main(void) -{ - printf("%d\n", zero); - return 0; -} -` - err = ioutil.WriteFile(srcpath, []byte(src), 0644) - if err != nil { - t.Fatal(err) - } - - objpath := filepath.Join(tmpdir, "a.obj") - cmd := exec.Command(gccpath, "-c", srcpath, "-o", objpath) - out, err := cmd.CombinedOutput() - if err != nil { - t.Fatalf("failed to build object file: %v - %v", err, string(out)) - } - - f, err := Open(objpath) - if err != nil { - t.Fatal(err) - } - defer f.Close() - - var bss *Section - for _, sect := range f.Sections { - if sect.Name == ".bss" { - bss = sect - break - } - } - if bss == nil { - t.Fatal("could not find .bss section") - } - data, err := bss.Data() - if err != nil { - t.Fatal(err) - } - if len(data) == 0 { - t.Fatalf("%s file .bss section cannot be empty", objpath) - } - for _, b := range data { - if b != 0 { - t.Fatalf(".bss section has non zero bytes: %v", data) - } - } -} diff --git a/src/cmd/link/internal/pe/pe.go b/src/cmd/link/internal/pe/pe.go deleted file mode 100644 index 8050d59c70..0000000000 --- a/src/cmd/link/internal/pe/pe.go +++ /dev/null @@ -1,110 +0,0 @@ -// Copyright 2009 The Go Authors. All rights reserved. -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. - -package pe - -type FileHeader struct { - Machine uint16 - NumberOfSections uint16 - TimeDateStamp uint32 - PointerToSymbolTable uint32 - NumberOfSymbols uint32 - SizeOfOptionalHeader uint16 - Characteristics uint16 -} - -type DataDirectory struct { - VirtualAddress uint32 - Size uint32 -} - -type OptionalHeader32 struct { - Magic uint16 - MajorLinkerVersion uint8 - MinorLinkerVersion uint8 - SizeOfCode uint32 - SizeOfInitializedData uint32 - SizeOfUninitializedData uint32 - AddressOfEntryPoint uint32 - BaseOfCode uint32 - BaseOfData uint32 - ImageBase uint32 - SectionAlignment uint32 - FileAlignment uint32 - MajorOperatingSystemVersion uint16 - MinorOperatingSystemVersion uint16 - MajorImageVersion uint16 - MinorImageVersion uint16 - MajorSubsystemVersion uint16 - MinorSubsystemVersion uint16 - Win32VersionValue uint32 - SizeOfImage uint32 - SizeOfHeaders uint32 - CheckSum uint32 - Subsystem uint16 - DllCharacteristics uint16 - SizeOfStackReserve uint32 - SizeOfStackCommit uint32 - SizeOfHeapReserve uint32 - SizeOfHeapCommit uint32 - LoaderFlags uint32 - NumberOfRvaAndSizes uint32 - DataDirectory [16]DataDirectory -} - -type OptionalHeader64 struct { - Magic uint16 - MajorLinkerVersion uint8 - MinorLinkerVersion uint8 - SizeOfCode uint32 - SizeOfInitializedData uint32 - SizeOfUninitializedData uint32 - AddressOfEntryPoint uint32 - BaseOfCode uint32 - ImageBase uint64 - SectionAlignment uint32 - FileAlignment uint32 - MajorOperatingSystemVersion uint16 - MinorOperatingSystemVersion uint16 - MajorImageVersion uint16 - MinorImageVersion uint16 - MajorSubsystemVersion uint16 - MinorSubsystemVersion uint16 - Win32VersionValue uint32 - SizeOfImage uint32 - SizeOfHeaders uint32 - CheckSum uint32 - Subsystem uint16 - DllCharacteristics uint16 - SizeOfStackReserve uint64 - SizeOfStackCommit uint64 - SizeOfHeapReserve uint64 - SizeOfHeapCommit uint64 - LoaderFlags uint32 - NumberOfRvaAndSizes uint32 - DataDirectory [16]DataDirectory -} - -const ( - IMAGE_FILE_MACHINE_UNKNOWN = 0x0 - IMAGE_FILE_MACHINE_AM33 = 0x1d3 - IMAGE_FILE_MACHINE_AMD64 = 0x8664 - IMAGE_FILE_MACHINE_ARM = 0x1c0 - IMAGE_FILE_MACHINE_EBC = 0xebc - IMAGE_FILE_MACHINE_I386 = 0x14c - IMAGE_FILE_MACHINE_IA64 = 0x200 - IMAGE_FILE_MACHINE_M32R = 0x9041 - IMAGE_FILE_MACHINE_MIPS16 = 0x266 - IMAGE_FILE_MACHINE_MIPSFPU = 0x366 - IMAGE_FILE_MACHINE_MIPSFPU16 = 0x466 - IMAGE_FILE_MACHINE_POWERPC = 0x1f0 - IMAGE_FILE_MACHINE_POWERPCFP = 0x1f1 - IMAGE_FILE_MACHINE_R4000 = 0x166 - IMAGE_FILE_MACHINE_SH3 = 0x1a2 - IMAGE_FILE_MACHINE_SH3DSP = 0x1a3 - IMAGE_FILE_MACHINE_SH4 = 0x1a6 - IMAGE_FILE_MACHINE_SH5 = 0x1a8 - IMAGE_FILE_MACHINE_THUMB = 0x1c2 - IMAGE_FILE_MACHINE_WCEMIPSV2 = 0x169 -) diff --git a/src/cmd/link/internal/pe/section.go b/src/cmd/link/internal/pe/section.go deleted file mode 100644 index fc6c062d62..0000000000 --- a/src/cmd/link/internal/pe/section.go +++ /dev/null @@ -1,112 +0,0 @@ -// Copyright 2016 The Go Authors. All rights reserved. -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. - -package pe - -import ( - "encoding/binary" - "fmt" - "io" - "os" - "strconv" -) - -// SectionHeader32 represents real PE COFF section header. -type SectionHeader32 struct { - Name [8]uint8 - VirtualSize uint32 - VirtualAddress uint32 - SizeOfRawData uint32 - PointerToRawData uint32 - PointerToRelocations uint32 - PointerToLineNumbers uint32 - NumberOfRelocations uint16 - NumberOfLineNumbers uint16 - Characteristics uint32 -} - -// fullName finds real name of section sh. Normally name is stored -// in sh.Name, but if it is longer then 8 characters, it is stored -// in COFF string table st instead. -func (sh *SectionHeader32) fullName(st StringTable) (string, error) { - if sh.Name[0] != '/' { - return cstring(sh.Name[:]), nil - } - i, err := strconv.Atoi(cstring(sh.Name[1:])) - if err != nil { - return "", err - } - return st.String(uint32(i)) -} - -// TODO(brainman): copy all IMAGE_REL_* consts from ldpe.go here - -// Reloc represents a PE COFF relocation. -// Each section contains its own relocation list. -type Reloc struct { - VirtualAddress uint32 - SymbolTableIndex uint32 - Type uint16 -} - -func readRelocs(sh *SectionHeader, r io.ReadSeeker) ([]Reloc, error) { - if sh.NumberOfRelocations <= 0 { - return nil, nil - } - _, err := r.Seek(int64(sh.PointerToRelocations), os.SEEK_SET) - if err != nil { - return nil, fmt.Errorf("fail to seek to %q section relocations: %v", sh.Name, err) - } - relocs := make([]Reloc, sh.NumberOfRelocations) - err = binary.Read(r, binary.LittleEndian, relocs) - if err != nil { - return nil, fmt.Errorf("fail to read section relocations: %v", err) - } - return relocs, nil -} - -// SectionHeader is similar to SectionHeader32 with Name -// field replaced by Go string. -type SectionHeader struct { - Name string - VirtualSize uint32 - VirtualAddress uint32 - Size uint32 - Offset uint32 - PointerToRelocations uint32 - PointerToLineNumbers uint32 - NumberOfRelocations uint16 - NumberOfLineNumbers uint16 - Characteristics uint32 -} - -// Section provides access to PE COFF section. -type Section struct { - SectionHeader - Relocs []Reloc - - // Embed ReaderAt for ReadAt method. - // Do not embed SectionReader directly - // to avoid having Read and Seek. - // If a client wants Read and Seek it must use - // Open() to avoid fighting over the seek offset - // with other clients. - io.ReaderAt - sr *io.SectionReader -} - -// Data reads and returns the contents of the PE section s. -func (s *Section) Data() ([]byte, error) { - dat := make([]byte, s.sr.Size()) - n, err := s.sr.ReadAt(dat, 0) - if n == len(dat) { - err = nil - } - return dat[0:n], err -} - -// Open returns a new ReadSeeker reading the PE section s. -func (s *Section) Open() io.ReadSeeker { - return io.NewSectionReader(s.sr, 0, 1<<63-1) -} diff --git a/src/cmd/link/internal/pe/string.go b/src/cmd/link/internal/pe/string.go deleted file mode 100644 index dd0df7f3fd..0000000000 --- a/src/cmd/link/internal/pe/string.go +++ /dev/null @@ -1,67 +0,0 @@ -// Copyright 2016 The Go Authors. All rights reserved. -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. - -package pe - -import ( - "encoding/binary" - "fmt" - "io" - "os" -) - -// cstring converts ASCII byte sequence b to string. -// It stops once it finds 0 or reaches end of b. -func cstring(b []byte) string { - var i int - for i = 0; i < len(b) && b[i] != 0; i++ { - } - return string(b[:i]) -} - -// StringTable is a COFF string table. -type StringTable []byte - -func readStringTable(fh *FileHeader, r io.ReadSeeker) (StringTable, error) { - // COFF string table is located right after COFF symbol table. - if fh.PointerToSymbolTable <= 0 { - return nil, nil - } - offset := fh.PointerToSymbolTable + COFFSymbolSize*fh.NumberOfSymbols - _, err := r.Seek(int64(offset), os.SEEK_SET) - if err != nil { - return nil, fmt.Errorf("fail to seek to string table: %v", err) - } - var l uint32 - err = binary.Read(r, binary.LittleEndian, &l) - if err != nil { - return nil, fmt.Errorf("fail to read string table length: %v", err) - } - // string table length includes itself - if l <= 4 { - return nil, nil - } - l -= 4 - buf := make([]byte, l) - _, err = io.ReadFull(r, buf) - if err != nil { - return nil, fmt.Errorf("fail to read string table: %v", err) - } - return StringTable(buf), nil -} - -// TODO(brainman): decide if start parameter should be int instead of uint32 - -// String extracts string from COFF string table st at offset start. -func (st StringTable) String(start uint32) (string, error) { - // start includes 4 bytes of string table length - if start < 4 { - return "", fmt.Errorf("offset %d is before the start of string table", start) - } - start -= 4 - if int(start) > len(st) { - return "", fmt.Errorf("offset %d is beyond the end of string table", start) - } - return cstring(st[start:]), nil -} diff --git a/src/cmd/link/internal/pe/symbol.go b/src/cmd/link/internal/pe/symbol.go deleted file mode 100644 index 16ca91e58e..0000000000 --- a/src/cmd/link/internal/pe/symbol.go +++ /dev/null @@ -1,96 +0,0 @@ -// Copyright 2016 The Go Authors. All rights reserved. -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. - -package pe - -import ( - "encoding/binary" - "fmt" - "io" - "os" -) - -const COFFSymbolSize = 18 - -// COFFSymbol represents single COFF symbol table record. -type COFFSymbol struct { - Name [8]uint8 - Value uint32 - SectionNumber int16 - Type uint16 - StorageClass uint8 - NumberOfAuxSymbols uint8 -} - -func readCOFFSymbols(fh *FileHeader, r io.ReadSeeker) ([]COFFSymbol, error) { - if fh.NumberOfSymbols <= 0 { - return nil, nil - } - _, err := r.Seek(int64(fh.PointerToSymbolTable), os.SEEK_SET) - if err != nil { - return nil, fmt.Errorf("fail to seek to symbol table: %v", err) - } - syms := make([]COFFSymbol, fh.NumberOfSymbols) - err = binary.Read(r, binary.LittleEndian, syms) - if err != nil { - return nil, fmt.Errorf("fail to read symbol table: %v", err) - } - return syms, nil -} - -// isSymNameOffset checks symbol name if it is encoded as offset into string table. -func isSymNameOffset(name [8]byte) (bool, uint32) { - if name[0] == 0 && name[1] == 0 && name[2] == 0 && name[3] == 0 { - return true, binary.LittleEndian.Uint32(name[4:]) - } - return false, 0 -} - -// FullName finds real name of symbol sym. Normally name is stored -// in sym.Name, but if it is longer then 8 characters, it is stored -// in COFF string table st instead. -func (sym *COFFSymbol) FullName(st StringTable) (string, error) { - if ok, offset := isSymNameOffset(sym.Name); ok { - return st.String(offset) - } - return cstring(sym.Name[:]), nil -} - -func removeAuxSymbols(allsyms []COFFSymbol, st StringTable) ([]*Symbol, error) { - if len(allsyms) == 0 { - return nil, nil - } - syms := make([]*Symbol, 0) - aux := uint8(0) - for _, sym := range allsyms { - if aux > 0 { - aux-- - continue - } - name, err := sym.FullName(st) - if err != nil { - return nil, err - } - aux = sym.NumberOfAuxSymbols - s := &Symbol{ - Name: name, - Value: sym.Value, - SectionNumber: sym.SectionNumber, - Type: sym.Type, - StorageClass: sym.StorageClass, - } - syms = append(syms, s) - } - return syms, nil -} - -// Symbol is similar to COFFSymbol with Name field replaced -// by Go string. Symbol also does not have NumberOfAuxSymbols. -type Symbol struct { - Name string - Value uint32 - SectionNumber int16 - Type uint16 - StorageClass uint8 -} diff --git a/src/cmd/link/internal/pe/testdata/gcc-386-mingw-exec b/src/cmd/link/internal/pe/testdata/gcc-386-mingw-exec deleted file mode 100644 index 4b808d0432..0000000000 Binary files a/src/cmd/link/internal/pe/testdata/gcc-386-mingw-exec and /dev/null differ diff --git a/src/cmd/link/internal/pe/testdata/gcc-386-mingw-no-symbols-exec b/src/cmd/link/internal/pe/testdata/gcc-386-mingw-no-symbols-exec deleted file mode 100644 index 329dca60b9..0000000000 Binary files a/src/cmd/link/internal/pe/testdata/gcc-386-mingw-no-symbols-exec and /dev/null differ diff --git a/src/cmd/link/internal/pe/testdata/gcc-386-mingw-obj b/src/cmd/link/internal/pe/testdata/gcc-386-mingw-obj deleted file mode 100644 index 0c84d898d5..0000000000 Binary files a/src/cmd/link/internal/pe/testdata/gcc-386-mingw-obj and /dev/null differ diff --git a/src/cmd/link/internal/pe/testdata/gcc-amd64-mingw-exec b/src/cmd/link/internal/pe/testdata/gcc-amd64-mingw-exec deleted file mode 100644 index ce6feb6b7b..0000000000 Binary files a/src/cmd/link/internal/pe/testdata/gcc-amd64-mingw-exec and /dev/null differ diff --git a/src/cmd/link/internal/pe/testdata/gcc-amd64-mingw-obj b/src/cmd/link/internal/pe/testdata/gcc-amd64-mingw-obj deleted file mode 100644 index 48ae7921f3..0000000000 Binary files a/src/cmd/link/internal/pe/testdata/gcc-amd64-mingw-obj and /dev/null differ diff --git a/src/cmd/link/internal/pe/testdata/hello.c b/src/cmd/link/internal/pe/testdata/hello.c deleted file mode 100644 index a689d3644e..0000000000 --- a/src/cmd/link/internal/pe/testdata/hello.c +++ /dev/null @@ -1,8 +0,0 @@ -#include - -int -main(void) -{ - printf("hello, world\n"); - return 0; -} diff --git a/src/cmd/link/internal/pe/vendor.bash b/src/cmd/link/internal/pe/vendor.bash deleted file mode 100755 index 8a27ec8797..0000000000 --- a/src/cmd/link/internal/pe/vendor.bash +++ /dev/null @@ -1,31 +0,0 @@ -#!/usr/bin/env bash - -# Copyright 2016 The Go Authors. All rights reserved. -# Use of this source code is governed by a BSD-style -# license that can be found in the LICENSE file. - -# Run this script to obtain an up-to-date vendored version of debug/pe - -PEDIR=../../../../debug/pe - -# Start from scratch. -rm testdata/* -rm *.go -rmdir testdata - -# Copy all files. -mkdir testdata -cp $PEDIR/*.go . -cp $PEDIR/testdata/* ./testdata - -# go1.4 (bootstrap) does not know what io.SeekStart is. -sed -i 's|io.SeekStart|os.SEEK_SET|' *.go - -# goimports to clean up after sed -goimports -w . - -# gofmt to clean up after sed -gofmt -w . - -# Test that it works -go test -short diff --git a/src/debug/pe/file.go b/src/debug/pe/file.go index ef4ae352fe..87f225cb39 100644 --- a/src/debug/pe/file.go +++ b/src/debug/pe/file.go @@ -13,6 +13,9 @@ import ( "os" ) +// Avoid use of post-Go 1.4 io features, to make safe for toolchain bootstrap. +const seekStart = 0 + // A File represents an open PE file. type File struct { FileHeader @@ -80,7 +83,7 @@ func NewFile(r io.ReaderAt) (*File, error) { } else { base = int64(0) } - sr.Seek(base, io.SeekStart) + sr.Seek(base, seekStart) if err := binary.Read(sr, binary.LittleEndian, &f.FileHeader); err != nil { return nil, err } @@ -109,7 +112,7 @@ func NewFile(r io.ReaderAt) (*File, error) { } // Read optional header. - sr.Seek(base, io.SeekStart) + sr.Seek(base, seekStart) if err := binary.Read(sr, binary.LittleEndian, &f.FileHeader); err != nil { return nil, err } diff --git a/src/debug/pe/section.go b/src/debug/pe/section.go index 5d881577d3..b641158ecc 100644 --- a/src/debug/pe/section.go +++ b/src/debug/pe/section.go @@ -53,7 +53,7 @@ func readRelocs(sh *SectionHeader, r io.ReadSeeker) ([]Reloc, error) { if sh.NumberOfRelocations <= 0 { return nil, nil } - _, err := r.Seek(int64(sh.PointerToRelocations), io.SeekStart) + _, err := r.Seek(int64(sh.PointerToRelocations), seekStart) if err != nil { return nil, fmt.Errorf("fail to seek to %q section relocations: %v", sh.Name, err) } diff --git a/src/debug/pe/string.go b/src/debug/pe/string.go index 357fcf4343..0155adf9f0 100644 --- a/src/debug/pe/string.go +++ b/src/debug/pe/string.go @@ -28,7 +28,7 @@ func readStringTable(fh *FileHeader, r io.ReadSeeker) (StringTable, error) { return nil, nil } offset := fh.PointerToSymbolTable + COFFSymbolSize*fh.NumberOfSymbols - _, err := r.Seek(int64(offset), io.SeekStart) + _, err := r.Seek(int64(offset), seekStart) if err != nil { return nil, fmt.Errorf("fail to seek to string table: %v", err) } diff --git a/src/debug/pe/symbol.go b/src/debug/pe/symbol.go index 3cf5a101e7..b7d5d09bcf 100644 --- a/src/debug/pe/symbol.go +++ b/src/debug/pe/symbol.go @@ -26,7 +26,7 @@ func readCOFFSymbols(fh *FileHeader, r io.ReadSeeker) ([]COFFSymbol, error) { if fh.NumberOfSymbols <= 0 { return nil, nil } - _, err := r.Seek(int64(fh.PointerToSymbolTable), io.SeekStart) + _, err := r.Seek(int64(fh.PointerToSymbolTable), seekStart) if err != nil { return nil, fmt.Errorf("fail to seek to symbol table: %v", err) }