summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorAsh Logan <ash@heyquark.com>2025-02-27 13:58:38 +0000
committerAnna Wilcox <awilcox@wilcox-tech.com>2025-05-04 17:51:21 +0000
commita63a3d152e1128c76c359ebef570c7b6e752d284 (patch)
tree7af27cf7f2eddc2638c35929083b88c31c216e9a
parent3ce000829d8d4f900fdaedee646ca8bca3a2cbbe (diff)
downloadpackages-a63a3d152e1128c76c359ebef570c7b6e752d284.tar.gz
packages-a63a3d152e1128c76c359ebef570c7b6e752d284.tar.bz2
packages-a63a3d152e1128c76c359ebef570c7b6e752d284.tar.xz
packages-a63a3d152e1128c76c359ebef570c7b6e752d284.zip
user/llvm18: Add support for additional relocation types in RuntimeDyld
* The REL24 relocation is used in JIT'd code for library calls. Implementing this allows the ExecutionEngine tests, clang-repl, and llvmpipe to all start working. * Implement a bunch of "easy" relocations while we're here. These are not really tested. * Anna's existing patch leaked a "delta" variable into the switch scope, so add braces to contain that. Also, the PPC ELF ABI doesn't specify an overflow check for REL32 (unlike ppc64), so remove it and allow truncation. * Add mention of the problematic relocation type to the LLVM error message, so if other relocation types (like the PLT/GOT relocs) end up being needed later, this is obvious from user reports. Partially resolves #1233
-rw-r--r--user/llvm18/APKBUILD28
-rw-r--r--user/llvm18/dyld-elf-ppc32-2.patch176
-rw-r--r--user/llvm18/dyld-elf-ppc32.patch8
3 files changed, 183 insertions, 29 deletions
diff --git a/user/llvm18/APKBUILD b/user/llvm18/APKBUILD
index 694f8245e..bc5bb0c83 100644
--- a/user/llvm18/APKBUILD
+++ b/user/llvm18/APKBUILD
@@ -6,7 +6,7 @@ _pkgname=llvm
pkgver=18.1.8
_majorver=${pkgver%%.*}
pkgname=$_pkgname$_majorver
-pkgrel=0
+pkgrel=1
pkgdesc="Low Level Virtual Machine compiler system, version $_majorver"
url="https://llvm.org/"
arch="all"
@@ -23,6 +23,7 @@ source="https://github.com/llvm/llvm-project/releases/download/llvmorg-$pkgver/l
llvm-fix-build-with-musl-libc.patch
disable-FileSystemTest.CreateDir-perms-assert.patch
dyld-elf-ppc32.patch
+ dyld-elf-ppc32-2.patch
hexagon.patch
i586-json-test.patch
m68k-endianness.patch
@@ -98,28 +99,6 @@ prepare() {
# RISC-V issues are uninvestigated as of yet. #1233
rm -v test/CodeGen/RISCV/rvv/combine-store-extract-crash.ll
rm -v test/CodeGen/RISCV/xtheadmempair.ll
-
- # ExecutionEngine for PPC32 requires R_PPC_REL24 to be
- # implemented in RuntimeDyld.
- for _bad_orc in global-ctor-with-cast.ll \
- global-variable-alignment.ll \
- trivial-call-to-function.ll \
- trivial-call-to-internal-function.ll \
- trivial-reference-to-global-variable.ll \
- trivial-reference-to-internal-variable-nonzeroinit.ll \
- trivial-reference-to-internal-variable-zeroinit.ll \
- trivial-return-zero.ll \
- weak-comdat.ll; do
- rm -v test/ExecutionEngine/Orc/$_bad_orc;
- done
- for _bad_ee in frem.ll mov64zext32.ll \
- test-interp-vec-arithm_float.ll \
- test-interp-vec-arithm_int.ll \
- test-interp-vec-logical.ll \
- test-interp-vec-setcond-fp.ll \
- test-interp-vec-setcond-int.ll; do
- rm -v test/ExecutionEngine/$_bad_ee;
- done
esac
#1053
@@ -337,7 +316,8 @@ _common_subpkg() {
sha512sums="25eeee9984c8b4d0fbc240df90f33cbb000d3b0414baff5c8982beafcc5e59e7ef18f6f85d95b3a5f60cb3d4cd4f877c80487b5768bc21bc833f107698ad93db llvm-project-18.1.8.src.tar.xz
f84cd65d7042e89826ba6e8d48c4c302bf4980da369d7f19a55f217e51c00ca8ed178d453df3a3cee76598a7cecb94aed0775a6d24fe73266f82749913fc3e71 llvm-fix-build-with-musl-libc.patch
d56945bb0476561028616222846257f990d66e68b4458894f8791252411038b269831f9400ed9df3b99f571a82443caaac347a8b38a5516c77c3583469118309 disable-FileSystemTest.CreateDir-perms-assert.patch
-9e919d7988b18c7184d9fccd14911d70bbe2acf82d38111bfd41f1ba2976fea07e74527a43c552dad158c982a2cbaaf03f6a1e98c7a1fc02b4e75382cfe6d0b2 dyld-elf-ppc32.patch
+94099a2001d38d935ece69943971e7943691e8a5471b31ae2169e1f2f2e60de8a9fe8ba718dfa942c84d22fced7492bc9b87bce84a3e801a46e549c4657f9eb5 dyld-elf-ppc32.patch
+23cd4c38899bf001f6e27db9a21dfb9fa1264a81993ef423535ff3132d2a258b4706d201ff15a96624db82540ee09c14810af0392f0786262699dfdbcb47b9ba dyld-elf-ppc32-2.patch
807587a0c897d47a01a846c5c4f7cbf1f2d16437a163b66ee2381a7147e9d04b0141b2c76d022db61903d0d2841ddb267ba98c66c9e41501ca41837659743df8 hexagon.patch
22dedbbdc99ab4df6c64921186803552fc61cfc00a5cd052295a5450809e7205ac21dd07df158b7e99b960084b2ec3d8832480a8cd073fe1c2d613cd21c90b60 i586-json-test.patch
b186ce027dca389cfd23dc91b03e023e688c7610745cf62d0b277b6178972bcf55abf0df08453f2a6b85dc61dba929cb565cb30633a2fe0f193a443f54025bf7 m68k-endianness.patch
diff --git a/user/llvm18/dyld-elf-ppc32-2.patch b/user/llvm18/dyld-elf-ppc32-2.patch
new file mode 100644
index 000000000..d424554e2
--- /dev/null
+++ b/user/llvm18/dyld-elf-ppc32-2.patch
@@ -0,0 +1,176 @@
+Author: Ash Logan <ash@heyquark.com>
+
+adds a whole bunch of ppc32 relocation types - probably only REL32 and REL24 are actually needed, or
+indeed tested.
+mostly copypasted from the ppc64 code with ELFv2 ABI removed. No attempt is made to support GOT/PLT
+relocations, since the JIT doesn't seem to generate these.
+
+makes clang-repl and the ExecutionEngine testsuites pass, and allows llvmpipe to run
+
+diff -rup llvm/lib/ExecutionEngine/RuntimeDyld/RuntimeDyld.cpp llvm/lib/ExecutionEngine/RuntimeDyld/RuntimeDyld.cpp
+--- llvm/lib/ExecutionEngine/RuntimeDyld/RuntimeDyld.cpp 2024-06-16 03:21:32.000000000 +1000
++++ llvm/lib/ExecutionEngine/RuntimeDyld/RuntimeDyld.cpp 2025-02-26 00:10:04.114888980 +1100
+@@ -1029,6 +1029,14 @@ uint8_t *RuntimeDyldImpl::createStubFunc
+ writeBytesUnaligned(JrT9Instr, Addr + 24, 4);
+ writeBytesUnaligned(NopInstr, Addr + 28, 4);
+ return Addr;
++ } else if (Arch == Triple::ppc || Arch == Triple::ppcle) {
++ // The ABI docs talk endlessly of PLTs and GOTs which have special relocation types.
++ // For the generic types, just do a generic jump.
++ writeInt32BE(Addr, 0x3D800000); // lis r12, h(addr)
++ writeInt32BE(Addr+4, 0x618C0000); // ori r12, l(addr)
++ writeInt32BE(Addr+8, 0x7D8903A6); // mtctr r12
++ writeInt32BE(Addr+12, 0x4E800420); // bctr
++ return Addr;
+ } else if (Arch == Triple::ppc64 || Arch == Triple::ppc64le) {
+ // Depending on which version of the ELF ABI is in use, we need to
+ // generate one of two variants of the stub. They both start with
+diff -rup llvm/lib/ExecutionEngine/RuntimeDyld/RuntimeDyldELF.cpp llvm/lib/ExecutionEngine/RuntimeDyld/RuntimeDyldELF.cpp
+--- llvm/lib/ExecutionEngine/RuntimeDyld/RuntimeDyldELF.cpp 2024-06-16 03:21:32.000000000 +1000
++++ llvm/lib/ExecutionEngine/RuntimeDyld/RuntimeDyldELF.cpp 2025-02-26 00:32:57.021079997 +1100
+@@ -819,7 +819,7 @@ void RuntimeDyldELF::resolvePPC32Relocat
+ uint8_t *LocalAddress = Section.getAddressWithOffset(Offset);
+ switch (Type) {
+ default:
+- report_fatal_error("Relocation type not implemented yet!");
++ report_fatal_error("Relocation type " + Twine(Type) + " not implemented yet!");
+ break;
+ case ELF::R_PPC_ADDR16_LO:
+ writeInt16BE(LocalAddress, applyPPClo(Value + Addend));
+@@ -835,6 +835,37 @@ void RuntimeDyldELF::resolvePPC32Relocat
+ int64_t delta = static_cast<int64_t>(Value - FinalAddress + Addend);
+ writeInt32BE(LocalAddress, delta);
+ } break;
++ case ELF::R_PPC_REL24: {
++ uint32_t FinalAddress = Section.getLoadAddressWithOffset(Offset);
++ int64_t delta = static_cast<int64_t>(Value - FinalAddress + Addend);
++ if (SignExtend64<26>(delta) != delta)
++ llvm_unreachable("Relocation R_PPC_REL24 overflow");
++ uint32_t Inst = readBytesUnaligned(LocalAddress, 4);
++ writeInt32BE(LocalAddress, (Inst & 0xFC000003) | (delta & 0x03FFFFFC));
++ } break;
++ case ELF::R_PPC_ADDR32: {
++ int64_t delta = static_cast<int64_t>(Value + Addend);
++ writeInt32BE(LocalAddress, delta);
++ } break;
++ case ELF::R_PPC_ADDR30: {
++ uint32_t FinalAddress = Section.getLoadAddressWithOffset(Offset);
++ int64_t delta = static_cast<int64_t>(Value - FinalAddress + Addend);
++ uint32_t Inst = readBytesUnaligned(LocalAddress, 4);
++ writeInt32BE(LocalAddress, (Inst & 0x00000003) | (delta & 0xFFFFFFFC));
++ } break;
++ case ELF::R_PPC_ADDR24: {
++ int64_t delta = static_cast<int64_t>(Value + Addend);
++ if (SignExtend64<26>(delta) != delta)
++ llvm_unreachable("Relocation R_PPC_ADDR24 overflow");
++ uint32_t Inst = readBytesUnaligned(LocalAddress, 4);
++ writeInt32BE(LocalAddress, (Inst & 0xFC000003) | (delta & 0x03FFFFFC));
++ } break;
++ case ELF::R_PPC_ADDR16: {
++ int64_t delta = static_cast<int64_t>(Value + Addend);
++ if (SignExtend64<16>(delta) != delta)
++ llvm_unreachable("Relocation R_PPC_ADDR16 overflow");
++ writeInt16BE(LocalAddress, delta);
++ } break;
+ }
+ }
+
+@@ -1551,6 +1587,76 @@ RuntimeDyldELF::processRelocationRef(
+ processSimpleRelocation(SectionID, Offset, RelType, Value);
+ }
+
++ } else if (Arch == Triple::ppc || Arch == Triple::ppcle) {
++ if (RelType == ELF::R_PPC_REL24) {
++ // A PPC branch relocation will need a stub function if the target is
++ // an external symbol (either Value.SymbolName is set, or SymType is
++ // Symbol::ST_Unknown) or if the target address is not within the
++ // signed 24-bits branch address.
++ SectionEntry &Section = Sections[SectionID];
++ uint8_t *Target = Section.getAddressWithOffset(Offset);
++ bool RangeOverflow = false;
++ bool IsExtern = Value.SymbolName || SymType == SymbolRef::ST_Unknown;
++ if (!IsExtern) {
++ uint8_t *RelocTarget =
++ Sections[Value.SectionID].getAddressWithOffset(Value.Addend);
++ int64_t delta = static_cast<int64_t>(Target - RelocTarget);
++ // If it is within 26-bits branch range, just set the branch target
++ if (SignExtend64<26>(delta) != delta) {
++ RangeOverflow = true;
++ } else {
++ RelocationEntry RE(SectionID, Offset, RelType, Value.Addend);
++ addRelocationForSection(RE, Value.SectionID);
++ }
++ }
++ if (IsExtern || RangeOverflow) {
++ // It is an external symbol (either Value.SymbolName is set, or
++ // SymType is SymbolRef::ST_Unknown) or out of range.
++ StubMap::const_iterator i = Stubs.find(Value);
++ if (i != Stubs.end()) {
++ // Symbol function stub already created, just relocate to it
++ resolveRelocation(Section, Offset,
++ reinterpret_cast<uint64_t>(
++ Section.getAddressWithOffset(i->second)),
++ RelType, 0);
++ LLVM_DEBUG(dbgs() << " Stub function found\n");
++ } else {
++ // Create a new stub function.
++ LLVM_DEBUG(dbgs() << " Create a new stub function\n");
++ Stubs[Value] = Section.getStubOffset();
++ uint8_t *StubTargetAddr = createStubFunction(
++ Section.getAddressWithOffset(Section.getStubOffset()));
++
++ // The PPC32 ELF ABI doesn't really provide any guidance on the no-PLT case so let's do
++ // our best
++ uint64_t StubRelocOffset = StubTargetAddr - Section.getAddress();
++ if (!IsTargetLittleEndian)
++ StubRelocOffset += 2;
++
++ RelocationEntry REh(SectionID, StubRelocOffset + 0,
++ ELF::R_PPC_ADDR16_HI, Value.Addend);
++ RelocationEntry REl(SectionID, StubRelocOffset + 4,
++ ELF::R_PPC_ADDR16_LO, Value.Addend);
++
++ if (Value.SymbolName) {
++ addRelocationForSymbol(REh, Value.SymbolName);
++ addRelocationForSymbol(REl, Value.SymbolName);
++ } else {
++ addRelocationForSection(REh, Value.SectionID);
++ addRelocationForSection(REl, Value.SectionID);
++ }
++
++ resolveRelocation(Section, Offset, reinterpret_cast<uint64_t>(
++ Section.getAddressWithOffset(
++ Section.getStubOffset())),
++ RelType, 0);
++ Section.advanceStubOffset(getMaxStubSize());
++ }
++ }
++ } else {
++ // Normal relocations are fine as-is probs
++ processSimpleRelocation(SectionID, Offset, RelType, Value);
++ }
+ } else if (Arch == Triple::ppc64 || Arch == Triple::ppc64le) {
+ if (RelType == ELF::R_PPC64_REL24) {
+ // Determine ABI variant in use for this object.
+@@ -2228,6 +2334,8 @@ size_t RuntimeDyldELF::getGOTEntrySize()
+ case Triple::x86:
+ case Triple::arm:
+ case Triple::thumb:
++ case Triple::ppc:
++ case Triple::ppcle:
+ Result = sizeof(uint32_t);
+ break;
+ case Triple::mips:
+diff -rup llvm/lib/ExecutionEngine/RuntimeDyld/RuntimeDyldELF.h llvm/lib/ExecutionEngine/RuntimeDyld/RuntimeDyldELF.h
+--- llvm/lib/ExecutionEngine/RuntimeDyld/RuntimeDyldELF.h 2024-06-16 03:21:32.000000000 +1000
++++ llvm/lib/ExecutionEngine/RuntimeDyld/RuntimeDyldELF.h 2025-02-25 23:51:24.830956991 +1100
+@@ -69,6 +69,8 @@ class RuntimeDyldELF : public RuntimeDyl
+ return 16;
+ else if (IsMipsN64ABI)
+ return 32;
++ else if (Arch == Triple::ppc || Arch == Triple::ppcle)
++ return 16;
+ else if (Arch == Triple::ppc64 || Arch == Triple::ppc64le)
+ return 44;
+ else if (Arch == Triple::x86_64)
+
diff --git a/user/llvm18/dyld-elf-ppc32.patch b/user/llvm18/dyld-elf-ppc32.patch
index 7fb744169..77ff8c644 100644
--- a/user/llvm18/dyld-elf-ppc32.patch
+++ b/user/llvm18/dyld-elf-ppc32.patch
@@ -8,17 +8,15 @@ Needs more tests before submitting upstream, but seems to DTRT.
--- llvm-14.0.6.src/lib/ExecutionEngine/RuntimeDyld/RuntimeDyldELF.cpp.old 2022-06-22 16:46:24.000000000 +0000
+++ llvm-14.0.6.src/lib/ExecutionEngine/RuntimeDyld/RuntimeDyldELF.cpp 2022-11-28 06:33:12.239921624 +0000
-@@ -830,6 +830,13 @@
+@@ -830,6 +830,11 @@
case ELF::R_PPC_ADDR16_HA:
writeInt16BE(LocalAddress, applyPPCha(Value + Addend));
break;
-+ case ELF::R_PPC_REL32:
++ case ELF::R_PPC_REL32: {
+ uint32_t FinalAddress = Section.getLoadAddressWithOffset(Offset);
+ int64_t delta = static_cast<int64_t>(Value - FinalAddress + Addend);
-+ if (SignExtend64<32>(delta) != delta)
-+ llvm_unreachable("Relocation R_PPC_REL32 overflow");
+ writeInt32BE(LocalAddress, delta);
-+ break;
++ } break;
}
}