cmd/link: attempt to rationalize linkmode init

This CL gives Linkmode a type, switches it to the standard flag
handling mechanism, and deduplicates some logic.

There is a semantic change in this CL. Previously if a link was
invoked explicitly with -linkmode=internal, any condition that forced
external linking would silently override this and use external
linking. Instead it now fails with a reason why. I believe this is an
improvement, but will change it back if there's disagreement.

Fixes #12848

Change-Id: Ic80e341fff65ecfdd2b6fdd6079674cc7210fc5f
Reviewed-on: https://go-review.googlesource.com/28971
Run-TryBot: David Crawshaw <crawshaw@golang.org>
TryBot-Result: Gobot Gobot <gobot@golang.org>
Reviewed-by: Ian Lance Taylor <iant@golang.org>
This commit is contained in:
David Crawshaw 2016-09-09 17:34:07 -04:00
parent 1df438f79c
commit 6007c8c76b
13 changed files with 250 additions and 338 deletions

View file

@ -198,7 +198,6 @@ var (
Headtype obj.HeadType
nerrors int
Linkmode int
liveness int64
)
@ -441,49 +440,12 @@ func (ctxt *Link) loadlib() {
}
}
if Linkmode == LinkAuto {
if iscgo && externalobj {
Linkmode = LinkExternal
} else {
Linkmode = LinkInternal
}
// We now have enough information to determine the link mode.
determineLinkMode(ctxt)
// Force external linking for android.
if obj.GOOS == "android" {
Linkmode = LinkExternal
}
// These build modes depend on the external linker
// to handle some relocations (such as TLS IE) not
// yet supported by the internal linker.
switch Buildmode {
case BuildmodeCArchive, BuildmodeCShared, BuildmodePIE, BuildmodePlugin, BuildmodeShared:
Linkmode = LinkExternal
}
if *FlagLinkshared {
Linkmode = LinkExternal
}
// cgo on Darwin must use external linking
// we can always use external linking, but then there will be circular
// dependency problems when compiling natively (external linking requires
// runtime/cgo, runtime/cgo requires cmd/cgo, but cmd/cgo needs to be
// compiled using external linking.)
if SysArch.InFamily(sys.ARM, sys.ARM64) && Headtype == obj.Hdarwin && iscgo {
Linkmode = LinkExternal
}
// Force external linking for msan.
if *flagMsan {
Linkmode = LinkExternal
}
}
// cmd/7l doesn't support cgo internal linking
// This is https://golang.org/issue/10373.
// mips64x doesn't support cgo internal linking either (golang.org/issue/14449)
if iscgo && (obj.GOARCH == "arm64" || obj.GOARCH == "mips64" || obj.GOARCH == "mips64le") {
Linkmode = LinkExternal
if Linkmode == LinkExternal && SysArch.Family == sys.PPC64 {
toc := Linklookup(ctxt, ".TOC.", 0)
toc.Type = obj.SDYNIMPORT
}
if Linkmode == LinkExternal && !iscgo {