[llvm] b6553f5 - [JITLink][ELF][AArch64] Lift MachO/arm64 edges into aarch64.h, reuse for ELF.

Lang Hames via llvm-commits llvm-commits at lists.llvm.org
Tue Jun 7 12:01:51 PDT 2022


Author: Sunho Kim
Date: 2022-06-07T12:01:43-07:00
New Revision: b6553f592aa4227f73d31f656bf84c9b722ea4cd

URL: https://github.com/llvm/llvm-project/commit/b6553f592aa4227f73d31f656bf84c9b722ea4cd
DIFF: https://github.com/llvm/llvm-project/commit/b6553f592aa4227f73d31f656bf84c9b722ea4cd.diff

LOG: [JITLink][ELF][AArch64] Lift MachO/arm64 edges into aarch64.h, reuse for ELF.

This patch moves the aarch64 fixup logic from the MachO/arm64 backend to
aarch64.h header so that it can be re-used in the ELF/aarch64 backend. This
significantly expands relocation support in the ELF/aarch64 backend.

Reviewed By: lhames, sgraenitz

Differential Revision: https://reviews.llvm.org/D126286

Added: 
    

Modified: 
    llvm/include/llvm/ExecutionEngine/JITLink/MachO_arm64.h
    llvm/include/llvm/ExecutionEngine/JITLink/aarch64.h
    llvm/lib/ExecutionEngine/JITLink/ELF_aarch64.cpp
    llvm/lib/ExecutionEngine/JITLink/MachO_arm64.cpp
    llvm/lib/ExecutionEngine/JITLink/aarch64.cpp

Removed: 
    


################################################################################
diff  --git a/llvm/include/llvm/ExecutionEngine/JITLink/MachO_arm64.h b/llvm/include/llvm/ExecutionEngine/JITLink/MachO_arm64.h
index aee14c0d1fe5..6f2ff012697d 100644
--- a/llvm/include/llvm/ExecutionEngine/JITLink/MachO_arm64.h
+++ b/llvm/include/llvm/ExecutionEngine/JITLink/MachO_arm64.h
@@ -18,30 +18,6 @@
 namespace llvm {
 namespace jitlink {
 
-namespace MachO_arm64_Edges {
-
-enum MachOARM64RelocationKind : Edge::Kind {
-  Branch26 = Edge::FirstRelocation,
-  Pointer32,
-  Pointer64,
-  Pointer64Anon,
-  Page21,
-  PageOffset12,
-  GOTPage21,
-  GOTPageOffset12,
-  TLVPage21,
-  TLVPageOffset12,
-  PointerToGOT,
-  PairedAddend,
-  LDRLiteral19,
-  Delta32,
-  Delta64,
-  NegDelta32,
-  NegDelta64,
-};
-
-} // namespace MachO_arm64_Edges
-
 /// Create a LinkGraph from a MachO/arm64 relocatable object.
 ///
 /// Note: The graph does not take ownership of the underlying buffer, nor copy
@@ -62,9 +38,6 @@ createLinkGraphFromMachOObject_arm64(MemoryBufferRef ObjectBuffer);
 void link_MachO_arm64(std::unique_ptr<LinkGraph> G,
                       std::unique_ptr<JITLinkContext> Ctx);
 
-/// Return the string name of the given MachO arm64 edge kind.
-const char *getMachOARM64RelocationKindName(Edge::Kind R);
-
 } // end namespace jitlink
 } // end namespace llvm
 

diff  --git a/llvm/include/llvm/ExecutionEngine/JITLink/aarch64.h b/llvm/include/llvm/ExecutionEngine/JITLink/aarch64.h
index 994ce783b058..ef38a1690c9b 100644
--- a/llvm/include/llvm/ExecutionEngine/JITLink/aarch64.h
+++ b/llvm/include/llvm/ExecutionEngine/JITLink/aarch64.h
@@ -19,18 +19,34 @@ namespace llvm {
 namespace jitlink {
 namespace aarch64 {
 
-/// Represets aarch64 fixups
 enum EdgeKind_aarch64 : Edge::Kind {
-
-  /// Set a CALL immediate field to bits [27:2] of X = Target - Fixup + Addend
-  R_AARCH64_CALL26 = Edge::FirstRelocation,
-
+  Branch26 = Edge::FirstRelocation,
+  Pointer32,
+  Pointer64,
+  Pointer64Anon,
+  Page21,
+  PageOffset12,
+  GOTPage21,
+  GOTPageOffset12,
+  TLVPage21,
+  TLVPageOffset12,
+  PointerToGOT,
+  PairedAddend,
+  LDRLiteral19,
+  Delta32,
+  Delta64,
+  NegDelta32,
+  NegDelta64,
 };
 
 /// Returns a string name for the given aarch64 edge. For debugging purposes
 /// only
 const char *getEdgeKindName(Edge::Kind K);
 
+unsigned getPageOffset12Shift(uint32_t Instr);
+
+Error applyFixup(LinkGraph &G, Block &B, const Edge &E);
+
 } // namespace aarch64
 } // namespace jitlink
 } // namespace llvm

