aboutsummaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/cmd/compile/internal/gc/gsubr.go19
1 files changed, 15 insertions, 4 deletions
diff --git a/src/cmd/compile/internal/gc/gsubr.go b/src/cmd/compile/internal/gc/gsubr.go
index 6e9f80a89d..827ccf3696 100644
--- a/src/cmd/compile/internal/gc/gsubr.go
+++ b/src/cmd/compile/internal/gc/gsubr.go
@@ -201,7 +201,8 @@ func (f *Func) initLSym(hasBody bool) {
var aliasABI obj.ABI
needABIAlias := false
- if abi, ok := symabiDefs[f.lsym.Name]; ok && abi == obj.ABI0 {
+ defABI, hasDefABI := symabiDefs[f.lsym.Name]
+ if hasDefABI && defABI == obj.ABI0 {
// Symbol is defined as ABI0. Create an
// Internal -> ABI0 wrapper.
f.lsym.SetABI(obj.ABI0)
@@ -215,9 +216,19 @@ func (f *Func) initLSym(hasBody bool) {
}
}
- if abi, ok := symabiRefs[f.lsym.Name]; ok && abi == obj.ABI0 {
- // Symbol is referenced as ABI0. Create an
- // ABI0 -> Internal wrapper if necessary.
+ isLinknameExported := nam.Sym.Linkname != "" && (hasBody || hasDefABI)
+ if abi, ok := symabiRefs[f.lsym.Name]; (ok && abi == obj.ABI0) || isLinknameExported {
+ // Either 1) this symbol is definitely
+ // referenced as ABI0 from this package; or 2)
+ // this symbol is defined in this package but
+ // given a linkname, indicating that it may be
+ // referenced from another package. Create an
+ // ABI0 -> Internal wrapper so it can be
+ // called as ABI0. In case 2, it's important
+ // that we know it's defined in this package
+ // since other packages may "pull" symbols
+ // using linkname and we don't want to create
+ // duplicate ABI wrappers.
if f.lsym.ABI() != obj.ABI0 {
needABIAlias, aliasABI = true, obj.ABI0
}