]> Cypherpunks repositories - gostls13.git/commitdiff
[dev.link] cmd/link: support new dodata for PPC64
authorThan McIntosh <thanm@google.com>
Fri, 24 Apr 2020 19:32:46 +0000 (15:32 -0400)
committerThan McIntosh <thanm@google.com>
Mon, 27 Apr 2020 17:31:07 +0000 (17:31 +0000)
Add linux/{ppc64,ppc64le} and aix/ppc64 arch support for the new
dodata() phase.

This completes the picture in terms of architecture support for the
new dodata(), but to be safe this patch leaves the command line flag
in place there are problems on the builders (especially given that we
have a dead aix-ppc64 builder).

Change-Id: I78da615c3b540d8925ed7b3226e199280eb7451d
Reviewed-on: https://go-review.googlesource.com/c/go/+/229983
Reviewed-by: Cherry Zhang <cherryyz@google.com>
src/cmd/link/internal/ld/main.go
src/cmd/link/internal/ld/xcoff.go
src/cmd/link/internal/ld/xcoff2.go
src/cmd/link/internal/ppc64/asm.go
src/cmd/link/internal/ppc64/asm2.go [new file with mode: 0644]
src/cmd/link/internal/ppc64/obj.go

index 837cfe59ca4a5e31f5604c449e5a18471f8bdcb5..b97ccf0ec9704a81350e663325f27b3f34130757 100644 (file)
@@ -200,24 +200,6 @@ func Main(arch *sys.Arch, theArch Arch) {
        bench.Start("Archinit")
        thearch.Archinit(ctxt)
 
-       if *flagnewDoData {
-               // New dodata() is currently only implemented for selected targets.
-               switch {
-               case ctxt.IsElf():
-                       switch {
-                       case ctxt.Is386(), ctxt.IsAMD64(), ctxt.IsARM(), ctxt.IsARM64(),
-                               ctxt.IsMIPS(), ctxt.IsMIPS64(), ctxt.IsRISCV64(), ctxt.IsS390X():
-                               // supported
-                       default:
-                               *flagnewDoData = false
-                       }
-               case ctxt.IsDarwin(), ctxt.IsPlan9(), ctxt.IsWasm():
-                       // supported
-               default:
-                       *flagnewDoData = false
-               }
-       }
-
        if ctxt.linkShared && !ctxt.IsELF {
                Exitf("-linkshared can only be used on elf systems")
        }
index 379ecec6e74b7f68f70ce80eaa68b1e3ea90915c..f156cbf439f193b7f616a869aaa109c0572c1aff 100644 (file)
@@ -360,7 +360,8 @@ type XcoffLdRel64 struct {
 // xcoffLoaderReloc holds information about a relocation made by the loader.
 type xcoffLoaderReloc struct {
        sym    *sym.Symbol
-       rel    *sym.Reloc
+       sym2   loader.Sym
+       roff   int32
        rtype  uint16
        symndx int32
 }
@@ -1108,51 +1109,55 @@ func (f *xcoffFile) adddynimpsym(ctxt *Link, s loader.Sym) {
 
 // Xcoffadddynrel adds a dynamic relocation in a XCOFF file.
 // This relocation will be made by the loader.
-func Xcoffadddynrel(target *Target, ldr *loader.Loader, s *sym.Symbol, r *sym.Reloc) bool {
+func Xcoffadddynrel2(target *Target, ldr *loader.Loader, syms *ArchSyms, s loader.Sym, r *loader.Reloc2, rIdx int) bool {
        if target.IsExternal() {
                return true
        }
-       if s.Type <= sym.SPCLNTAB {
-               Errorf(s, "cannot have a relocation to %s in a text section symbol", r.Sym.Name)
+       if ldr.SymType(s) <= sym.SPCLNTAB {
+               ldr.Errorf(s, "cannot have a relocation to %s in a text section symbol", ldr.SymName(r.Sym()))
                return false
        }
 
        xldr := &xcoffLoaderReloc{
-               sym: s,
-               rel: r,
+               sym2: s,
+               roff: r.Off(),
+       }
+       targ := r.Sym()
+       var targType sym.SymKind
+       if targ != 0 {
+               targType = ldr.SymType(targ)
        }
 
-       switch r.Type {
+       switch r.Type() {
        default:
-               Errorf(s, "unexpected .loader relocation to symbol: %s (type: %s)", r.Sym.Name, r.Type.String())
+               ldr.Errorf(s, "unexpected .loader relocation to symbol: %s (type: %s)", ldr.SymName(targ), r.Type().String())
                return false
        case objabi.R_ADDR:
-               if s.Type == sym.SXCOFFTOC && r.Sym.Type == sym.SDYNIMPORT {
+               if ldr.SymType(s) == sym.SXCOFFTOC && targType == sym.SDYNIMPORT {
                        // Imported symbol relocation
                        for i, dynsym := range xfile.loaderSymbols {
-                               if ldr.Syms[dynsym.sym].Name == r.Sym.Name {
+                               if ldr.SymName(dynsym.sym) == ldr.SymName(targ) {
                                        xldr.symndx = int32(i + 3) // +3 because of 3 section symbols
                                        break
                                }
                        }
-               } else if s.Type == sym.SDATA {
-                       switch r.Sym.Sect.Seg {
+               } else if ldr.SymType(s) == sym.SDATA {
+                       switch ldr.SymSect(targ).Seg {
                        default:
-                               Errorf(s, "unknown segment for .loader relocation with symbol %s", r.Sym.Name)
+                               ldr.Errorf(s, "unknown segment for .loader relocation with symbol %s", ldr.SymName(targ))
                        case &Segtext:
                        case &Segrodata:
                                xldr.symndx = 0 // .text
                        case &Segdata:
-                               if r.Sym.Type == sym.SBSS || r.Sym.Type == sym.SNOPTRBSS {
+                               if targType == sym.SBSS || targType == sym.SNOPTRBSS {
                                        xldr.symndx = 2 // .bss
                                } else {
                                        xldr.symndx = 1 // .data
                                }
-
                        }
 
                } else {
-                       Errorf(s, "unexpected type for .loader relocation R_ADDR for symbol %s: %s to %s", r.Sym.Name, s.Type, r.Sym.Type)
+                       ldr.Errorf(s, "unexpected type for .loader relocation R_ADDR for symbol %s: %s to %s", ldr.SymName(targ), ldr.SymType(s), ldr.SymType(targ))
                        return false
                }
 
@@ -1303,14 +1308,18 @@ func (f *xcoffFile) writeLdrScn(ctxt *Link, globalOff uint64) {
 
        off += uint64(16 * len(f.loaderReloc))
        for _, r := range f.loaderReloc {
+               symp := r.sym
+               if symp == nil {
+                       symp = ctxt.loader.Syms[r.sym2]
+               }
                xldr = &XcoffLdRel64{
-                       Lvaddr:  uint64(r.sym.Value + int64(r.rel.Off)),
+                       Lvaddr:  uint64(symp.Value + int64(r.roff)),
                        Lrtype:  r.rtype,
                        Lsymndx: r.symndx,
                }
 
-               if r.sym.Sect != nil {
-                       xldr.Lrsecnm = f.getXCOFFscnum(r.sym.Sect)
+               if symp.Sect != nil {
+                       xldr.Lrsecnm = f.getXCOFFscnum(symp.Sect)
                }
 
                reloctab = append(reloctab, xldr)
index f2c893feca60541f80a27178dde633cb5cc45140..a8c2268fb7f607025868311dd5c5f12936252629 100644 (file)
@@ -4,7 +4,11 @@
 
 package ld
 
-import "cmd/link/internal/sym"
+import (
+       "cmd/internal/objabi"
+       "cmd/link/internal/loader"
+       "cmd/link/internal/sym"
+)
 
 // Temporary dumping around for sym.Symbol version of helper
 // functions in xcoff.go, still being used for some archs/oses.
@@ -50,3 +54,60 @@ func xcoffUpdateOuterSize(ctxt *Link, size int64, stype sym.SymKind) {
 
        }
 }
+
+// Xcoffadddynrel adds a dynamic relocation in a XCOFF file.
+// This relocation will be made by the loader.
+func Xcoffadddynrel(target *Target, ldr *loader.Loader, s *sym.Symbol, r *sym.Reloc) bool {
+       if target.IsExternal() {
+               return true
+       }
+       if s.Type <= sym.SPCLNTAB {
+               Errorf(s, "cannot have a relocation to %s in a text section symbol", r.Sym.Name)
+               return false
+       }
+
+       xldr := &xcoffLoaderReloc{
+               sym:  s,
+               roff: r.Off,
+       }
+
+       switch r.Type {
+       default:
+               Errorf(s, "unexpected .loader relocation to symbol: %s (type: %s)", r.Sym.Name, r.Type.String())
+               return false
+       case objabi.R_ADDR:
+               if s.Type == sym.SXCOFFTOC && r.Sym.Type == sym.SDYNIMPORT {
+                       // Imported symbol relocation
+                       for i, dynsym := range xfile.loaderSymbols {
+                               if ldr.Syms[dynsym.sym].Name == r.Sym.Name {
+                                       xldr.symndx = int32(i + 3) // +3 because of 3 section symbols
+                                       break
+                               }
+                       }
+               } else if s.Type == sym.SDATA {
+                       switch r.Sym.Sect.Seg {
+                       default:
+                               Errorf(s, "unknown segment for .loader relocation with symbol %s", r.Sym.Name)
+                       case &Segtext:
+                       case &Segrodata:
+                               xldr.symndx = 0 // .text
+                       case &Segdata:
+                               if r.Sym.Type == sym.SBSS || r.Sym.Type == sym.SNOPTRBSS {
+                                       xldr.symndx = 2 // .bss
+                               } else {
+                                       xldr.symndx = 1 // .data
+                               }
+
+                       }
+
+               } else {
+                       Errorf(s, "unexpected type for .loader relocation R_ADDR for symbol %s: %s to %s", r.Sym.Name, s.Type, r.Sym.Type)
+                       return false
+               }
+
+               xldr.rtype = 0x3F<<8 + XCOFF_R_POS
+       }
+
+       xfile.loaderReloc = append(xfile.loaderReloc, xldr)
+       return true
+}
index 8f7fe35220aba4352714f4e275dc34e58f99ba84..be124acaf86b7565e1a323b55b7e8ec8da8fca4c 100644 (file)
@@ -267,120 +267,134 @@ func gencallstub2(ctxt *ld.Link, ldr *loader.Loader, abicase int, stub *loader.S
        stub.AddUint32(ctxt.Arch, 0x4e800420) // bctr
 }
 
-func adddynrel(target *ld.Target, ldr *loader.Loader, syms *ld.ArchSyms, s *sym.Symbol, r *sym.Reloc) bool {
+func adddynrel2(target *ld.Target, ldr *loader.Loader, syms *ld.ArchSyms, s loader.Sym, r *loader.Reloc2, rIdx int) bool {
        if target.IsElf() {
-               return addelfdynrel(target, syms, s, r)
+               return addelfdynrel2(target, ldr, syms, s, r, rIdx)
        } else if target.IsAIX() {
-               return ld.Xcoffadddynrel(target, ldr, s, r)
+               return ld.Xcoffadddynrel2(target, ldr, syms, s, r, rIdx)
        }
        return false
 }
 
-func addelfdynrel(target *ld.Target, syms *ld.ArchSyms, s *sym.Symbol, r *sym.Reloc) bool {
-       targ := r.Sym
-       r.InitExt()
+func addelfdynrel2(target *ld.Target, ldr *loader.Loader, syms *ld.ArchSyms, s loader.Sym, r *loader.Reloc2, rIdx int) bool {
+       targ := r.Sym()
+       var targType sym.SymKind
+       if targ != 0 {
+               targType = ldr.SymType(targ)
+       }
 
-       switch r.Type {
+       switch r.Type() {
        default:
-               if r.Type >= objabi.ElfRelocOffset {
-                       ld.Errorf(s, "unexpected relocation type %d (%s)", r.Type, sym.RelocName(target.Arch, r.Type))
+               if r.Type() >= objabi.ElfRelocOffset {
+                       ldr.Errorf(s, "unexpected relocation type %d (%s)", r.Type(), sym.RelocName(target.Arch, r.Type()))
                        return false
                }
 
                // Handle relocations found in ELF object files.
        case objabi.ElfRelocOffset + objabi.RelocType(elf.R_PPC64_REL24):
-               r.Type = objabi.R_CALLPOWER
+               su := ldr.MakeSymbolUpdater(s)
+               su.SetRelocType(rIdx, objabi.R_CALLPOWER)
 
                // This is a local call, so the caller isn't setting
                // up r12 and r2 is the same for the caller and
                // callee. Hence, we need to go to the local entry
                // point.  (If we don't do this, the callee will try
                // to use r12 to compute r2.)
-               r.Add += int64(r.Sym.Localentry()) * 4
+               su.SetRelocAdd(rIdx, r.Add()+int64(ldr.SymLocalentry(targ))*4)
 
-               if targ.Type == sym.SDYNIMPORT {
+               if targType == sym.SDYNIMPORT {
                        // Should have been handled in elfsetupplt
-                       ld.Errorf(s, "unexpected R_PPC64_REL24 for dyn import")
+                       ldr.Errorf(s, "unexpected R_PPC64_REL24 for dyn import")
                }
 
                return true
 
        case objabi.ElfRelocOffset + objabi.RelocType(elf.R_PPC_REL32):
-               r.Type = objabi.R_PCREL
-               r.Add += 4
+               su := ldr.MakeSymbolUpdater(s)
+               su.SetRelocType(rIdx, objabi.R_PCREL)
+               su.SetRelocAdd(rIdx, r.Add()+4)
 
-               if targ.Type == sym.SDYNIMPORT {
-                       ld.Errorf(s, "unexpected R_PPC_REL32 for dyn import")
+               if targType == sym.SDYNIMPORT {
+                       ldr.Errorf(s, "unexpected R_PPC_REL32 for dyn import")
                }
 
                return true
 
        case objabi.ElfRelocOffset + objabi.RelocType(elf.R_PPC64_ADDR64):
-               r.Type = objabi.R_ADDR
-               if targ.Type == sym.SDYNIMPORT {
+               su := ldr.MakeSymbolUpdater(s)
+               su.SetRelocType(rIdx, objabi.R_ADDR)
+               if targType == sym.SDYNIMPORT {
                        // These happen in .toc sections
-                       ld.Adddynsym(target, syms, targ)
+                       ld.Adddynsym2(ldr, target, syms, targ)
 
-                       rela := syms.Rela
-                       rela.AddAddrPlus(target.Arch, s, int64(r.Off))
-                       rela.AddUint64(target.Arch, ld.ELF64_R_INFO(uint32(targ.Dynid), uint32(elf.R_PPC64_ADDR64)))
-                       rela.AddUint64(target.Arch, uint64(r.Add))
-                       r.Type = objabi.ElfRelocOffset // ignore during relocsym
+                       rela := ldr.MakeSymbolUpdater(syms.Rela2)
+                       rela.AddAddrPlus(target.Arch, s, int64(r.Off()))
+                       rela.AddUint64(target.Arch, ld.ELF64_R_INFO(uint32(ldr.SymDynid(targ)), uint32(elf.R_PPC64_ADDR64)))
+                       rela.AddUint64(target.Arch, uint64(r.Add()))
+                       su.SetRelocType(rIdx, objabi.ElfRelocOffset) // ignore during relocsym
                }
-
                return true
 
        case objabi.ElfRelocOffset + objabi.RelocType(elf.R_PPC64_TOC16):
-               r.Type = objabi.R_POWER_TOC
-               r.Variant = sym.RV_POWER_LO | sym.RV_CHECK_OVERFLOW
+               su := ldr.MakeSymbolUpdater(s)
+               su.SetRelocType(rIdx, objabi.R_POWER_TOC)
+               ldr.SetRelocVariant(s, rIdx, sym.RV_POWER_LO|sym.RV_CHECK_OVERFLOW)
                return true
 
        case objabi.ElfRelocOffset + objabi.RelocType(elf.R_PPC64_TOC16_LO):
-               r.Type = objabi.R_POWER_TOC
-               r.Variant = sym.RV_POWER_LO
+               su := ldr.MakeSymbolUpdater(s)
+               su.SetRelocType(rIdx, objabi.R_POWER_TOC)
+               ldr.SetRelocVariant(s, rIdx, sym.RV_POWER_LO)
                return true
 
        case objabi.ElfRelocOffset + objabi.RelocType(elf.R_PPC64_TOC16_HA):
-               r.Type = objabi.R_POWER_TOC
-               r.Variant = sym.RV_POWER_HA | sym.RV_CHECK_OVERFLOW
+               su := ldr.MakeSymbolUpdater(s)
+               su.SetRelocType(rIdx, objabi.R_POWER_TOC)
+               ldr.SetRelocVariant(s, rIdx, sym.RV_POWER_HA|sym.RV_CHECK_OVERFLOW)
                return true
 
        case objabi.ElfRelocOffset + objabi.RelocType(elf.R_PPC64_TOC16_HI):
-               r.Type = objabi.R_POWER_TOC
-               r.Variant = sym.RV_POWER_HI | sym.RV_CHECK_OVERFLOW
+               su := ldr.MakeSymbolUpdater(s)
+               su.SetRelocType(rIdx, objabi.R_POWER_TOC)
+               ldr.SetRelocVariant(s, rIdx, sym.RV_POWER_HI|sym.RV_CHECK_OVERFLOW)
                return true
 
        case objabi.ElfRelocOffset + objabi.RelocType(elf.R_PPC64_TOC16_DS):
-               r.Type = objabi.R_POWER_TOC
-               r.Variant = sym.RV_POWER_DS | sym.RV_CHECK_OVERFLOW
+               su := ldr.MakeSymbolUpdater(s)
+               su.SetRelocType(rIdx, objabi.R_POWER_TOC)
+               ldr.SetRelocVariant(s, rIdx, sym.RV_POWER_DS|sym.RV_CHECK_OVERFLOW)
                return true
 
        case objabi.ElfRelocOffset + objabi.RelocType(elf.R_PPC64_TOC16_LO_DS):
-               r.Type = objabi.R_POWER_TOC
-               r.Variant = sym.RV_POWER_DS
+               su := ldr.MakeSymbolUpdater(s)
+               su.SetRelocType(rIdx, objabi.R_POWER_TOC)
+               ldr.SetRelocVariant(s, rIdx, sym.RV_POWER_DS)
                return true
 
        case objabi.ElfRelocOffset + objabi.RelocType(elf.R_PPC64_REL16_LO):
-               r.Type = objabi.R_PCREL
-               r.Variant = sym.RV_POWER_LO
-               r.Add += 2 // Compensate for relocation size of 2
+               su := ldr.MakeSymbolUpdater(s)
+               su.SetRelocType(rIdx, objabi.R_PCREL)
+               ldr.SetRelocVariant(s, rIdx, sym.RV_POWER_LO)
+               su.SetRelocAdd(rIdx, r.Add()+2) // Compensate for relocation size of 2
                return true
 
        case objabi.ElfRelocOffset + objabi.RelocType(elf.R_PPC64_REL16_HI):
-               r.Type = objabi.R_PCREL
-               r.Variant = sym.RV_POWER_HI | sym.RV_CHECK_OVERFLOW
-               r.Add += 2
+               su := ldr.MakeSymbolUpdater(s)
+               su.SetRelocType(rIdx, objabi.R_PCREL)
+               ldr.SetRelocVariant(s, rIdx, sym.RV_POWER_HI|sym.RV_CHECK_OVERFLOW)
+               su.SetRelocAdd(rIdx, r.Add()+2)
                return true
 
        case objabi.ElfRelocOffset + objabi.RelocType(elf.R_PPC64_REL16_HA):
-               r.Type = objabi.R_PCREL
-               r.Variant = sym.RV_POWER_HA | sym.RV_CHECK_OVERFLOW
-               r.Add += 2
+               su := ldr.MakeSymbolUpdater(s)
+               su.SetRelocType(rIdx, objabi.R_PCREL)
+               ldr.SetRelocVariant(s, rIdx, sym.RV_POWER_HA|sym.RV_CHECK_OVERFLOW)
+               su.SetRelocAdd(rIdx, r.Add()+2)
                return true
        }
 
        // Handle references to ELF symbols from our own object files.
-       if targ.Type != sym.SDYNIMPORT {
+       if targType != sym.SDYNIMPORT {
                return true
        }
 
diff --git a/src/cmd/link/internal/ppc64/asm2.go b/src/cmd/link/internal/ppc64/asm2.go
new file mode 100644 (file)
index 0000000..0940df9
--- /dev/null
@@ -0,0 +1,140 @@
+// Copyright 2020 The Go Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style
+// license that can be found in the LICENSE file.
+
+package ppc64
+
+import (
+       "cmd/internal/objabi"
+       "cmd/link/internal/ld"
+       "cmd/link/internal/loader"
+       "cmd/link/internal/sym"
+       "debug/elf"
+)
+
+// Temporary dumping ground for sym.Symbol version of helper
+// functions in asm.go, still being used for some oses.
+// FIXME: get rid of this file when dodata() is completely
+// converted.
+
+func adddynrel(target *ld.Target, ldr *loader.Loader, syms *ld.ArchSyms, s *sym.Symbol, r *sym.Reloc) bool {
+       if target.IsElf() {
+               return addelfdynrel(target, syms, s, r)
+       } else if target.IsAIX() {
+               return ld.Xcoffadddynrel(target, ldr, s, r)
+       }
+       return false
+}
+
+func addelfdynrel(target *ld.Target, syms *ld.ArchSyms, s *sym.Symbol, r *sym.Reloc) bool {
+       targ := r.Sym
+       r.InitExt()
+
+       switch r.Type {
+       default:
+               if r.Type >= objabi.ElfRelocOffset {
+                       ld.Errorf(s, "unexpected relocation type %d (%s)", r.Type, sym.RelocName(target.Arch, r.Type))
+                       return false
+               }
+
+               // Handle relocations found in ELF object files.
+       case objabi.ElfRelocOffset + objabi.RelocType(elf.R_PPC64_REL24):
+               r.Type = objabi.R_CALLPOWER
+
+               // This is a local call, so the caller isn't setting
+               // up r12 and r2 is the same for the caller and
+               // callee. Hence, we need to go to the local entry
+               // point.  (If we don't do this, the callee will try
+               // to use r12 to compute r2.)
+               r.Add += int64(r.Sym.Localentry()) * 4
+
+               if targ.Type == sym.SDYNIMPORT {
+                       // Should have been handled in elfsetupplt
+                       ld.Errorf(s, "unexpected R_PPC64_REL24 for dyn import")
+               }
+
+               return true
+
+       case objabi.ElfRelocOffset + objabi.RelocType(elf.R_PPC_REL32):
+               r.Type = objabi.R_PCREL
+               r.Add += 4
+
+               if targ.Type == sym.SDYNIMPORT {
+                       ld.Errorf(s, "unexpected R_PPC_REL32 for dyn import")
+               }
+
+               return true
+
+       case objabi.ElfRelocOffset + objabi.RelocType(elf.R_PPC64_ADDR64):
+               r.Type = objabi.R_ADDR
+               if targ.Type == sym.SDYNIMPORT {
+                       // These happen in .toc sections
+                       ld.Adddynsym(target, syms, targ)
+
+                       rela := syms.Rela
+                       rela.AddAddrPlus(target.Arch, s, int64(r.Off))
+                       rela.AddUint64(target.Arch, ld.ELF64_R_INFO(uint32(targ.Dynid), uint32(elf.R_PPC64_ADDR64)))
+                       rela.AddUint64(target.Arch, uint64(r.Add))
+                       r.Type = objabi.ElfRelocOffset // ignore during relocsym
+               }
+
+               return true
+
+       case objabi.ElfRelocOffset + objabi.RelocType(elf.R_PPC64_TOC16):
+               r.Type = objabi.R_POWER_TOC
+               r.Variant = sym.RV_POWER_LO | sym.RV_CHECK_OVERFLOW
+               return true
+
+       case objabi.ElfRelocOffset + objabi.RelocType(elf.R_PPC64_TOC16_LO):
+               r.Type = objabi.R_POWER_TOC
+               r.Variant = sym.RV_POWER_LO
+               return true
+
+       case objabi.ElfRelocOffset + objabi.RelocType(elf.R_PPC64_TOC16_HA):
+               r.Type = objabi.R_POWER_TOC
+               r.Variant = sym.RV_POWER_HA | sym.RV_CHECK_OVERFLOW
+               return true
+
+       case objabi.ElfRelocOffset + objabi.RelocType(elf.R_PPC64_TOC16_HI):
+               r.Type = objabi.R_POWER_TOC
+               r.Variant = sym.RV_POWER_HI | sym.RV_CHECK_OVERFLOW
+               return true
+
+       case objabi.ElfRelocOffset + objabi.RelocType(elf.R_PPC64_TOC16_DS):
+               r.Type = objabi.R_POWER_TOC
+               r.Variant = sym.RV_POWER_DS | sym.RV_CHECK_OVERFLOW
+               return true
+
+       case objabi.ElfRelocOffset + objabi.RelocType(elf.R_PPC64_TOC16_LO_DS):
+               r.Type = objabi.R_POWER_TOC
+               r.Variant = sym.RV_POWER_DS
+               return true
+
+       case objabi.ElfRelocOffset + objabi.RelocType(elf.R_PPC64_REL16_LO):
+               r.Type = objabi.R_PCREL
+               r.Variant = sym.RV_POWER_LO
+               r.Add += 2 // Compensate for relocation size of 2
+               return true
+
+       case objabi.ElfRelocOffset + objabi.RelocType(elf.R_PPC64_REL16_HI):
+               r.Type = objabi.R_PCREL
+               r.Variant = sym.RV_POWER_HI | sym.RV_CHECK_OVERFLOW
+               r.Add += 2
+               return true
+
+       case objabi.ElfRelocOffset + objabi.RelocType(elf.R_PPC64_REL16_HA):
+               r.Type = objabi.R_PCREL
+               r.Variant = sym.RV_POWER_HA | sym.RV_CHECK_OVERFLOW
+               r.Add += 2
+               return true
+       }
+
+       // Handle references to ELF symbols from our own object files.
+       if targ.Type != sym.SDYNIMPORT {
+               return true
+       }
+
+       // TODO(austin): Translate our relocations to ELF
+
+       return false
+}
index cff1e9cc733a2e539725766e2ee2e803a95b663f..51620b87a025f6ed3dd500648bdf2709b4948ca9 100644 (file)
@@ -50,6 +50,7 @@ func Init() (*sys.Arch, ld.Arch) {
                Dwarfreglr: dwarfRegLR,
 
                Adddynrel:        adddynrel,
+               Adddynrel2:       adddynrel2,
                Archinit:         archinit,
                Archreloc:        archreloc,
                Archrelocvariant: archrelocvariant,