]> Cypherpunks repositories - gostls13.git/commitdiff
cmd/link: handle R_GOTPCREL separately on darwin
authorDavid Crawshaw <crawshaw@golang.org>
Mon, 14 Nov 2016 02:20:58 +0000 (21:20 -0500)
committerDavid Crawshaw <crawshaw@golang.org>
Wed, 16 Nov 2016 18:37:03 +0000 (18:37 +0000)
To generate the correct section offset the shared code path for
R_CALL, R_PCREL, and R_GOTPCREL on darwin when externally linking
walks up the symbol heirarchy adding the differences. This is fine,
except in the case where we are generating a GOT lookup, because
the topmost symbol is left in r.Xsym instead of the symbol we are
looking up. So all funcsym GOT lookups were looking up the outer
"go.func.*" symbol.

Fix this by separating out the R_GOTPCREL code path.

For #17828 (and may fix it).

Change-Id: I2c9f4d135e77c17270aa064d8c876dc6d485d659
Reviewed-on: https://go-review.googlesource.com/33211
Run-TryBot: David Crawshaw <crawshaw@golang.org>
TryBot-Result: Gobot Gobot <gobot@golang.org>
Reviewed-by: Ian Lance Taylor <iant@golang.org>
misc/cgo/testplugin/src/plugin1/plugin1.go
src/cmd/link/internal/ld/data.go

index c3966f34014ca7b23c3a29c61e352636bbceece4..7a62242134338e63a3b3e408b17b769425f900bb 100644 (file)
@@ -17,9 +17,17 @@ func ReadCommonX() int {
 
 var Seven int
 
+func call(fn func()) {
+       fn()
+}
+
+func g() {
+       common.X *= Seven
+}
+
 func init() {
        Seven = 7
-       common.X *= Seven
+       call(g)
 }
 
 func main() {
index 7dff9baaeafa37af49e3ae481c2c44c36d1f4291..de043305d0c525e847759d3e748ce32fb4f381fc 100644 (file)
@@ -599,7 +599,19 @@ func relocsym(ctxt *Link, s *Symbol) {
                        }
 
                        // r->sym can be null when CALL $(constant) is transformed from absolute PC to relative PC call.
-               case obj.R_CALL, obj.R_GOTPCREL, obj.R_PCREL:
+               case obj.R_GOTPCREL:
+                       if ctxt.DynlinkingGo() && Headtype == obj.Hdarwin && r.Sym != nil && r.Sym.Type != obj.SCONST {
+                               r.Done = 0
+                               r.Xadd = r.Add
+                               r.Xadd -= int64(r.Siz) // relative to address after the relocated chunk
+                               r.Xsym = r.Sym
+
+                               o = r.Xadd
+                               o += int64(r.Siz)
+                               break
+                       }
+                       fallthrough
+               case obj.R_CALL, obj.R_PCREL:
                        if Linkmode == LinkExternal && r.Sym != nil && r.Sym.Type != obj.SCONST && (r.Sym.Sect != s.Sect || r.Type == obj.R_GOTPCREL) {
                                r.Done = 0