aboutsummaryrefslogtreecommitdiff
path: root/llvm/lib/ExecutionEngine
diff options
context:
space:
mode:
authorLang Hames <lhames@gmail.com>2016-08-19 01:15:39 +0000
committerLang Hames <lhames@gmail.com>2016-08-19 01:15:39 +0000
commitb65f16c8e56bd88872ba1fa5740b8628b361dccd (patch)
tree0cc4cdc11868aecf600dd0409dae4534dbcdcc60 /llvm/lib/ExecutionEngine
parent719238b7d3907182e5c1e325370a1b55dc438b2e (diff)
downloadllvm-b65f16c8e56bd88872ba1fa5740b8628b361dccd.zip
llvm-b65f16c8e56bd88872ba1fa5740b8628b361dccd.tar.gz
llvm-b65f16c8e56bd88872ba1fa5740b8628b361dccd.tar.bz2
[RuntimeDyld] Add support for ELF R_ARM_REL32 and R_ARM_GOT_PREL.
Patch by William Dillon. Thanks William! This patch adds support for the R_ARM_REL32 and R_ARM_GOT_PREL ELF ARM relocations to RuntimeDyld, which should allow JITing of code that produces these relocations. No test case: Unfortunately RuntimeDyldELF's GOT building mechanism (which uses a separate section for GOT entries) isn't compatible with RuntimeDyldChecker. The correct fix for this is to fix RuntimeDyldELF's GOT support (it's fundamentally broken at the moment: separate sections aren't guaranteed to be in range of a GOT entry load), but that's a non-trivial job. llvm-svn: 279182
Diffstat (limited to 'llvm/lib/ExecutionEngine')
-rw-r--r--llvm/lib/ExecutionEngine/RuntimeDyld/RuntimeDyldELF.cpp16
1 files changed, 16 insertions, 0 deletions
diff --git a/llvm/lib/ExecutionEngine/RuntimeDyld/RuntimeDyldELF.cpp b/llvm/lib/ExecutionEngine/RuntimeDyld/RuntimeDyldELF.cpp
index 6929732..5bc3264 100644
--- a/llvm/lib/ExecutionEngine/RuntimeDyld/RuntimeDyldELF.cpp
+++ b/llvm/lib/ExecutionEngine/RuntimeDyld/RuntimeDyldELF.cpp
@@ -480,6 +480,9 @@ void RuntimeDyldELF::resolveARMRelocation(const SectionEntry &Section,
*TargetPtr |= Value & 0xFFF;
*TargetPtr |= ((Value >> 12) & 0xF) << 16;
break;
+ case ELF::R_ARM_REL32:
+ *TargetPtr += Value - FinalAddress;
+ break;
// Write 24 bit relative value to the branch instruction.
case ELF::R_ARM_PC24: // Fall through.
case ELF::R_ARM_CALL: // Fall through.
@@ -1365,6 +1368,19 @@ RuntimeDyldELF::processRelocationRef(
RelType, 0);
Section.advanceStubOffset(getMaxStubSize());
}
+ } else if (RelType == ELF::R_ARM_GOT_PREL) {
+ uint32_t GOTOffset = allocateGOTEntries(SectionID, 1);
+
+ RelocationEntry GOTRE(SectionID, Offset, ELF::R_ARM_REL32, GOTOffset);
+ addRelocationForSection(GOTRE, GOTSectionID);
+
+ // Fill in the value of the symbol we're targeting into the GOT
+ RelocationEntry RE = computeGOTOffsetRE(SectionID, GOTOffset,
+ Value.Offset, ELF::R_ARM_ABS32);
+ if (Value.SymbolName)
+ addRelocationForSymbol(RE, Value.SymbolName);
+ else
+ addRelocationForSection(RE, Value.SectionID);
} else {
uint32_t *Placeholder =
reinterpret_cast<uint32_t*>(computePlaceholderAddress(SectionID, Offset));