diff  --git a/llvm/lib/ExecutionEngine/JITLink/ELF_aarch64.cpp b/llvm/lib/ExecutionEngine/JITLink/ELF_aarch64.cpp
index dd3eb97c21a0..1d00dab8212c 100644
--- a/llvm/lib/ExecutionEngine/JITLink/ELF_aarch64.cpp
+++ b/llvm/lib/ExecutionEngine/JITLink/ELF_aarch64.cpp
@@ -37,46 +37,23 @@ class ELFJITLinker_aarch64 : public JITLinker<ELFJITLinker_aarch64> {
 
 private:
   Error applyFixup(LinkGraph &G, Block &B, const Edge &E) const {
-    using namespace aarch64;
-    using namespace llvm::support;
-
-    char *BlockWorkingMem = B.getAlreadyMutableContent().data();
-    char *FixupPtr = BlockWorkingMem + E.getOffset();
-    auto FixupAddress = B.getAddress() + E.getOffset();
-    switch (E.getKind()) {
-    case aarch64::R_AARCH64_CALL26: {
-      assert((FixupAddress.getValue() & 0x3) == 0 &&
-             "Call-inst is not 32-bit aligned");
-      int64_t Value = E.getTarget().getAddress() - FixupAddress + E.getAddend();
-
-      if (static_cast<uint64_t>(Value) & 0x3)
-        return make_error<JITLinkError>("Call target is not 32-bit aligned");
-
-      if (!isInt<28>(Value))
-        return makeTargetOutOfRangeError(G, B, E);
-
-      uint32_t RawInstr = *(little32_t *)FixupPtr;
-      assert((RawInstr & 0x7fffffff) == 0x14000000 &&
-             "RawInstr isn't a B or BR immediate instruction");
-      uint32_t Imm = (static_cast<uint32_t>(Value) & ((1 << 28) - 1)) >> 2;
-      uint32_t FixedInstr = RawInstr | Imm;
-      *(little32_t *)FixupPtr = FixedInstr;
-      break;
-    }
-    }
-    return Error::success();
+    return aarch64::applyFixup(G, B, E);
   }
 };
 
 template <typename ELFT>
 class ELFLinkGraphBuilder_aarch64 : public ELFLinkGraphBuilder<ELFT> {
 private:
-  static Expected<aarch64::EdgeKind_aarch64>
+  enum ELFAArch64RelocationKind : Edge::Kind {
+    ELFBranch26 = Edge::FirstRelocation,
+  };
+
+  static Expected<ELFAArch64RelocationKind>
   getRelocationKind(const uint32_t Type) {
     using namespace aarch64;
     switch (Type) {
     case ELF::R_AARCH64_CALL26:
-      return EdgeKind_aarch64::R_AARCH64_CALL26;
+      return ELFBranch26;
     }
 
     return make_error<JITLinkError>("Unsupported aarch64 relocation:" +
@@ -116,18 +93,28 @@ class ELFLinkGraphBuilder_aarch64 : public ELFLinkGraphBuilder<ELFT> {
           inconvertibleErrorCode());
 
     uint32_t Type = Rel.getType(false);
-    Expected<aarch64::EdgeKind_aarch64> Kind = getRelocationKind(Type);
-    if (!Kind)
-      return Kind.takeError();
+    Expected<ELFAArch64RelocationKind> RelocKind = getRelocationKind(Type);
+    if (!RelocKind)
+      return RelocKind.takeError();
 
     int64_t Addend = Rel.r_addend;
     orc::ExecutorAddr FixupAddress =
         orc::ExecutorAddr(FixupSect.sh_addr) + Rel.r_offset;
     Edge::OffsetT Offset = FixupAddress - BlockToFix.getAddress();
-    Edge GE(*Kind, Offset, *GraphSymbol, Addend);
+
+    Edge::Kind Kind = Edge::Invalid;
+
+    switch (*RelocKind) {
+    case ELFBranch26: {
+      Kind = aarch64::Branch26;
+      break;
+    }
+    };
+
+    Edge GE(Kind, Offset, *GraphSymbol, Addend);
     LLVM_DEBUG({
       dbgs() << "    ";
-      printEdge(dbgs(), BlockToFix, GE, aarch64::getEdgeKindName(*Kind));
+      printEdge(dbgs(), BlockToFix, GE, aarch64::getEdgeKindName(Kind));
       dbgs() << "\n";
     });
 
@@ -135,6 +122,16 @@ class ELFLinkGraphBuilder_aarch64 : public ELFLinkGraphBuilder<ELFT> {
     return Error::success();
   }
 
+  /// Return the string name of the given ELF aarch64 edge kind.
+  const char *getELFAArch64RelocationKindName(Edge::Kind R) {
+    switch (R) {
+    case ELFBranch26:
+      return "ELFBranch26";
+    default:
+      return getGenericEdgeKindName(static_cast<Edge::Kind>(R));
+    }
+  }
+
 public:
   ELFLinkGraphBuilder_aarch64(StringRef FileName,
                               const object::ELFFile<ELFT> &Obj, const Triple T)

diff  --git a/llvm/lib/ExecutionEngine/JITLink/MachO_arm64.cpp b/llvm/lib/ExecutionEngine/JITLink/MachO_arm64.cpp
index ed59aa4be968..1356f53b6292 100644
--- a/llvm/lib/ExecutionEngine/JITLink/MachO_arm64.cpp
+++ b/llvm/lib/ExecutionEngine/JITLink/MachO_arm64.cpp
@@ -12,6 +12,7 @@
 
 #include "llvm/ExecutionEngine/JITLink/MachO_arm64.h"
 #include "llvm/ExecutionEngine/JITLink/DWARFRecordSectionSplitter.h"
+#include "llvm/ExecutionEngine/JITLink/aarch64.h"
 
 #include "MachOLinkGraphBuilder.h"
 #include "PerGraphGOTAndPLTStubsBuilder.h"
@@ -20,7 +21,6 @@
 
 using namespace llvm;
 using namespace llvm::jitlink;
-using namespace llvm::jitlink::MachO_arm64_Edges;
 
 namespace {
 
@@ -28,19 +28,39 @@ class MachOLinkGraphBuilder_arm64 : public MachOLinkGraphBuilder {
 public:
   MachOLinkGraphBuilder_arm64(const object::MachOObjectFile &Obj)
       : MachOLinkGraphBuilder(Obj, Triple("arm64-apple-darwin"),
-                              getMachOARM64RelocationKindName),
+                              aarch64::getEdgeKindName),
         NumSymbols(Obj.getSymtabLoadCommand().nsyms) {}
 
 private:
+  enum MachOARM64RelocationKind : Edge::Kind {
+    MachOBranch26 = Edge::FirstRelocation,
+    MachOPointer32,
+    MachOPointer64,
+    MachOPointer64Anon,
+    MachOPage21,
+    MachOPageOffset12,
+    MachOGOTPage21,
+    MachOGOTPageOffset12,
+    MachOTLVPage21,
+    MachOTLVPageOffset12,
+    MachOPointerToGOT,
+    MachOPairedAddend,
+    MachOLDRLiteral19,
+    MachODelta32,
+    MachODelta64,
+    MachONegDelta32,
+    MachONegDelta64,
+  };
+
   static Expected<MachOARM64RelocationKind>
   getRelocationKind(const MachO::relocation_info &RI) {
     switch (RI.r_type) {
     case MachO::ARM64_RELOC_UNSIGNED:
       if (!RI.r_pcrel) {
         if (RI.r_length == 3)
-          return RI.r_extern ? Pointer64 : Pointer64Anon;
+          return RI.r_extern ? MachOPointer64 : MachOPointer64Anon;
         else if (RI.r_length == 2)
-          return Pointer32;
+          return MachOPointer32;
       }
       break;
     case MachO::ARM64_RELOC_SUBTRACTOR:
@@ -49,46 +69,46 @@ class MachOLinkGraphBuilder_arm64 : public MachOLinkGraphBuilder {
       // They may be turned into NegDelta<W> by parsePairRelocation.
       if (!RI.r_pcrel && RI.r_extern) {
         if (RI.r_length == 2)
-          return Delta32;
+          return MachODelta32;
         else if (RI.r_length == 3)
-          return Delta64;
+          return MachODelta64;
       }
       break;
     case MachO::ARM64_RELOC_BRANCH26:
       if (RI.r_pcrel && RI.r_extern && RI.r_length == 2)
-        return Branch26;
+        return MachOBranch26;
       break;
     case MachO::ARM64_RELOC_PAGE21:
       if (RI.r_pcrel && RI.r_extern && RI.r_length == 2)
-        return Page21;
+        return MachOPage21;
       break;
     case MachO::ARM64_RELOC_PAGEOFF12:
       if (!RI.r_pcrel && RI.r_extern && RI.r_length == 2)
-        return PageOffset12;
+        return MachOPageOffset12;
       break;
     case MachO::ARM64_RELOC_GOT_LOAD_PAGE21:
       if (RI.r_pcrel && RI.r_extern && RI.r_length == 2)
-        return GOTPage21;
+        return MachOGOTPage21;
       break;
     case MachO::ARM64_RELOC_GOT_LOAD_PAGEOFF12:
       if (!RI.r_pcrel && RI.r_extern && RI.r_length == 2)
-        return GOTPageOffset12;
+        return MachOGOTPageOffset12;
       break;
     case MachO::ARM64_RELOC_POINTER_TO_GOT:
       if (RI.r_pcrel && RI.r_extern && RI.r_length == 2)
-        return PointerToGOT;
+        return MachOPointerToGOT;
       break;
     case MachO::ARM64_RELOC_ADDEND:
       if (!RI.r_pcrel && !RI.r_extern && RI.r_length == 2)
-        return PairedAddend;
+        return MachOPairedAddend;
       break;
     case MachO::ARM64_RELOC_TLVP_LOAD_PAGE21:
       if (RI.r_pcrel && RI.r_extern && RI.r_length == 2)
-        return TLVPage21;
+        return MachOTLVPage21;
       break;
     case MachO::ARM64_RELOC_TLVP_LOAD_PAGEOFF12:
       if (!RI.r_pcrel && RI.r_extern && RI.r_length == 2)
-        return TLVPageOffset12;
+        return MachOTLVPageOffset12;
       break;
     }
 
@@ -102,8 +122,7 @@ class MachOLinkGraphBuilder_arm64 : public MachOLinkGraphBuilder {
         ", length=" + formatv("{0:d}", RI.r_length));
   }
 
-  using PairRelocInfo =
-      std::tuple<MachOARM64RelocationKind, Symbol *, uint64_t>;
+  using PairRelocInfo = std::tuple<Edge::Kind, Symbol *, uint64_t>;
 
   // Parses paired SUBTRACTOR/UNSIGNED relocations and, on success,
   // returns the edge kind and addend to be used.
@@ -115,8 +134,8 @@ class MachOLinkGraphBuilder_arm64 : public MachOLinkGraphBuilder {
                       object::relocation_iterator &RelEnd) {
     using namespace support;
 
-    assert(((SubtractorKind == Delta32 && SubRI.r_length == 2) ||
-            (SubtractorKind == Delta64 && SubRI.r_length == 3)) &&
+    assert(((SubtractorKind == MachODelta32 && SubRI.r_length == 2) ||
+            (SubtractorKind == MachODelta64 && SubRI.r_length == 3)) &&
            "Subtractor kind should match length");
     assert(SubRI.r_extern && "SUBTRACTOR reloc symbol should be extern");
     assert(!SubRI.r_pcrel && "SUBTRACTOR reloc should not be PCRel");
@@ -166,17 +185,18 @@ class MachOLinkGraphBuilder_arm64 : public MachOLinkGraphBuilder {
       FixupValue -= ToSymbol->getAddress().getValue();
     }
 
-    MachOARM64RelocationKind DeltaKind;
+    Edge::Kind DeltaKind;
     Symbol *TargetSymbol;
     uint64_t Addend;
     if (&BlockToFix == &FromSymbol->getAddressable()) {
       TargetSymbol = ToSymbol;
-      DeltaKind = (SubRI.r_length == 3) ? Delta64 : Delta32;
+      DeltaKind = (SubRI.r_length == 3) ? aarch64::Delta64 : aarch64::Delta32;
       Addend = FixupValue + (FixupAddress - FromSymbol->getAddress());
       // FIXME: handle extern 'from'.
     } else if (&BlockToFix == &ToSymbol->getAddressable()) {
       TargetSymbol = &*FromSymbol;
-      DeltaKind = (SubRI.r_length == 3) ? NegDelta64 : NegDelta32;
+      DeltaKind =
+          (SubRI.r_length == 3) ? aarch64::NegDelta64 : aarch64::NegDelta32;
       Addend = FixupValue - (FixupAddress - ToSymbol->getAddress());
     } else {
       // BlockToFix was neither FromSymbol nor ToSymbol.
@@ -230,9 +250,9 @@ class MachOLinkGraphBuilder_arm64 : public MachOLinkGraphBuilder {
         MachO::relocation_info RI = getRelocationInfo(RelItr);
 
         // Validate the relocation kind.
-        auto Kind = getRelocationKind(RI);
-        if (!Kind)
-          return Kind.takeError();
+        auto MachORelocKind = getRelocationKind(RI);
+        if (!MachORelocKind)
+          return MachORelocKind.takeError();
 
         // Find the address of the value to fix up.
         orc::ExecutorAddr FixupAddress =
@@ -256,6 +276,8 @@ class MachOLinkGraphBuilder_arm64 : public MachOLinkGraphBuilder {
           return make_error<JITLinkError>(
               "Relocation content extends past end of fixup block");
 
+        Edge::Kind Kind = Edge::Invalid;
+
         // Get a pointer to the fixup content.
         const char *FixupContent = BlockToFix->getContent().data() +
                                    (FixupAddress - BlockToFix->getAddress());
@@ -264,7 +286,7 @@ class MachOLinkGraphBuilder_arm64 : public MachOLinkGraphBuilder {
         Symbol *TargetSymbol = nullptr;
         uint64_t Addend = 0;
 
-        if (*Kind == PairedAddend) {
+        if (*MachORelocKind == MachOPairedAddend) {
           // If this is an Addend relocation then process it and move to the
           // paired reloc.
 
@@ -276,19 +298,21 @@ class MachOLinkGraphBuilder_arm64 : public MachOLinkGraphBuilder {
           ++RelItr;
           RI = getRelocationInfo(RelItr);
 
-          Kind = getRelocationKind(RI);
-          if (!Kind)
-            return Kind.takeError();
+          MachORelocKind = getRelocationKind(RI);
+          if (!MachORelocKind)
+            return MachORelocKind.takeError();
 
-          if (*Kind != Branch26 && *Kind != Page21 && *Kind != PageOffset12)
+          if (*MachORelocKind != MachOBranch26 &&
+              *MachORelocKind != MachOPage21 &&
+              *MachORelocKind != MachOPageOffset12)
             return make_error<JITLinkError>(
                 "Invalid relocation pair: Addend + " +
-                StringRef(getMachOARM64RelocationKindName(*Kind)));
+                StringRef(getMachOARM64RelocationKindName(*MachORelocKind)));
 
           LLVM_DEBUG({
             dbgs() << "    Addend: value = " << formatv("{0:x6}", Addend)
-                   << ", pair is " << getMachOARM64RelocationKindName(*Kind)
-                   << "\n";
+                   << ", pair is "
+                   << getMachOARM64RelocationKindName(*MachORelocKind) << "\n";
           });
 
           // Find the address of the value to fix up.
@@ -299,8 +323,8 @@ class MachOLinkGraphBuilder_arm64 : public MachOLinkGraphBuilder {
                                             "
diff erent target");
         }
 
-        switch (*Kind) {
-        case Branch26: {
+        switch (*MachORelocKind) {
+        case MachOBranch26: {
           if (auto TargetSymbolOrErr = findSymbolByIndex(RI.r_symbolnum))
             TargetSymbol = TargetSymbolOrErr->GraphSymbol;
           else
@@ -309,23 +333,26 @@ class MachOLinkGraphBuilder_arm64 : public MachOLinkGraphBuilder {
           if ((Instr & 0x7fffffff) != 0x14000000)
             return make_error<JITLinkError>("BRANCH26 target is not a B or BL "
                                             "instruction with a zero addend");
+          Kind = aarch64::Branch26;
           break;
         }
-        case Pointer32:
+        case MachOPointer32:
           if (auto TargetSymbolOrErr = findSymbolByIndex(RI.r_symbolnum))
             TargetSymbol = TargetSymbolOrErr->GraphSymbol;
           else
             return TargetSymbolOrErr.takeError();
           Addend = *(const ulittle32_t *)FixupContent;
+          Kind = aarch64::Pointer32;
           break;
-        case Pointer64:
+        case MachOPointer64:
           if (auto TargetSymbolOrErr = findSymbolByIndex(RI.r_symbolnum))
             TargetSymbol = TargetSymbolOrErr->GraphSymbol;
           else
             return TargetSymbolOrErr.takeError();
           Addend = *(const ulittle64_t *)FixupContent;
+          Kind = aarch64::Pointer64;
           break;
-        case Pointer64Anon: {
+        case MachOPointer64Anon: {
           orc::ExecutorAddr TargetAddress(*(const ulittle64_t *)FixupContent);
           auto TargetNSec = findSectionByIndex(RI.r_symbolnum - 1);
           if (!TargetNSec)
@@ -336,11 +363,12 @@ class MachOLinkGraphBuilder_arm64 : public MachOLinkGraphBuilder {
           else
             return TargetSymbolOrErr.takeError();
           Addend = TargetAddress - TargetSymbol->getAddress();
+          Kind = aarch64::Pointer64Anon;
           break;
         }
-        case Page21:
-        case TLVPage21:
-        case GOTPage21: {
+        case MachOPage21:
+        case MachOTLVPage21:
+        case MachOGOTPage21: {
           if (auto TargetSymbolOrErr = findSymbolByIndex(RI.r_symbolnum))
             TargetSymbol = TargetSymbolOrErr->GraphSymbol;
           else
@@ -350,9 +378,17 @@ class MachOLinkGraphBuilder_arm64 : public MachOLinkGraphBuilder {
             return make_error<JITLinkError>("PAGE21/GOTPAGE21 target is not an "
                                             "ADRP instruction with a zero "
                                             "addend");
+
+          if (*MachORelocKind == MachOPage21) {
+            Kind = aarch64::Page21;
+          } else if (*MachORelocKind == MachOTLVPage21) {
+            Kind = aarch64::TLVPage21;
+          } else if (*MachORelocKind == MachOGOTPage21) {
+            Kind = aarch64::GOTPage21;
+          }
           break;
         }
-        case PageOffset12: {
+        case MachOPageOffset12: {
           if (auto TargetSymbolOrErr = findSymbolByIndex(RI.r_symbolnum))
             TargetSymbol = TargetSymbolOrErr->GraphSymbol;
           else
@@ -362,10 +398,11 @@ class MachOLinkGraphBuilder_arm64 : public MachOLinkGraphBuilder {
           if (EncodedAddend != 0)
             return make_error<JITLinkError>("GOTPAGEOFF12 target has non-zero "
                                             "encoded addend");
+          Kind = aarch64::PageOffset12;
           break;
         }
-        case TLVPageOffset12:
-        case GOTPageOffset12: {
+        case MachOTLVPageOffset12:
+        case MachOGOTPageOffset12: {
           if (auto TargetSymbolOrErr = findSymbolByIndex(RI.r_symbolnum))
             TargetSymbol = TargetSymbolOrErr->GraphSymbol;
           else
@@ -375,27 +412,35 @@ class MachOLinkGraphBuilder_arm64 : public MachOLinkGraphBuilder {
             return make_error<JITLinkError>("GOTPAGEOFF12 target is not an LDR "
                                             "immediate instruction with a zero "
                                             "addend");
+
+          if (*MachORelocKind == MachOTLVPageOffset12) {
+            Kind = aarch64::TLVPageOffset12;
+          } else if (*MachORelocKind == MachOGOTPageOffset12) {
+            Kind = aarch64::GOTPageOffset12;
+          }
           break;
         }
-        case PointerToGOT:
+        case MachOPointerToGOT:
           if (auto TargetSymbolOrErr = findSymbolByIndex(RI.r_symbolnum))
             TargetSymbol = TargetSymbolOrErr->GraphSymbol;
           else
             return TargetSymbolOrErr.takeError();
+
+          Kind = aarch64::PointerToGOT;
           break;
-        case Delta32:
-        case Delta64: {
+        case MachODelta32:
+        case MachODelta64: {
           // We use Delta32/Delta64 to represent SUBTRACTOR relocations.
           // parsePairRelocation handles the paired reloc, and returns the
           // edge kind to be used (either Delta32/Delta64, or
           // NegDelta32/NegDelta64, depending on the direction of the
           // subtraction) along with the addend.
           auto PairInfo =
-              parsePairRelocation(*BlockToFix, *Kind, RI, FixupAddress,
-                                  FixupContent, ++RelItr, RelEnd);
+              parsePairRelocation(*BlockToFix, *MachORelocKind, RI,
+                                  FixupAddress, FixupContent, ++RelItr, RelEnd);
           if (!PairInfo)
             return PairInfo.takeError();
-          std::tie(*Kind, TargetSymbol, Addend) = *PairInfo;
+          std::tie(Kind, TargetSymbol, Addend) = *PairInfo;
           assert(TargetSymbol && "No target symbol from parsePairRelocation?");
           break;
         }
@@ -406,19 +451,58 @@ class MachOLinkGraphBuilder_arm64 : public MachOLinkGraphBuilder {
 
         LLVM_DEBUG({
           dbgs() << "    ";
-          Edge GE(*Kind, FixupAddress - BlockToFix->getAddress(), *TargetSymbol,
+          Edge GE(Kind, FixupAddress - BlockToFix->getAddress(), *TargetSymbol,
                   Addend);
-          printEdge(dbgs(), *BlockToFix, GE,
-                    getMachOARM64RelocationKindName(*Kind));
+          printEdge(dbgs(), *BlockToFix, GE, aarch64::getEdgeKindName(Kind));
           dbgs() << "\n";
         });
-        BlockToFix->addEdge(*Kind, FixupAddress - BlockToFix->getAddress(),
+        BlockToFix->addEdge(Kind, FixupAddress - BlockToFix->getAddress(),
                             *TargetSymbol, Addend);
       }
     }
     return Error::success();
   }
 
+  /// Return the string name of the given MachO arm64 edge kind.
+  const char *getMachOARM64RelocationKindName(Edge::Kind R) {
+    switch (R) {
+    case MachOBranch26:
+      return "MachOBranch26";
+    case MachOPointer64:
+      return "MachOPointer64";
+    case MachOPointer64Anon:
+      return "MachOPointer64Anon";
+    case MachOPage21:
+      return "MachOPage21";
+    case MachOPageOffset12:
+      return "MachOPageOffset12";
+    case MachOGOTPage21:
+      return "MachOGOTPage21";
+    case MachOGOTPageOffset12:
+      return "MachOGOTPageOffset12";
+    case MachOTLVPage21:
+      return "MachOTLVPage21";
+    case MachOTLVPageOffset12:
+      return "MachOTLVPageOffset12";
+    case MachOPointerToGOT:
+      return "MachOPointerToGOT";
+    case MachOPairedAddend:
+      return "MachOPairedAddend";
+    case MachOLDRLiteral19:
+      return "MachOLDRLiteral19";
+    case MachODelta32:
+      return "MachODelta32";
+    case MachODelta64:
+      return "MachODelta64";
+    case MachONegDelta32:
+      return "MachONegDelta32";
+    case MachONegDelta64:
+      return "MachONegDelta64";
+    default:
+      return getGenericEdgeKindName(static_cast<Edge::Kind>(R));
+    }
+  }
+
   unsigned NumSymbols = 0;
 };
 
@@ -430,32 +514,36 @@ class PerGraphGOTAndPLTStubsBuilder_MachO_arm64
       PerGraphGOTAndPLTStubsBuilder_MachO_arm64>::PerGraphGOTAndPLTStubsBuilder;
 
   bool isGOTEdgeToFix(Edge &E) const {
-    return E.getKind() == GOTPage21 || E.getKind() == GOTPageOffset12 ||
-           E.getKind() == TLVPage21 || E.getKind() == TLVPageOffset12 ||
-           E.getKind() == PointerToGOT;
+    return E.getKind() == aarch64::GOTPage21 ||
+           E.getKind() == aarch64::GOTPageOffset12 ||
+           E.getKind() == aarch64::TLVPage21 ||
+           E.getKind() == aarch64::TLVPageOffset12 ||
+           E.getKind() == aarch64::PointerToGOT;
   }
 
   Symbol &createGOTEntry(Symbol &Target) {
     auto &GOTEntryBlock = G.createContentBlock(
         getGOTSection(), getGOTEntryBlockContent(), orc::ExecutorAddr(), 8, 0);
-    GOTEntryBlock.addEdge(Pointer64, 0, Target, 0);
+    GOTEntryBlock.addEdge(aarch64::Pointer64, 0, Target, 0);
     return G.addAnonymousSymbol(GOTEntryBlock, 0, 8, false, false);
   }
 
   void fixGOTEdge(Edge &E, Symbol &GOTEntry) {
-    if (E.getKind() == GOTPage21 || E.getKind() == GOTPageOffset12 ||
-        E.getKind() == TLVPage21 || E.getKind() == TLVPageOffset12) {
+    if (E.getKind() == aarch64::GOTPage21 ||
+        E.getKind() == aarch64::GOTPageOffset12 ||
+        E.getKind() == aarch64::TLVPage21 ||
+        E.getKind() == aarch64::TLVPageOffset12) {
       // Update the target, but leave the edge addend as-is.
       E.setTarget(GOTEntry);
-    } else if (E.getKind() == PointerToGOT) {
+    } else if (E.getKind() == aarch64::PointerToGOT) {
       E.setTarget(GOTEntry);
-      E.setKind(Delta32);
+      E.setKind(aarch64::Delta32);
     } else
       llvm_unreachable("Not a GOT edge?");
   }
 
   bool isExternalBranchEdge(Edge &E) {
-    return E.getKind() == Branch26 && !E.getTarget().isDefined();
+    return E.getKind() == aarch64::Branch26 && !E.getTarget().isDefined();
   }
 
   Symbol &createPLTStub(Symbol &Target) {
@@ -463,12 +551,12 @@ class PerGraphGOTAndPLTStubsBuilder_MachO_arm64
         getStubsSection(), getStubBlockContent(), orc::ExecutorAddr(), 1, 0);
     // Re-use GOT entries for stub targets.
     auto &GOTEntrySymbol = getGOTEntry(Target);
-    StubContentBlock.addEdge(LDRLiteral19, 0, GOTEntrySymbol, 0);
+    StubContentBlock.addEdge(aarch64::LDRLiteral19, 0, GOTEntrySymbol, 0);
     return G.addAnonymousSymbol(StubContentBlock, 0, 8, true, false);
   }
 
   void fixPLTEdge(Edge &E, Symbol &Stub) {
-    assert(E.getKind() == Branch26 && "Not a Branch32 edge?");
+    assert(E.getKind() == aarch64::Branch26 && "Not a Branch32 edge?");
     assert(E.getAddend() == 0 && "Branch32 edge has non-zero addend?");
     E.setTarget(Stub);
   }
@@ -525,165 +613,8 @@ class MachOJITLinker_arm64 : public JITLinker<MachOJITLinker_arm64> {
       : JITLinker(std::move(Ctx), std::move(G), std::move(PassConfig)) {}
 
 private:
-
-  static unsigned getPageOffset12Shift(uint32_t Instr) {
-    constexpr uint32_t LoadStoreImm12Mask = 0x3b000000;
-    constexpr uint32_t Vec128Mask = 0x04800000;
-
-    if ((Instr & LoadStoreImm12Mask) == 0x39000000) {
-      uint32_t ImplicitShift = Instr >> 30;
-      if (ImplicitShift == 0)
-        if ((Instr & Vec128Mask) == Vec128Mask)
-          ImplicitShift = 4;
-
-      return ImplicitShift;
-    }
-
-    return 0;
-  }
-
   Error applyFixup(LinkGraph &G, Block &B, const Edge &E) const {
-    using namespace support;
-
-    char *BlockWorkingMem = B.getAlreadyMutableContent().data();
-    char *FixupPtr = BlockWorkingMem + E.getOffset();
-    orc::ExecutorAddr FixupAddress = B.getAddress() + E.getOffset();
-
-    switch (E.getKind()) {
-    case Branch26: {
-      assert((FixupAddress.getValue() & 0x3) == 0 &&
-             "Branch-inst is not 32-bit aligned");
-
-      int64_t Value = E.getTarget().getAddress() - FixupAddress + E.getAddend();
-
-      if (static_cast<uint64_t>(Value) & 0x3)
-        return make_error<JITLinkError>("Branch26 target is not 32-bit "
-                                        "aligned");
-
-      if (Value < -(1 << 27) || Value > ((1 << 27) - 1))
-        return makeTargetOutOfRangeError(G, B, E);
-
-      uint32_t RawInstr = *(little32_t *)FixupPtr;
-      assert((RawInstr & 0x7fffffff) == 0x14000000 &&
-             "RawInstr isn't a B or BR immediate instruction");
-      uint32_t Imm = (static_cast<uint32_t>(Value) & ((1 << 28) - 1)) >> 2;
-      uint32_t FixedInstr = RawInstr | Imm;
-      *(little32_t *)FixupPtr = FixedInstr;
-      break;
-    }
-    case Pointer32: {
-      uint64_t Value = E.getTarget().getAddress().getValue() + E.getAddend();
-      if (Value > std::numeric_limits<uint32_t>::max())
-        return makeTargetOutOfRangeError(G, B, E);
-      *(ulittle32_t *)FixupPtr = Value;
-      break;
-    }
-    case Pointer64:
-    case Pointer64Anon: {
-      uint64_t Value = E.getTarget().getAddress().getValue() + E.getAddend();
-      *(ulittle64_t *)FixupPtr = Value;
-      break;
-    }
-    case Page21:
-    case TLVPage21:
-    case GOTPage21: {
-      assert((E.getKind() != GOTPage21 || E.getAddend() == 0) &&
-             "GOTPAGE21 with non-zero addend");
-      uint64_t TargetPage =
-          (E.getTarget().getAddress().getValue() + E.getAddend()) &
-          ~static_cast<uint64_t>(4096 - 1);
-      uint64_t PCPage =
-          FixupAddress.getValue() & ~static_cast<uint64_t>(4096 - 1);
-
-      int64_t PageDelta = TargetPage - PCPage;
-      if (PageDelta < -(1 << 30) || PageDelta > ((1 << 30) - 1))
-        return makeTargetOutOfRangeError(G, B, E);
-
-      uint32_t RawInstr = *(ulittle32_t *)FixupPtr;
-      assert((RawInstr & 0xffffffe0) == 0x90000000 &&
-             "RawInstr isn't an ADRP instruction");
-      uint32_t ImmLo = (static_cast<uint64_t>(PageDelta) >> 12) & 0x3;
-      uint32_t ImmHi = (static_cast<uint64_t>(PageDelta) >> 14) & 0x7ffff;
-      uint32_t FixedInstr = RawInstr | (ImmLo << 29) | (ImmHi << 5);
-      *(ulittle32_t *)FixupPtr = FixedInstr;
-      break;
-    }
-    case PageOffset12: {
-      uint64_t TargetOffset =
-          (E.getTarget().getAddress() + E.getAddend()).getValue() & 0xfff;
-
-      uint32_t RawInstr = *(ulittle32_t *)FixupPtr;
-      unsigned ImmShift = getPageOffset12Shift(RawInstr);
-
-      if (TargetOffset & ((1 << ImmShift) - 1))
-        return make_error<JITLinkError>("PAGEOFF12 target is not aligned");
-
-      uint32_t EncodedImm = (TargetOffset >> ImmShift) << 10;
-      uint32_t FixedInstr = RawInstr | EncodedImm;
-      *(ulittle32_t *)FixupPtr = FixedInstr;
-      break;
-    }
-    case TLVPageOffset12:
-    case GOTPageOffset12: {
-      assert(E.getAddend() == 0 && "GOTPAGEOF12 with non-zero addend");
-
-      uint32_t RawInstr = *(ulittle32_t *)FixupPtr;
-      assert((RawInstr & 0xfffffc00) == 0xf9400000 &&
-             "RawInstr isn't a 64-bit LDR immediate");
-
-      uint32_t TargetOffset = E.getTarget().getAddress().getValue() & 0xfff;
-      assert((TargetOffset & 0x7) == 0 && "GOT entry is not 8-byte aligned");
-      uint32_t EncodedImm = (TargetOffset >> 3) << 10;
-      uint32_t FixedInstr = RawInstr | EncodedImm;
-      *(ulittle32_t *)FixupPtr = FixedInstr;
-      break;
-    }
-    case LDRLiteral19: {
-      assert((FixupAddress.getValue() & 0x3) == 0 &&
-             "LDR is not 32-bit aligned");
-      assert(E.getAddend() == 0 && "LDRLiteral19 with non-zero addend");
-      uint32_t RawInstr = *(ulittle32_t *)FixupPtr;
-      assert(RawInstr == 0x58000010 && "RawInstr isn't a 64-bit LDR literal");
-      int64_t Delta = E.getTarget().getAddress() - FixupAddress;
-      if (Delta & 0x3)
-        return make_error<JITLinkError>("LDR literal target is not 32-bit "
-                                        "aligned");
-      if (Delta < -(1 << 20) || Delta > ((1 << 20) - 1))
-        return makeTargetOutOfRangeError(G, B, E);
-
-      uint32_t EncodedImm =
-        ((static_cast<uint32_t>(Delta) >> 2) & 0x7ffff) << 5;
-      uint32_t FixedInstr = RawInstr | EncodedImm;
-      *(ulittle32_t *)FixupPtr = FixedInstr;
-      break;
-    }
-    case Delta32:
-    case Delta64:
-    case NegDelta32:
-    case NegDelta64: {
-      int64_t Value;
-      if (E.getKind() == Delta32 || E.getKind() == Delta64)
-        Value = E.getTarget().getAddress() - FixupAddress + E.getAddend();
-      else
-        Value = FixupAddress - E.getTarget().getAddress() + E.getAddend();
-
-      if (E.getKind() == Delta32 || E.getKind() == NegDelta32) {
-        if (Value < std::numeric_limits<int32_t>::min() ||
-            Value > std::numeric_limits<int32_t>::max())
-          return makeTargetOutOfRangeError(G, B, E);
-        *(little32_t *)FixupPtr = Value;
-      } else
-        *(little64_t *)FixupPtr = Value;
-      break;
-    }
-    default:
-      return make_error<JITLinkError>(
-          "In graph " + G.getName() + ", section " + B.getSection().getName() +
-          "unsupported edge kind" +
-          getMachOARM64RelocationKindName(E.getKind()));
-    }
-
-    return Error::success();
+    return aarch64::applyFixup(G, B, E);
   }
 
   uint64_t NullValue = 0;
@@ -718,9 +649,9 @@ void link_MachO_arm64(std::unique_ptr<LinkGraph> G,
     // we support compact-unwind registration with libunwind.
     Config.PrePrunePasses.push_back(
         DWARFRecordSectionSplitter("__TEXT,__eh_frame"));
-    Config.PrePrunePasses.push_back(
-        EHFrameEdgeFixer("__TEXT,__eh_frame", 8, Pointer32, Pointer64, Delta32,
-                         Delta64, NegDelta32));
+    Config.PrePrunePasses.push_back(EHFrameEdgeFixer(
+        "__TEXT,__eh_frame", 8, aarch64::Pointer32, aarch64::Pointer64,
+        aarch64::Delta32, aarch64::Delta64, aarch64::NegDelta32));
 
     // Add an in-place GOT/Stubs pass.
     Config.PostPrunePasses.push_back(
@@ -734,44 +665,5 @@ void link_MachO_arm64(std::unique_ptr<LinkGraph> G,
   MachOJITLinker_arm64::link(std::move(Ctx), std::move(G), std::move(Config));
 }
 
-const char *getMachOARM64RelocationKindName(Edge::Kind R) {
-  switch (R) {
-  case Branch26:
-    return "Branch26";
-  case Pointer64:
-    return "Pointer64";
-  case Pointer64Anon:
-    return "Pointer64Anon";
-  case Page21:
-    return "Page21";
-  case PageOffset12:
-    return "PageOffset12";
-  case GOTPage21:
-    return "GOTPage21";
-  case GOTPageOffset12:
-    return "GOTPageOffset12";
-  case TLVPage21:
-    return "TLVPage21";
-  case TLVPageOffset12:
-    return "TLVPageOffset12";
-  case PointerToGOT:
-    return "PointerToGOT";
-  case PairedAddend:
-    return "PairedAddend";
-  case LDRLiteral19:
-    return "LDRLiteral19";
-  case Delta32:
-    return "Delta32";
-  case Delta64:
-    return "Delta64";
-  case NegDelta32:
-    return "NegDelta32";
-  case NegDelta64:
-    return "NegDelta64";
-  default:
-    return getGenericEdgeKindName(static_cast<Edge::Kind>(R));
-  }
-}
-
 } // end namespace jitlink
 } // end namespace llvm

diff  --git a/llvm/lib/ExecutionEngine/JITLink/aarch64.cpp b/llvm/lib/ExecutionEngine/JITLink/aarch64.cpp
index 6dccc4811885..5a1aaee512e5 100644
--- a/llvm/lib/ExecutionEngine/JITLink/aarch64.cpp
+++ b/llvm/lib/ExecutionEngine/JITLink/aarch64.cpp
@@ -18,13 +18,202 @@ namespace llvm {
 namespace jitlink {
 namespace aarch64 {
 
-const char *getEdgeKindName(Edge::Kind K) {
-  switch (K) {
-  case R_AARCH64_CALL26:
-    return "R_AARCH64_CALL26";
+unsigned getPageOffset12Shift(uint32_t Instr) {
+  constexpr uint32_t LoadStoreImm12Mask = 0x3b000000;
+  constexpr uint32_t Vec128Mask = 0x04800000;
+
+  if ((Instr & LoadStoreImm12Mask) == 0x39000000) {
+    uint32_t ImplicitShift = Instr >> 30;
+    if (ImplicitShift == 0)
+      if ((Instr & Vec128Mask) == Vec128Mask)
+        ImplicitShift = 4;
+
+    return ImplicitShift;
+  }
+
+  return 0;
+}
+
+Error applyFixup(LinkGraph &G, Block &B, const Edge &E) {
+  using namespace support;
+
+  char *BlockWorkingMem = B.getAlreadyMutableContent().data();
+  char *FixupPtr = BlockWorkingMem + E.getOffset();
+  orc::ExecutorAddr FixupAddress = B.getAddress() + E.getOffset();
+
+  switch (E.getKind()) {
+  case Branch26: {
+    assert((FixupAddress.getValue() & 0x3) == 0 &&
+           "Branch-inst is not 32-bit aligned");
+
+    int64_t Value = E.getTarget().getAddress() - FixupAddress + E.getAddend();
+
+    if (static_cast<uint64_t>(Value) & 0x3)
+      return make_error<JITLinkError>("Branch26 target is not 32-bit "
+                                      "aligned");
+
+    if (Value < -(1 << 27) || Value > ((1 << 27) - 1))
+      return makeTargetOutOfRangeError(G, B, E);
+
+    uint32_t RawInstr = *(little32_t *)FixupPtr;
+    assert((RawInstr & 0x7fffffff) == 0x14000000 &&
+           "RawInstr isn't a B or BR immediate instruction");
+    uint32_t Imm = (static_cast<uint32_t>(Value) & ((1 << 28) - 1)) >> 2;
+    uint32_t FixedInstr = RawInstr | Imm;
+    *(little32_t *)FixupPtr = FixedInstr;
+    break;
+  }
+  case Pointer32: {
+    uint64_t Value = E.getTarget().getAddress().getValue() + E.getAddend();
+    if (Value > std::numeric_limits<uint32_t>::max())
+      return makeTargetOutOfRangeError(G, B, E);
+    *(ulittle32_t *)FixupPtr = Value;
+    break;
+  }
+  case Pointer64:
+  case Pointer64Anon: {
+    uint64_t Value = E.getTarget().getAddress().getValue() + E.getAddend();
+    *(ulittle64_t *)FixupPtr = Value;
+    break;
+  }
+  case Page21:
+  case TLVPage21:
+  case GOTPage21: {
+    assert((E.getKind() != GOTPage21 || E.getAddend() == 0) &&
+           "GOTPAGE21 with non-zero addend");
+    uint64_t TargetPage =
+        (E.getTarget().getAddress().getValue() + E.getAddend()) &
+        ~static_cast<uint64_t>(4096 - 1);
+    uint64_t PCPage =
+        FixupAddress.getValue() & ~static_cast<uint64_t>(4096 - 1);
+
+    int64_t PageDelta = TargetPage - PCPage;
+    if (PageDelta < -(1 << 30) || PageDelta > ((1 << 30) - 1))
+      return makeTargetOutOfRangeError(G, B, E);
+
+    uint32_t RawInstr = *(ulittle32_t *)FixupPtr;
+    assert((RawInstr & 0xffffffe0) == 0x90000000 &&
+           "RawInstr isn't an ADRP instruction");
+    uint32_t ImmLo = (static_cast<uint64_t>(PageDelta) >> 12) & 0x3;
+    uint32_t ImmHi = (static_cast<uint64_t>(PageDelta) >> 14) & 0x7ffff;
+    uint32_t FixedInstr = RawInstr | (ImmLo << 29) | (ImmHi << 5);
+    *(ulittle32_t *)FixupPtr = FixedInstr;
+    break;
   }
-  return getGenericEdgeKindName(K);
+  case PageOffset12: {
+    uint64_t TargetOffset =
+        (E.getTarget().getAddress() + E.getAddend()).getValue() & 0xfff;
+
+    uint32_t RawInstr = *(ulittle32_t *)FixupPtr;
+    unsigned ImmShift = getPageOffset12Shift(RawInstr);
+
+    if (TargetOffset & ((1 << ImmShift) - 1))
+      return make_error<JITLinkError>("PAGEOFF12 target is not aligned");
+
+    uint32_t EncodedImm = (TargetOffset >> ImmShift) << 10;
+    uint32_t FixedInstr = RawInstr | EncodedImm;
+    *(ulittle32_t *)FixupPtr = FixedInstr;
+    break;
+  }
+  case TLVPageOffset12:
+  case GOTPageOffset12: {
+    assert(E.getAddend() == 0 && "GOTPAGEOF12 with non-zero addend");
+
+    uint32_t RawInstr = *(ulittle32_t *)FixupPtr;
+    assert((RawInstr & 0xfffffc00) == 0xf9400000 &&
+           "RawInstr isn't a 64-bit LDR immediate");
+
+    uint32_t TargetOffset = E.getTarget().getAddress().getValue() & 0xfff;
+    assert((TargetOffset & 0x7) == 0 && "GOT entry is not 8-byte aligned");
+    uint32_t EncodedImm = (TargetOffset >> 3) << 10;
+    uint32_t FixedInstr = RawInstr | EncodedImm;
+    *(ulittle32_t *)FixupPtr = FixedInstr;
+    break;
+  }
+  case LDRLiteral19: {
+    assert((FixupAddress.getValue() & 0x3) == 0 && "LDR is not 32-bit aligned");
+    assert(E.getAddend() == 0 && "LDRLiteral19 with non-zero addend");
+    uint32_t RawInstr = *(ulittle32_t *)FixupPtr;
+    assert(RawInstr == 0x58000010 && "RawInstr isn't a 64-bit LDR literal");
+    int64_t Delta = E.getTarget().getAddress() - FixupAddress;
+    if (Delta & 0x3)
+      return make_error<JITLinkError>("LDR literal target is not 32-bit "
+                                      "aligned");
+    if (Delta < -(1 << 20) || Delta > ((1 << 20) - 1))
+      return makeTargetOutOfRangeError(G, B, E);
+
+    uint32_t EncodedImm = ((static_cast<uint32_t>(Delta) >> 2) & 0x7ffff) << 5;
+    uint32_t FixedInstr = RawInstr | EncodedImm;
+    *(ulittle32_t *)FixupPtr = FixedInstr;
+    break;
+  }
+  case Delta32:
+  case Delta64:
+  case NegDelta32:
+  case NegDelta64: {
+    int64_t Value;
+    if (E.getKind() == Delta32 || E.getKind() == Delta64)
+      Value = E.getTarget().getAddress() - FixupAddress + E.getAddend();
+    else
+      Value = FixupAddress - E.getTarget().getAddress() + E.getAddend();
+
+    if (E.getKind() == Delta32 || E.getKind() == NegDelta32) {
+      if (Value < std::numeric_limits<int32_t>::min() ||
+          Value > std::numeric_limits<int32_t>::max())
+        return makeTargetOutOfRangeError(G, B, E);
+      *(little32_t *)FixupPtr = Value;
+    } else
+      *(little64_t *)FixupPtr = Value;
+    break;
+  }
+  default:
+    return make_error<JITLinkError>(
+        "In graph " + G.getName() + ", section " + B.getSection().getName() +
+        "unsupported edge kind" + getEdgeKindName(E.getKind()));
+  }
+
+  return Error::success();
 }
+
+const char *getEdgeKindName(Edge::Kind R) {
+  switch (R) {
+  case Branch26:
+    return "Branch26";
+  case Pointer64:
+    return "Pointer64";
+  case Pointer64Anon:
+    return "Pointer64Anon";
+  case Page21:
+    return "Page21";
+  case PageOffset12:
+    return "PageOffset12";
+  case GOTPage21:
+    return "GOTPage21";
+  case GOTPageOffset12:
+    return "GOTPageOffset12";
+  case TLVPage21:
+    return "TLVPage21";
+  case TLVPageOffset12:
+    return "TLVPageOffset12";
+  case PointerToGOT:
+    return "PointerToGOT";
+  case PairedAddend:
+    return "PairedAddend";
+  case LDRLiteral19:
+    return "LDRLiteral19";
+  case Delta32:
+    return "Delta32";
+  case Delta64:
+    return "Delta64";
+  case NegDelta32:
+    return "NegDelta32";
+  case NegDelta64:
+    return "NegDelta64";
+  default:
+    return getGenericEdgeKindName(static_cast<Edge::Kind>(R));
+  }
+}
+
 } // namespace aarch64
 } // namespace jitlink
 } // namespace llvm


        


More information about the llvm-commits mailing list