-
Notifications
You must be signed in to change notification settings - Fork 18k
cmd/link: compilation failure on armv6/armv7 due to truncated relocations #58428
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Comments
Fixes golang#58428 Change-Id: I2e5c277cf609b98081f38da8de4716fd0cd8efdd
So the reference PR is over 6 years old now, and things have moved around in the linker. I noticed the |
@golang/compiler |
I'd be interested to know if the workaround in #58425 (comment) works here as well |
👋 Reporting in for the Grafana Agent team while @tpaschalis is out: I just tested the workaround from #58425 (comment). One of our binaries still gets linking errors for GOARCH=arm GOARM=7 even when using the workaround:
|
thanks for checking... does the same issue reproduce with go1.19.5 (dropping the |
Yes, we first started to observe this with go1.19.4, and I'm able to locally reproduce the same issue using go1.19.5 as well. |
That's a helpful data point, thanks... sounds like this particular build / set of dependencies comes up "unlucky" as described in #57410 (comment), unrelated to changes in the go compiler to switch to the unified compiler frontend between go1.19 and go1.20 |
dup of #58425 |
Change https://go.dev/cl/467715 mentions this issue: |
Fix a problem with trampoline generation for ARM that was causing link failures when building selected k8s targets. Representative error (this is coming from the external linker): go.go:(.text+...): relocation truncated to fit: R_ARM_CALL against `runtime.duffcopy' The Go linker is supposed to be limiting text section size for ARM to 0x1c00000 bytes, however due to a problem in the tramp generation phase this limit wasn't being enforced. Updates #58428. Fixes #58425. Change-Id: I4e778bdcbebeab607a6e626b354ca5109e52a1aa Reviewed-on: https://go-review.googlesource.com/c/go/+/467715 Run-TryBot: Than McIntosh <[email protected]> Reviewed-by: David Chase <[email protected]> TryBot-Result: Gopher Robot <[email protected]>
Change https://go.dev/cl/468537 mentions this issue: |
Change https://go.dev/cl/468538 mentions this issue: |
Change https://go.dev/cl/469275 mentions this issue: |
Fix a problem with trampoline generation for ARM that was causing link failures when building selected k8s targets. Representative error (this is coming from the external linker): go.go:(.text+...): relocation truncated to fit: R_ARM_CALL against `runtime.duffcopy' The Go linker is supposed to be limiting text section size for ARM to 0x1c00000 bytes, however due to a problem in the tramp generation phase this limit wasn't being enforced. Updates golang#58428. Fixes golang#58425. Change-Id: I4e778bdcbebeab607a6e626b354ca5109e52a1aa Reviewed-on: https://go-review.googlesource.com/c/go/+/467715 Run-TryBot: Than McIntosh <[email protected]> Reviewed-by: David Chase <[email protected]> TryBot-Result: Gopher Robot <[email protected]>
Change https://go.dev/cl/471596 mentions this issue: |
This patch provides a fix for a problem linking large arm32 binaries with external linking, specifically R_CALLARM relocations against runtime.duff* routines being flagged by the external linker as not reaching. What appears to be happening in the bug in question is that the Go linker and the external linker are using slightly different recipes to decide whether a given R_CALLARM relocation will "fit" (e.g. will not require a trampoline). The Go linker is taking into account the addend on the call reloc (which for calls to runtime.duffcopy or runtime.duffzero is nonzero), whereas the external linker appears to be ignoring the addend. Example to illustrate: Addr Size Func ----- ----- ----- ... XYZ 1024 runtime.duffcopy ... ABC ... mypackge.MyFunc + R0: R_CALLARM o=8 a=848 tgt=runtime.duffcopy<0> Let's say that the distance between ABC (start address of runtime.duffcopy) and XYZ (start of MyFunc) is just over the architected 24-bit maximum displacement for an R_CALLARM (let's say that ABC-XYZ is just over the architected limit by some small value, say 36). Because we're calling into runtime.duffcopy at offset 848, however, the relocation does in fact fit, but if the external linker isn't taking into account the addend (assuming that all calls target the first instruction of the called routine), then we'll get a "doesn't fit" error from the linker. To work around this problem, revise the ARM trampoline generation code in the Go linker that computes the trampoline threshold to ignore the addend on R_CALLARM relocations, so as to harmonize the two linkers. Updates #58428. Updates #58425. Change-Id: I56e580c05b7b47bbe8edf5532a1770bbd700fbe5 Reviewed-on: https://go-review.googlesource.com/c/go/+/469275 TryBot-Result: Gopher Robot <[email protected]> Reviewed-by: Cherry Mui <[email protected]> Run-TryBot: Than McIntosh <[email protected]>
This patch backs out CL 467715 (written to fix 58425), now that we have a better fix for the "relocation doesn't fit" problem in the trampoline generation phase (send in a previous CL). Updates #58428. Updates #58425. Change-Id: Ib0d966fed00bd04db7ed85aa4e9132382b979a44 Reviewed-on: https://go-review.googlesource.com/c/go/+/471596 Run-TryBot: Than McIntosh <[email protected]> TryBot-Result: Gopher Robot <[email protected]> Reviewed-by: Cherry Mui <[email protected]>
Change https://go.dev/cl/471597 mentions this issue: |
Change https://go.dev/cl/471598 mentions this issue: |
…em with duff routines This patch provides a fix for a problem linking large arm32 binaries with external linking, specifically R_CALLARM relocations against runtime.duff* routines being flagged by the external linker as not reaching. What appears to be happening in the bug in question is that the Go linker and the external linker are using slightly different recipes to decide whether a given R_CALLARM relocation will "fit" (e.g. will not require a trampoline). The Go linker is taking into account the addend on the call reloc (which for calls to runtime.duffcopy or runtime.duffzero is nonzero), whereas the external linker appears to be ignoring the addend. Example to illustrate: Addr Size Func ----- ----- ----- ... XYZ 1024 runtime.duffcopy ... ABC ... mypackge.MyFunc + R0: R_CALLARM o=8 a=848 tgt=runtime.duffcopy<0> Let's say that the distance between ABC (start address of runtime.duffcopy) and XYZ (start of MyFunc) is just over the architected 24-bit maximum displacement for an R_CALLARM (let's say that ABC-XYZ is just over the architected limit by some small value, say 36). Because we're calling into runtime.duffcopy at offset 848, however, the relocation does in fact fit, but if the external linker isn't taking into account the addend (assuming that all calls target the first instruction of the called routine), then we'll get a "doesn't fit" error from the linker. To work around this problem, revise the ARM trampoline generation code in the Go linker that computes the trampoline threshold to ignore the addend on R_CALLARM relocations, so as to harmonize the two linkers. Fixes #58502. Updates #58428. Updates #58425. Change-Id: I56e580c05b7b47bbe8edf5532a1770bbd700fbe5 Reviewed-on: https://go-review.googlesource.com/c/go/+/469275 TryBot-Result: Gopher Robot <[email protected]> Reviewed-by: Cherry Mui <[email protected]> Run-TryBot: Than McIntosh <[email protected]> (cherry picked from commit 0b5affb) Reviewed-on: https://go-review.googlesource.com/c/go/+/471598
…em with duff routines This patch provides a fix for a problem linking large arm32 binaries with external linking, specifically R_CALLARM relocations against runtime.duff* routines being flagged by the external linker as not reaching. What appears to be happening in the bug in question is that the Go linker and the external linker are using slightly different recipes to decide whether a given R_CALLARM relocation will "fit" (e.g. will not require a trampoline). The Go linker is taking into account the addend on the call reloc (which for calls to runtime.duffcopy or runtime.duffzero is nonzero), whereas the external linker appears to be ignoring the addend. Example to illustrate: Addr Size Func ----- ----- ----- ... XYZ 1024 runtime.duffcopy ... ABC ... mypackge.MyFunc + R0: R_CALLARM o=8 a=848 tgt=runtime.duffcopy<0> Let's say that the distance between ABC (start address of runtime.duffcopy) and XYZ (start of MyFunc) is just over the architected 24-bit maximum displacement for an R_CALLARM (let's say that ABC-XYZ is just over the architected limit by some small value, say 36). Because we're calling into runtime.duffcopy at offset 848, however, the relocation does in fact fit, but if the external linker isn't taking into account the addend (assuming that all calls target the first instruction of the called routine), then we'll get a "doesn't fit" error from the linker. To work around this problem, revise the ARM trampoline generation code in the Go linker that computes the trampoline threshold to ignore the addend on R_CALLARM relocations, so as to harmonize the two linkers. Fixes #58503. Updates #58428. Updates #58425. Change-Id: I56e580c05b7b47bbe8edf5532a1770bbd700fbe5 Reviewed-on: https://go-review.googlesource.com/c/go/+/469275 TryBot-Result: Gopher Robot <[email protected]> Reviewed-by: Cherry Mui <[email protected]> Run-TryBot: Than McIntosh <[email protected]> (cherry picked from commit 0b5affb) Reviewed-on: https://go-review.googlesource.com/c/go/+/471597
…em with duff routines This patch provides a fix for a problem linking large arm32 binaries with external linking, specifically R_CALLARM relocations against runtime.duff* routines being flagged by the external linker as not reaching. What appears to be happening in the bug in question is that the Go linker and the external linker are using slightly different recipes to decide whether a given R_CALLARM relocation will "fit" (e.g. will not require a trampoline). The Go linker is taking into account the addend on the call reloc (which for calls to runtime.duffcopy or runtime.duffzero is nonzero), whereas the external linker appears to be ignoring the addend. Example to illustrate: Addr Size Func ----- ----- ----- ... XYZ 1024 runtime.duffcopy ... ABC ... mypackge.MyFunc + R0: R_CALLARM o=8 a=848 tgt=runtime.duffcopy<0> Let's say that the distance between ABC (start address of runtime.duffcopy) and XYZ (start of MyFunc) is just over the architected 24-bit maximum displacement for an R_CALLARM (let's say that ABC-XYZ is just over the architected limit by some small value, say 36). Because we're calling into runtime.duffcopy at offset 848, however, the relocation does in fact fit, but if the external linker isn't taking into account the addend (assuming that all calls target the first instruction of the called routine), then we'll get a "doesn't fit" error from the linker. To work around this problem, revise the ARM trampoline generation code in the Go linker that computes the trampoline threshold to ignore the addend on R_CALLARM relocations, so as to harmonize the two linkers. Fixes golang#58503. Updates golang#58428. Updates golang#58425. Change-Id: I56e580c05b7b47bbe8edf5532a1770bbd700fbe5 Reviewed-on: https://go-review.googlesource.com/c/go/+/469275 TryBot-Result: Gopher Robot <[email protected]> Reviewed-by: Cherry Mui <[email protected]> Run-TryBot: Than McIntosh <[email protected]> (cherry picked from commit 0b5affb) Reviewed-on: https://go-review.googlesource.com/c/go/+/471597
What version of Go are you using (
go version
)?Does this issue reproduce with the latest release?
Yes
What operating system and processor architecture are you using (
go env
)?The following is for the build container that cross-compiles to armv6/armv7 and encounters the failure
go env
OutputWhat did you do?
reproduce-relocation-truncated
branch or grafana/agent@7e4cae2USE_CONTAINER=1 GOOS=linux GOARCH=arm GOARM=6 make agentctl
to cross-compile theagentctl
binary for ARMv6What did you expect to see?
A successful compilation
What did you see instead?
Background
Hello team! I'm opening this issue on behalf of the Grafana Agent squad.
Recently, we saw our ARMv6 and ARMv6 builds start to fail with
relocation truncated to fit:
errors.We think it has to do with the growing binary size and the number of dependencies that the Agent brings in. Looking at the GCC arm-specific options, we used the
-mlong-calls
flag for our ARM builds which hid the issue for a few more commits, until it resurfaced.We also discovered #15823 for a similar issue around builds, but for a different architecture
ppc64le
which was fixed at the language level in CL27790. Do you think this is similar enough?Some other information that might be useful:
gcc
for the GOOS/GOARCH/GOARM tuple and calls out to it; in this casearm-linux-gnueabi-gcc
installed from Debian bullseye is usedThe text was updated successfully, but these errors were encountered: