mirror of
https://github.com/golang/go.git
synced 2026-06-28 03:40:37 +00:00
cmd/go: force external linking when CGO_LDFLAGS contains static-linking flags
When CGO_LDFLAGS contains flags that trigger static linking (-static,
--static, -Wl,-static, -Wl,--static, -Wl,-Bstatic), the internal
linker cannot resolve libc symbols, producing errors like "relocation
target stderr not defined".
Add checkLinkerFlagsForInternalLink, mirroring the existing
checkCompilerFlagsForInternalLink, to detect these flags in CGO_LDFLAGS
and emit the preferlinkext token to fall back to external linking.
Also check for -static/--static in compiler flags (CGO_CFLAGS etc.),
which some toolchains accept.
Fixes #77768
Change-Id: I5cbbc3cd30880ccf49dd575dd65188d9935d9488
GitHub-Last-Rev: 215efb6360
GitHub-Pull-Request: golang/go#79331
Reviewed-on: https://go-review.googlesource.com/c/go/+/776760
LUCI-TryBot-Result: golang-scoped@luci-project-accounts.iam.gserviceaccount.com <golang-scoped@luci-project-accounts.iam.gserviceaccount.com>
Reviewed-by: Cherry Mui <cherryyz@google.com>
Reviewed-by: Ian Lance Taylor <iant@golang.org>
Auto-Submit: Ian Lance Taylor <iant@golang.org>
Reviewed-by: Dmitri Shuralyov <dmitshur@google.com>
This commit is contained in:
parent
cd913caa3f
commit
42bdffec2d
3 changed files with 59 additions and 0 deletions
|
|
@ -2985,6 +2985,11 @@ func (b *Builder) runCgo(ctx context.Context, a *Action) error {
|
|||
flagSources := []string{"CGO_CFLAGS", "CGO_CXXFLAGS", "CGO_FFLAGS"}
|
||||
flagLists := [][]string{cgoCFLAGS, cgoCXXFLAGS, cgoFFLAGS}
|
||||
notCompatibleWithInternalLinking := flagsNotCompatibleWithInternalLinking(flagSources, flagLists)
|
||||
if !notCompatibleWithInternalLinking {
|
||||
if err := checkLinkerFlagsForInternalLink("CGO_LDFLAGS", "CGO_LDFLAGS", cgoLDFLAGS); err != nil {
|
||||
notCompatibleWithInternalLinking = true
|
||||
}
|
||||
}
|
||||
|
||||
if cfg.BuildMSan {
|
||||
cgoCFLAGS = append([]string{"-fsanitize=memory"}, cgoCFLAGS...)
|
||||
|
|
|
|||
|
|
@ -331,10 +331,34 @@ func checkCompilerFlagsForInternalLink(name, source string, list []string) error
|
|||
}
|
||||
// Currently the only flag on the allow list that causes problems
|
||||
// for the linker is "-flto"; check for it manually here.
|
||||
// Also check for -static/--static, which some toolchains accept
|
||||
// as a compiler flag.
|
||||
for _, fl := range list {
|
||||
if strings.HasPrefix(fl, "-flto") {
|
||||
return fmt.Errorf("flag %q triggers external linking", fl)
|
||||
}
|
||||
if fl == "-static" || fl == "--static" {
|
||||
return fmt.Errorf("flag %q triggers external linking", fl)
|
||||
}
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
// checkLinkerFlagsForInternalLink returns an error if 'list'
|
||||
// contains linker flags that are not compatible with internal linking.
|
||||
func checkLinkerFlagsForInternalLink(name, source string, list []string) error {
|
||||
checkOverrides := false
|
||||
if err := checkFlags(name, source, list, nil, validLinkerFlags, validLinkerFlagsWithNextArg, checkOverrides); err != nil {
|
||||
return err
|
||||
}
|
||||
// Flags that force static linking require the external linker
|
||||
// to resolve libc symbols. See #77768.
|
||||
for _, fl := range list {
|
||||
if fl == "-static" || fl == "--static" ||
|
||||
fl == "-Wl,-static" || fl == "-Wl,--static" ||
|
||||
fl == "-Wl,-Bstatic" {
|
||||
return fmt.Errorf("flag %q triggers external linking", fl)
|
||||
}
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
|
|
|||
|
|
@ -91,6 +91,36 @@ go build -x -n -o dummy.exe ./usesInternalCgo
|
|||
! stderr preferlinkext
|
||||
env CGO_CFLAGS=
|
||||
|
||||
# CGO_LDFLAGS with -static variants are not compatible with internal linking.
|
||||
env CGO_LDFLAGS=-static
|
||||
go build -x -n -o dummy.exe ./usesInternalCgo
|
||||
stderr preferlinkext
|
||||
env CGO_LDFLAGS=--static
|
||||
go build -x -n -o dummy.exe ./usesInternalCgo
|
||||
stderr preferlinkext
|
||||
env CGO_LDFLAGS=-Wl,-static
|
||||
go build -x -n -o dummy.exe ./usesInternalCgo
|
||||
stderr preferlinkext
|
||||
env CGO_LDFLAGS=-Wl,--static
|
||||
go build -x -n -o dummy.exe ./usesInternalCgo
|
||||
stderr preferlinkext
|
||||
env CGO_LDFLAGS=-Wl,-Bstatic
|
||||
go build -x -n -o dummy.exe ./usesInternalCgo
|
||||
stderr preferlinkext
|
||||
env CGO_LDFLAGS=
|
||||
|
||||
# CGO_LDFLAGS=-static-libgcc does NOT trigger external linking.
|
||||
env CGO_LDFLAGS=-static-libgcc
|
||||
go build -x -n -o dummy.exe ./usesInternalCgo
|
||||
! stderr preferlinkext
|
||||
env CGO_LDFLAGS=
|
||||
|
||||
# CGO_CFLAGS=--static triggers external linking (some toolchains accept it).
|
||||
env CGO_CFLAGS=--static
|
||||
go build -x -n -o dummy.exe ./usesInternalCgo
|
||||
stderr preferlinkext
|
||||
env CGO_CFLAGS=
|
||||
|
||||
[short] skip
|
||||
|
||||
# In the remaining tests below we do actual builds (without -n) to
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue