summaryrefslogtreecommitdiff
path: root/src/cmd/internal/goobj/read.go
diff options
context:
space:
mode:
authorAustin Clements <austin@google.com>2018-10-26 13:53:02 -0400
committerAustin Clements <austin@google.com>2018-11-12 20:46:48 +0000
commitc5718b6b261a66aa47312037f17281d3d810c98c (patch)
treeee975d089cb20dc038be7e1a4e68030a80615fe9 /src/cmd/internal/goobj/read.go
parent07544c7e80a7559973930befca8c8744f43df3ce (diff)
downloadgo-git-c5718b6b261a66aa47312037f17281d3d810c98c.tar.gz
cmd/internal/obj, cmd/link: record ABIs and aliases in Go obj files
This repurposes the "version" field of a symbol reference in the Go object file format to be an ABI field. Currently, this is just 0 or 1 depending on whether the symbol is static (the linker turns it into a different internal version number), so it's already only tenuously a symbol version. We change this to be -1 for static symbols and otherwise by the ABI number. This also adds a separate list of ABI alias symbols to be recorded in the object file. The ABI aliases must be a separate list and not just part of the symbol definitions because it's possible to have a symbol defined in one package and the alias "defined" in a different package. For example, this can happen if a symbol is defined in assembly in one package and stubbed in a different package. The stub triggers the generation of the ABI alias, but in a different package from the definition. For #27539. Change-Id: I015c9fe54690c027de6ef77e22b5585976a01587 Reviewed-on: https://go-review.googlesource.com/c/147157 Run-TryBot: Austin Clements <austin@google.com> TryBot-Result: Gobot Gobot <gobot@golang.org> Reviewed-by: David Chase <drchase@google.com>
Diffstat (limited to 'src/cmd/internal/goobj/read.go')
-rw-r--r--src/cmd/internal/goobj/read.go29
1 files changed, 21 insertions, 8 deletions
diff --git a/src/cmd/internal/goobj/read.go b/src/cmd/internal/goobj/read.go
index 2d618eefa5..2081098ca8 100644
--- a/src/cmd/internal/goobj/read.go
+++ b/src/cmd/internal/goobj/read.go
@@ -288,18 +288,31 @@ func (r *objReader) readSymID() SymID {
}
func (r *objReader) readRef() {
- name, vers := r.readString(), r.readInt()
+ name, abiOrStatic := r.readString(), r.readInt()
// In a symbol name in an object file, "". denotes the
// prefix for the package in which the object file has been found.
// Expand it.
name = strings.ReplaceAll(name, `"".`, r.pkgprefix)
- // An individual object file only records version 0 (extern) or 1 (static).
- // To make static symbols unique across all files being read, we
- // replace version 1 with the version corresponding to the current
- // file number. The number is incremented on each call to parseObject.
- if vers != 0 {
+ // The ABI field records either the ABI or -1 for static symbols.
+ //
+ // To distinguish different static symbols with the same name,
+ // we use the symbol "version". Version 0 corresponds to
+ // global symbols, and each file has a unique version > 0 for
+ // all of its static symbols. The version is incremented on
+ // each call to parseObject.
+ //
+ // For global symbols, we currently ignore the ABI.
+ //
+ // TODO(austin): Record the ABI in SymID. Since this is a
+ // public API, we'll have to keep Version as 0 and record the
+ // ABI in a new field (which differs from how the linker does
+ // this, but that's okay). Show the ABI in things like
+ // objdump.
+ var vers int64
+ if abiOrStatic == -1 {
+ // Static symbol
vers = r.p.MaxVersion
}
r.p.SymRefs = append(r.p.SymRefs, SymID{name, vers})
@@ -487,7 +500,7 @@ func (r *objReader) parseObject(prefix []byte) error {
// TODO: extract OS + build ID if/when we need it
r.readFull(r.tmp[:8])
- if !bytes.Equal(r.tmp[:8], []byte("\x00\x00go19ld")) {
+ if !bytes.Equal(r.tmp[:8], []byte("\x00go112ld")) {
return r.error(errCorruptObject)
}
@@ -602,7 +615,7 @@ func (r *objReader) parseObject(prefix []byte) error {
}
r.readFull(r.tmp[:7])
- if !bytes.Equal(r.tmp[:7], []byte("\xffgo19ld")) {
+ if !bytes.Equal(r.tmp[:7], []byte("go112ld")) {
return r.error(errCorruptObject)
}