In CL 326211 a change was made to switch "go.map.zero" symbols from
non-pkg DUPOK symbols to hashed symbols. The intent of this change was
ensure that in cases where there are multiple competing go.map.zero
symbols feeding into a link, the largest map.zero symbol is selected.
The change was buggy, however, and resulted in duplicate symbols in
the final binary (see bug cited below for details). This duplication
was relatively benign for linux/ELF, but causes duplicate definition
errors on Windows.
This patch switches "go.map.zero" symbols back from hashed symbols to
non-pkg DUPOK symbols, and updates the relevant code in the loader to
ensure that we do the right thing when there are multiple competing
DUPOK symbols with different sizes.
Fixes#47185.
Change-Id: I8aeb910c65827f5380144d07646006ba553c9251
Reviewed-on: https://go-review.googlesource.com/c/go/+/334930
Trust: Than McIntosh <thanm@google.com>
Run-TryBot: Than McIntosh <thanm@google.com>
TryBot-Result: Go Bot <gobot@golang.org>
Reviewed-by: Cherry Mui <cherryyz@google.com>
The linker's -strictdups debugging option was not properly checking
for cases where you have two dupok BSS symbols with different length
(the check examined data length and content, but not symbol size).
Updates #46653.
Change-Id: I3844f25ef76dd6e4a84ffd5caed5d19a1b1a57c9
Reviewed-on: https://go-review.googlesource.com/c/go/+/326210
Trust: Than McIntosh <thanm@google.com>
Run-TryBot: Than McIntosh <thanm@google.com>
TryBot-Result: Go Bot <gobot@golang.org>
Reviewed-by: Cherry Mui <cherryyz@google.com>
Print the packages where the duplicates come from.
Change-Id: Ib3dc9aa0a3f5ddd97b03744be6d01d4bfcb33996
Reviewed-on: https://go-review.googlesource.com/c/go/+/315949
Trust: Cherry Zhang <cherryyz@google.com>
Run-TryBot: Cherry Zhang <cherryyz@google.com>
TryBot-Result: Go Bot <gobot@golang.org>
Reviewed-by: Than McIntosh <thanm@google.com>
PLT and GOT are used more than on PE. Update the comment.
Change-Id: Iaddb326680a7709a1442675a38c021331be32472
Reviewed-on: https://go-review.googlesource.com/c/go/+/314929
Trust: Cherry Zhang <cherryyz@google.com>
Reviewed-by: Than McIntosh <thanm@google.com>
Even if not presented with a valid symbol, recover gracefully,
so that debug prints do not crash.
Change-Id: I06bbe4bec5f90b79b4830e772a7fc3d7c919df1b
Reviewed-on: https://go-review.googlesource.com/c/go/+/312036
Trust: Russ Cox <rsc@golang.org>
Run-TryBot: Russ Cox <rsc@golang.org>
TryBot-Result: Go Bot <gobot@golang.org>
Reviewed-by: Cherry Zhang <cherryyz@google.com>
Currently, Go functions exported to cgo have some confusion around
ABIs that leads to crashes. The cmd/cgo-generated C code references an
exported Go wrapper function (which calls the underlying exported user
function). The linker resolves this reference to the ABI0 entry-point
to that Go wrapper function because all host object references are
currently assumed to be to version 0 of a symbol. This gets passed via
crosscall2 and winds its way to cgocallbackg1, which puts this ABI0
entry-point into a function value and calls it. Unfortunately,
function values always use the ABIInternal calling convention, so
calling this ABI0 entry-point goes poorly.
Fix this by threading definition ABIs through the cgo export mechanism
so the linker can resolve host object references (which have no
concept of multiple ABIs) to the correct Go symbol. This involves a
few pieces:
- The compiler extends the cgo_export_{static,dynamic} directives that
get passed on to the linker with symbol definition ABIs.
- The linker parses the ABIs in the cgo_export_{static,dynamic}
directives to look up the right symbol to apply export attributes to
and put in the dynexp list.
- For internal linking, the linker's Loader structure tracks the right
symbol (in particular the right ABI) to resolve host object
references to, and we use this in all of the host object loaders.
- For external linking, we mangle only the non-ABIInternal symbols
now, so the external linker is able to resolve the correct reference
from host objects to Go symbols.
Updates #40724.
Change-Id: I70a0b1610596768c3f473745fa1a3e630afbf1a8
Reviewed-on: https://go-review.googlesource.com/c/go/+/309341
Trust: Austin Clements <austin@google.com>
Run-TryBot: Austin Clements <austin@google.com>
TryBot-Result: Go Bot <gobot@golang.org>
Reviewed-by: Cherry Zhang <cherryyz@google.com>
Reviewed-by: Than McIntosh <thanm@google.com>
Change-Id: I207541efa6a34bc21e7a00584376622b59e2bf6d
Reviewed-on: https://go-review.googlesource.com/c/go/+/302749
Trust: Ian Lance Taylor <iant@golang.org>
Run-TryBot: Ian Lance Taylor <iant@golang.org>
Reviewed-by: Cherry Zhang <cherryyz@google.com>
TryBot-Result: Go Bot <gobot@golang.org>
Instead of using two relocation types R_XXX and R_WEAKXXX, use a
separate bit, R_WEAK, to mark weak relocations. This makes it
easier to add more weak relocation types.
Change-Id: Iec4195c2aefa65f59e464c83018246e17cd08173
Reviewed-on: https://go-review.googlesource.com/c/go/+/268478
Trust: Cherry Zhang <cherryyz@google.com>
Run-TryBot: Cherry Zhang <cherryyz@google.com>
TryBot-Result: Go Bot <gobot@golang.org>
Reviewed-by: Jeremy Faller <jeremy@golang.org>
Reviewed-by: Than McIntosh <thanm@google.com>
Currently, relocation type is stored as uint8 in object files, as
Go relocations do not exceed 255. In the linker, however, it is
used as a 16-bit type, because external relocations can exceed
255. The linker has to store the extra byte in a side table. This
complicates many things.
Just store it as uint16 in object files. This simplifies things,
with a small cost of increasing the object file sizes.
before after
hello.o 1672 1678
runtime.a 7927784 8056194
Change-Id: I313cf44ad0b8b3b76e35055ae55d911ff35e3158
Reviewed-on: https://go-review.googlesource.com/c/go/+/268477
Trust: Cherry Zhang <cherryyz@google.com>
Run-TryBot: Cherry Zhang <cherryyz@google.com>
TryBot-Result: Go Bot <gobot@golang.org>
Reviewed-by: Than McIntosh <thanm@google.com>
The runtime traceback code has its own definition of which functions
mark the top frame of a stack, separate from the TOPFRAME bits that
exist in the assembly and are passed along in DWARF information.
It's error-prone and redundant to have two different sources of truth.
This CL provides the actual TOPFRAME bits to the runtime, so that
the runtime can use those bits instead of reinventing its own category.
This CL also adds a new bit, SPWRITE, which marks functions that
write directly to SP (anything but adding and subtracting constants).
Such functions must stop a traceback, because the traceback has no
way to rederive the SP on entry. Again, the runtime has its own definition
which is mostly correct, but also missing some functions. During ordinary
goroutine context switches, such functions do not appear on the stack,
so the incompleteness in the runtime usually doesn't matter.
But profiling signals can arrive at any moment, and the runtime may
crash during traceback if it attempts to unwind an SP-writing frame
and gets out-of-sync with the actual stack. The runtime contains code
to try to detect likely candidates but again it is incomplete.
Deriving the SPWRITE bit automatically from the actual assembly code
provides the complete truth, and passing it to the runtime lets the
runtime use it.
This CL is part of a stack adding windows/arm64
support (#36439), intended to land in the Go 1.17 cycle.
This CL is, however, not windows/arm64-specific.
It is cleanup meant to make the port (and future ports) easier.
Change-Id: I227f53b23ac5b3dabfcc5e8ee3f00df4e113cf58
Reviewed-on: https://go-review.googlesource.com/c/go/+/288800
Trust: Russ Cox <rsc@golang.org>
Trust: Jason A. Donenfeld <Jason@zx2c4.com>
Reviewed-by: Cherry Zhang <cherryyz@google.com>
Reviewed-by: Jason A. Donenfeld <Jason@zx2c4.com>
If ABI wrappers are enabled, we should not see ABI aliases at
link time. Stop resolving them. One exception is shared linkage,
where we still use ABI aliases as we don't always know the ABI
for symbols from shared libraries.
Change-Id: Ia89a788094382adeb4c4ef9b0312aa6e8c2f79ef
Reviewed-on: https://go-review.googlesource.com/c/go/+/290032
TryBot-Result: Go Bot <gobot@golang.org>
Reviewed-by: Than McIntosh <thanm@google.com>
Trust: Cherry Zhang <cherryyz@google.com>
Run-TryBot: Cherry Zhang <cherryyz@google.com>
When the compiler refers to a runtime builtin, it emits an indexed
symbol reference in the object file via predetermined/preassigned ID
within the PkgIdxBuiltin pseudo-package. At link time when the loader
encounters these references, it redirects them to the corresponding
defined symbol in the runtime package. This redirection process
currently assumes that if a runtime builtin is referenced, we'll
always have a definition for it. This assumption holds in most cases,
however for the builtins "runtime.racefuncenter" and
"runtime.racefuncexit", we'll only see definitions if the runtime
package we're linking against was built with "-race".
In the bug in question, build passes "-gcflags=-race" during
compilation of the main package, but doesn't pass "-race" directly to
'go build', and as a result the final link combines a
race-instrumented main with a non-race runtime; this results in R_CALL
relocations with zero-valued target symbols, resulting in a panic
during stack checking.
This patch changes the loader's resolve method to detect situations
where we're asking for builtin "runtime.X", but the runtime package
read in doesn't contain a definition for X.
Fixes#42396.
Change-Id: Iafd38bd3b0f7f462868d120ccd4d7d1b88b27436
Reviewed-on: https://go-review.googlesource.com/c/go/+/267881
Trust: Than McIntosh <thanm@google.com>
Run-TryBot: Than McIntosh <thanm@google.com>
Reviewed-by: Jeremy Faller <jeremy@golang.org>
Reviewed-by: Cherry Zhang <cherryyz@google.com>
TryBot-Result: Go Bot <gobot@golang.org>
Cgo programs work as well. Still not enabled by default for now.
Enable internal linking tests.
Updates #38485.
Change-Id: I8324a5c263fba221eb4e67d71207ca84fa241e6c
Reviewed-on: https://go-review.googlesource.com/c/go/+/263637
Trust: Cherry Zhang <cherryyz@google.com>
Run-TryBot: Cherry Zhang <cherryyz@google.com>
TryBot-Result: Go Bot <gobot@golang.org>
Reviewed-by: Than McIntosh <thanm@google.com>
2 conflicts, that make sense.
src/cmd/internal/obj/objfile.go
src/cmd/link/internal/loader/loader.go
Change-Id: Ib224e2d248cb568fa1e888af79dd908b2f5e05ff
Type namedata symbols are for type/field/method names and package
paths. We can use content-addressable symbol mechanism for them.
Change-Id: I923fda17b7094c7a0e46aad7c450622eb3826294
Reviewed-on: https://go-review.googlesource.com/c/go/+/257960
Trust: Cherry Zhang <cherryyz@google.com>
Run-TryBot: Cherry Zhang <cherryyz@google.com>
TryBot-Result: Go Bot <gobot@golang.org>
Reviewed-by: Than McIntosh <thanm@google.com>
Reviewed-by: Jeremy Faller <jeremy@golang.org>
The linker prunes methods that are not directly reachable if the
receiver type is never converted to interface. Currently, this
"never" is too strong: it is invalidated even if the interface
conversion is in an unreachable function. This CL improves it by
only considering interface conversions in reachable code. To do
that, we introduce a marker relocation R_USEIFACE, which marks
the target symbol as UsedInIface if the source symbol is reached.
binary size before after
cmd/compile 18897528 18887400
cmd/go 13607372 13470652
Change-Id: I66c6b69eeff9ae02d84d2e6f2bc7f1b29dd53910
Reviewed-on: https://go-review.googlesource.com/c/go/+/256797
Trust: Cherry Zhang <cherryyz@google.com>
Reviewed-by: Jeremy Faller <jeremy@golang.org>
Reviewed-by: Than McIntosh <thanm@google.com>
Pre-resolve package index references, so it doesn't need to do a
map lookup in every cross-package symbol reference resolution. It
increases the memory usage very slightly (O(# imported packages)).
Change-Id: Ia76c97ac51f1c2c2d5ea7ae34853850ec69ef0a8
Reviewed-on: https://go-review.googlesource.com/c/go/+/253604
Run-TryBot: Cherry Zhang <cherryyz@google.com>
Reviewed-by: Than McIntosh <thanm@google.com>
TryBot-Result: Gobot Gobot <gobot@golang.org>
Switch pcdata over to content addressable symbols. This is the last
step before removing these from pclntab_old.
No meaningful benchmarks changes come from this work.
Change-Id: I3f74f3d6026a278babe437c8010e22992c92bd89
Reviewed-on: https://go-review.googlesource.com/c/go/+/247399
Reviewed-by: Austin Clements <austin@google.com>
Reviewed-by: Than McIntosh <thanm@google.com>
In order to prevent renumbering of filenames in pclntab generation, use
the per-package file list (previously only used for DWARF generation) as
file-indices. This is the largest step to eliminate renumbering of
filenames in pclntab.
Note, this is probably not the final state of the file table within the
object file. In this form, the linker loads all filenames for all
objects. I'll move to storing the filenames as regular string
symbols,and defaulting all string symbols to using the larger hash value
to make generation of pcln simplest, and most memory friendly.
Change-Id: I23daafa3f4b4535076e23100200ae0e7163aafe0
Reviewed-on: https://go-review.googlesource.com/c/go/+/245485
Run-TryBot: Jeremy Faller <jeremy@golang.org>
TryBot-Result: Gobot Gobot <gobot@golang.org>
Reviewed-by: Austin Clements <austin@google.com>
Currently, at compile time, for each itab symbol, we create an
"itablink" symbol which holds solely the address of the itab
symbol. At link time, all the itablink symbols are grouped
together to form the itablinks slice.
This CL removes the itablink symbols, and directly generate the
itablinks slice in the linker. This removes a number of symbols,
which are dupOK and generally have long names. And also removes
a special handling of itablink symbols in the deadcode pass which
iterates through all symbols.
Change-Id: I475c3c8899e9fbeec9abc7647b1e4a69aa5c3c5a
Reviewed-on: https://go-review.googlesource.com/c/go/+/245901
Reviewed-by: Jeremy Faller <jeremy@golang.org>
The hash maps are used to deduplicate hashed symbols. Once we
loaded all the symbols, we no longer need the hash maps. Drop
them.
Linking cmd/compile,
name old live-B new live-B delta
Loadlib_GC 13.1M ± 0% 11.3M ± 0% -13.62% (p=0.008 n=5+5)
Change-Id: I4bb1f84e1111a56d9e777cd6a68f7d974b60e321
Reviewed-on: https://go-review.googlesource.com/c/go/+/245721
Reviewed-by: Jeremy Faller <jeremy@golang.org>
Extend the content-addressable symbol mechanism to itab symbols.
Itab symbols require global uniqueness (as at run time we compare
pointers), so it needs to be reliably deduplicated. Currently the
content hash depends on symbol name expansion, so we can only do
this when all Go packages are built with know package paths. Fall
back to checking names if any Go package is built with unknown
package path.
Change-Id: Icf5e8873755050c20e5fc6549f6de1c883254c89
Reviewed-on: https://go-review.googlesource.com/c/go/+/245719
Reviewed-by: Jeremy Faller <jeremy@golang.org>
The type descriptor symbol of a defined (named) type (and pointer
to it) is defined only in the package that defines the type. It
is not dupOK, unlike other type descriptors. So it can be
referenced by index. Currently it is referenced by name for
cross-package references, because the index is not exported and
so not known to the referencing package.
This CL passes the index through the export data, so the symbol
can be referenced by index, and does not need to be looked up by
name. This also makes such symbol references consistent: it is
referenced by index within the defining package and also cross-
package, which makes it easier for content hashing (in later CLs).
One complication is that we need to set flags on referenced
symbols (specifically, the UsedInIface flag). Before, they are
non-package refs, which naturally carry flags in the object file.
For indexed refs, we currently don't put their flags in the
object file. Introduce a new block for this.
Change-Id: I8126f8e318ac4e6609eb2ac136201fd6c264c256
Reviewed-on: https://go-review.googlesource.com/c/go/+/245718
Reviewed-by: Jeremy Faller <jeremy@golang.org>
Leaving creation of the funcID till the linker requires the linker to
load the function and file names into memory. Moving these into the
compiler/assembler prevents this.
This work is a step towards moving all func metadata into the compiler.
Change-Id: Iebffdc5a909adbd03ac263fde3f4c3d492fb1eac
Reviewed-on: https://go-review.googlesource.com/c/go/+/244024
Run-TryBot: Jeremy Faller <jeremy@golang.org>
TryBot-Result: Gobot Gobot <gobot@golang.org>
Reviewed-by: Cherry Zhang <cherryyz@google.com>
Reviewed-by: Austin Clements <austin@google.com>
For dupOK symbols, their attributes should be OR'd. Most of the
attributes are expected to be set consistently across multiple
definitions, but UsedInIface must be OR'd, and for alignment we
need to pick the largest one. Currently the attributes are not
always OR'd, depending on addSym returning true or false. This
doesn't cause any real problem, but it would be a problem if we
make type descriptor symbols content-addressable.
This CL removes the second result of addSym, and lets preloadSyms
always set the attributes. Also removes the alignment handling on
addSym, handles it in preloadSyms only.
Change-Id: I06b3f0adb733f6681956ea9ef54736baa86ae7bc
Reviewed-on: https://go-review.googlesource.com/c/go/+/245720
Reviewed-by: Jeremy Faller <jeremy@golang.org>
Move the function names out of runtime.pclntab_old, creating
runtime.funcnametab. There is an unfortunate artifact in this change in
that calculating the funcID still requires loading the name. Future work
will likely pull this out and put it into the object file Funcs.
ls -l cmd/compile (darwin):
before: 18524016
after: 18519952
The difference in size can be attributed to alignment in pclntab_old.
Change-Id: Ibcbb230d4632178f8fcd0667165f5335786381f8
Reviewed-on: https://go-review.googlesource.com/c/go/+/243223
Reviewed-by: Austin Clements <austin@google.com>
Rename Reloc2 to Reloc, At2 to At, Aux2 to Aux.
Change-Id: Ic98d83c080e8cd80fbe1837c8f0aa134033508ce
Reviewed-on: https://go-review.googlesource.com/c/go/+/245578
Reviewed-by: Jeremy Faller <jeremy@golang.org>
We have Reloc and Reloc2. Reloc2 is the better approach and most
code uses Reloc2. There are still uses of Reloc. This CL migrates
them to Reloc2, and removes Reloc.
Change-Id: Id5f6a6019e1e044add682d05e70ebb1548ec58d9
Reviewed-on: https://go-review.googlesource.com/c/go/+/245577
Reviewed-by: Jeremy Faller <jeremy@golang.org>
We used to generate all external relocations in memory, then emit
the relocation records at a later pass. The data structures were
chosen so that it takes as little memory as possible. Now we just
stream out external relocations, and ExtReloc is just a local
variable. Change the data structure to avoid repeated read of
some fields. Also get rid of ExtRelocView, as it is no longer
necessary.
Change-Id: I40209bbe4387af231b29788125c3b4ebb0ff4a33
Reviewed-on: https://go-review.googlesource.com/c/go/+/245479
Run-TryBot: Cherry Zhang <cherryyz@google.com>
TryBot-Result: Gobot Gobot <gobot@golang.org>
Reviewed-by: Jeremy Faller <jeremy@golang.org>
OutData was used for a symbol to point to its data in the output
buffer, in order to apply relocations. Now we fold relocation
application to Asmb next to symbol data writing. We can just pass
the output data as a local variable.
Linking cmd/compile,
name old time/op new time/op delta
Asmb_GC 19.0ms ±10% 16.6ms ± 9% -12.50% (p=0.032 n=5+5)
name old alloc/op new alloc/op delta
Asmb_GC 3.78MB ± 0% 0.14MB ± 1% -96.41% (p=0.008 n=5+5)
name old live-B new live-B delta
Asmb_GC 27.5M ± 0% 23.9M ± 0% -13.24% (p=0.008 n=5+5)
Change-Id: Id870a10dce2a0a7447a05029c6d0ab39b47d0a12
Reviewed-on: https://go-review.googlesource.com/c/go/+/244017
Reviewed-by: Jeremy Faller <jeremy@golang.org>
For content-addressable symbols, we build its content hash based
on the symbol data and relocations. When the compiler builds the
symbol data, it may not always include the trailing zeros, e.g.
the data of [10]int64{1,2,3} is only the first 24 bytes.
Therefore, we may end up with symbols with the same contents
(thus same hash) but different sizes. This is not actually a hash
collision. In this case, we can deduplicate them and keep the one
with the larger size.
Change-Id: If6834542d7914cc00f917d7db151955e5aee6f30
Reviewed-on: https://go-review.googlesource.com/c/go/+/243718
Run-TryBot: Cherry Zhang <cherryyz@google.com>
TryBot-Result: Gobot Gobot <gobot@golang.org>
Reviewed-by: Jeremy Faller <jeremy@golang.org>
Currently, when external linking, in relocsym (in asmb pass), we
convert Go relocations to an in-memory representation of external
relocations, and then in asmb2 pass we write them out to the
output file. This is not memory efficient.
This CL makes it not do the conversion but directly stream out
the external relocations based on Go relocations. Currently only
do this on AMD64 ELF systems.
This reduces memory usage, but makes the asmb2 pass a little
slower.
Linking cmd/compile with external linking:
name old time/op new time/op delta
Asmb_GC 83.8ms ± 7% 70.4ms ± 4% -16.03% (p=0.008 n=5+5)
Asmb2_GC 95.6ms ± 4% 118.2ms ± 5% +23.65% (p=0.008 n=5+5)
TotalTime_GC 1.59s ± 2% 1.62s ± 1% ~ (p=0.151 n=5+5)
name old alloc/op new alloc/op delta
Asmb_GC 26.0MB ± 0% 4.1MB ± 0% -84.15% (p=0.008 n=5+5)
Asmb2_GC 8.19MB ± 0% 8.18MB ± 0% ~ (p=0.222 n=5+5)
name old live-B new live-B delta
Asmb_GC 49.2M ± 0% 27.4M ± 0% -44.38% (p=0.008 n=5+5)
Asmb2_GC 51.5M ± 0% 29.7M ± 0% -42.33% (p=0.008 n=5+5)
TODO: figure out what is slow. Possible improvements:
- Remove redundant work in relocsym.
- Maybe there is a better representation for external relocations
now.
- Fine-grained parallelism in emitting external relocations.
- The old elfrelocsect only iterates over external relocations,
now we iterate over all relocations. Is it too many?
Change-Id: Ib0a8ee8c88d65864c62b89a8d634614f7f2c813e
Reviewed-on: https://go-review.googlesource.com/c/go/+/242603
Run-TryBot: Cherry Zhang <cherryyz@google.com>
TryBot-Result: Gobot Gobot <gobot@golang.org>
Reviewed-by: Jeremy Faller <jeremy@golang.org>
For symbols of size 8 bytes or below, we can map them to 64-bit
hash values using the identity function. There is no need to use
longer and more expensive hash functions.
For them, we introduce another pseudo-package, PkgIdxHashed64. It
is like PkgIdxHashed except that the hash function is different.
Note that the hash value is not affected with trailing zeros,
e.g. "A" and "A\0\0\0" have the same hash value. This allows
deduplicating a few more symbols. When deduplicating them, we
need to keep the longer one.
Change-Id: Iad0c2e9e569b6a59ca6a121fb8c8f0c018c6da03
Reviewed-on: https://go-review.googlesource.com/c/go/+/242362
Reviewed-by: Jeremy Faller <jeremy@golang.org>
Fill in the data at compile time, and get rid of the preprocess
function in the linker.
We need to be careful with symbol alignment: data symbols are
generally naturally aligned, except for string symbols which are
not aligned. When deduplicating two symbols with same content but
different alignments, we need to keep the biggest alignment.
Change-Id: I4bd96adfdc5f704b5bf3a0e723457c9bfe16a684
Reviewed-on: https://go-review.googlesource.com/c/go/+/242081
Run-TryBot: Cherry Zhang <cherryyz@google.com>
TryBot-Result: Gobot Gobot <gobot@golang.org>
Reviewed-by: Jeremy Faller <jeremy@golang.org>
This CL introduces content-addressable symbols (a.k.a. hashed
symbols) to object files. Content-addressable symbols are
identified and referenced by their content hashes, instead of by
names.
In the object file, a new pseudo-package index PkgIdxHashed is
introduced, for content-addressable symbols, and a new block is
added to store their hashes. The hashes are used by the linker to
identify and deduplicate the symbols.
For now, we only support content-addressable symbols that are
always locally defined (i.e. no cross-package references).
As a proof of concept, make string constant symbols content-
addressable.
Change-Id: Iaf53efd74c0ffb54fa95f784628cc84e95844536
Reviewed-on: https://go-review.googlesource.com/c/go/+/242079
Run-TryBot: Cherry Zhang <cherryyz@google.com>
TryBot-Result: Gobot Gobot <gobot@golang.org>
Reviewed-by: Jeremy Faller <jeremy@golang.org>
Don't emit symbol table entries for compiler-generated file-local
symbols (this category includes .stmp_* temporaries and *.stkobj
symbols). Note that user-written static symbols within assembler
sources will still be added to the symbol table. Apply the same test
when emitting DWARF for global variables.
Change-Id: I4db77a2750a0b575e051dfea895c4742cf6709a6
Reviewed-on: https://go-review.googlesource.com/c/go/+/240539
Run-TryBot: Than McIntosh <thanm@google.com>
TryBot-Result: Gobot Gobot <gobot@golang.org>
Reviewed-by: Cherry Zhang <cherryyz@google.com>
Introduce a new loader method "SetCarrierSym", to be used when
establishing container/containee symbol relationships for symbol
bucketing in the symtab phase.
This new method is intended to be employed in situations where you
have a series of related symbols will be represented by a single
carrier symbol as a combined entity. The pattern here is that the
sub-symbols contain content but will be anonymous from a symbol table
perspective; the carrier symbol has no content itself but will appear
in the symbol table. Examples of carrier symbols that follow this
model are "runtime.itablink" and "runtime.typelink".
Change-Id: I1a3391a71062c7c740cb108b3fa210b7f69b81ed
Reviewed-on: https://go-review.googlesource.com/c/go/+/240509
Reviewed-by: Cherry Zhang <cherryyz@google.com>
Reviewed-by: Austin Clements <austin@google.com>
Reviewed-by: Jeremy Faller <jeremy@golang.org>
Introduce a new loader method "AddInteriorSym" to be used when
establishing container/containee symbol relationships for host object
sub-symbols and GOT/dynamic sub-symbols.
Interior symbols are employed in situations where you have a
"container" or "payload" symbol that has content, and then a series of
"interior" sub-symbols that point into a portion of the container
symbol's content. Each interior symbol will typically have a useful
name / size / value, but no content of its own. From a symbol table
perspective the container symbol is anonymous, but the interior
symbols are added to the output symbol table.
Change-Id: I919ed5dbbfe2ef2c9a76214f7ea9b384a1be6297
Reviewed-on: https://go-review.googlesource.com/c/go/+/240508
Reviewed-by: Austin Clements <austin@google.com>
Reviewed-by: Cherry Zhang <cherryyz@google.com>
Reviewed-by: Jeremy Faller <jeremy@golang.org>
Create a new class of symbols internal to the linker. These symbols live
in the Loader, and are real smybols, but have no data, only size. After
symbols are allocated in the binary in asmb() a function is called that
is responsible for filling in the data.
This allows the linker to create large symbols, but not pay the price on
the heap memory.
Change-Id: Ib4291fc6e578478057ed2ec163d7b27426f1d5ff
Reviewed-on: https://go-review.googlesource.com/c/go/+/239280
Run-TryBot: Jeremy Faller <jeremy@golang.org>
TryBot-Result: Gobot Gobot <gobot@golang.org>
Reviewed-by: Than McIntosh <thanm@google.com>
Reviewed-by: Cherry Zhang <cherryyz@google.com>
The Go compiler includes special treatment for a small set of very
commonly used type symbols (26 to be exact); for these types it
doesn't bother to emit type descriptors for "normal" compilations, and
instead only generates them for the runtime package, so as to reduce
object file bloat.
This patch moves the set of type symbols in question from the
PkgIdxNone index space (in the object file) to the PkgIdxBuiltin
space, which saves some work in the compiler and loader (reduces each
package's index space slightly).
Change-Id: I039c805e05c1aef26f035e52760fd0a0af40f7a5
Reviewed-on: https://go-review.googlesource.com/c/go/+/239658
Run-TryBot: Than McIntosh <thanm@google.com>
TryBot-Result: Gobot Gobot <gobot@golang.org>
Reviewed-by: Cherry Zhang <cherryyz@google.com>
Reviewed-by: Jeremy Faller <jeremy@golang.org>
Currently, a method of a reachable type is live if it matches a
method of a reachable interface. In fact, we only need to retain
the method if the type is actually converted to an interface. If
the type is never converted to an interface, there is no way to
call the method through an interface method call (but the type
descriptor could still be used, e.g. in calling
runtime.newobject).
A type can be used in an interface in two ways:
- directly converted to interface. (Any interface counts, as it
is possible to convert one interface to another.)
- obtained by reflection from a related type (e.g. obtaining an
interface of T from []T).
For the former, we let the compiler emit a marker on the type
descriptor symbol when it is converted to an interface. In the
linker, we only need to check methods of marked types.
For the latter, when the linker visits a marked type, it needs to
visit all its "child" types as marked (i.e. potentially could be
converted to interface).
This reduces binary size:
cmd/compile 18792016 18706096 (-0.5%)
cmd/go 14120572 13398948 (-5.1%)
Change-Id: I4465c7eeabf575f4dc84017214c610fa05ae31fd
Reviewed-on: https://go-review.googlesource.com/c/go/+/237298
Run-TryBot: Cherry Zhang <cherryyz@google.com>
TryBot-Result: Gobot Gobot <gobot@golang.org>
Reviewed-by: Than McIntosh <thanm@google.com>
Reviewed-by: Jeremy Faller <jeremy@golang.org>