Skip to content

Commit f3128a1

Browse files
committed
Fix custom EHFrame registration on llvm21
1 parent 2193b19 commit f3128a1

File tree

1 file changed

+83
-3
lines changed

1 file changed

+83
-3
lines changed

src/jitlayers.cpp

Lines changed: 83 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -16,6 +16,7 @@
1616
#include <llvm/ExecutionEngine/Orc/DebugObjectManagerPlugin.h>
1717
#if JL_LLVM_VERSION >= 210000
1818
# include <llvm/ExecutionEngine/Orc/SelfExecutorProcessControl.h>
19+
# include <llvm/ExecutionEngine/Orc/Shared/OrcRTBridge.h>
1920
#endif
2021
#include <llvm/ExecutionEngine/Orc/TargetProcess/JITLoaderGDB.h>
2122
#if JL_LLVM_VERSION >= 200000
@@ -1226,6 +1227,8 @@ std::unique_ptr<jitlink::JITLinkMemoryManager> createJITLinkMemoryManager() JL_N
12261227
#endif
12271228
}
12281229

1230+
#if defined(JL_USE_JITLINK) && defined(LLVM_SHLIB)
1231+
# if JL_LLVM_VERSION < 210000
12291232
class JLEHFrameRegistrar final : public jitlink::EHFrameRegistrar {
12301233
public:
12311234
Error registerEHFrames(orc::ExecutorAddrRange EHFrameSection) override {
@@ -1238,6 +1241,72 @@ class JLEHFrameRegistrar final : public jitlink::EHFrameRegistrar {
12381241
return Error::success();
12391242
}
12401243
};
1244+
# else
1245+
class JLEHFrameRegistrationPlugin final : public LinkGraphLinkingLayer::Plugin {
1246+
static Error registerEHFrameWrapper(orc::ExecutorAddrRange EHFrame) {
1247+
register_eh_frames(EHFrame.Start.toPtr<uint8_t *>(), static_cast<size_t>(EHFrame.size()));
1248+
return Error::success();
1249+
}
1250+
1251+
static Error deregisterEHFrameWrapper(orc::ExecutorAddrRange EHFrame) {
1252+
deregister_eh_frames(EHFrame.Start.toPtr<uint8_t *>(), static_cast<size_t>(EHFrame.size()));
1253+
return Error::success();
1254+
}
1255+
1256+
static orc::shared::CWrapperFunctionResult
1257+
registerEHFrameSectionAllocAction(const char *ArgData, size_t ArgSize) {
1258+
using namespace llvm::orc::shared;
1259+
return WrapperFunction<SPSError(SPSExecutorAddrRange)>::handle(
1260+
ArgData, ArgSize, registerEHFrameWrapper)
1261+
.release();
1262+
}
1263+
1264+
static orc::shared::CWrapperFunctionResult
1265+
deregisterEHFrameSectionAllocAction(const char *ArgData, size_t ArgSize) {
1266+
using namespace llvm::orc::shared;
1267+
return WrapperFunction<SPSError(SPSExecutorAddrRange)>::handle(
1268+
ArgData, ArgSize, deregisterEHFrameWrapper)
1269+
.release();
1270+
}
1271+
1272+
static Error postFixup(jitlink::LinkGraph &G)
1273+
{
1274+
using namespace llvm::orc::shared;
1275+
auto registerFrame = ExecutorAddr::fromPtr(registerEHFrameSectionAllocAction);
1276+
auto deregisterFrame = ExecutorAddr::fromPtr(deregisterEHFrameSectionAllocAction);
1277+
if (auto *EHFrame = jitlink::getEHFrameSection(G)) {
1278+
auto R = jitlink::SectionRange(*EHFrame).getRange();
1279+
G.allocActions().push_back(
1280+
{cantFail(
1281+
WrapperFunctionCall::Create<SPSArgList<SPSExecutorAddrRange>>(
1282+
registerFrame, R)),
1283+
cantFail(
1284+
WrapperFunctionCall::Create<SPSArgList<SPSExecutorAddrRange>>(
1285+
deregisterFrame, R))});
1286+
}
1287+
return Error::success();
1288+
}
1289+
1290+
public:
1291+
JLEHFrameRegistrationPlugin() {}
1292+
1293+
void modifyPassConfig(MaterializationResponsibility&,
1294+
jitlink::LinkGraph&,
1295+
jitlink::PassConfiguration &PassConfig) override
1296+
{
1297+
PassConfig.PostFixupPasses.push_back(postFixup);
1298+
}
1299+
Error notifyFailed(MaterializationResponsibility&) override {
1300+
return Error::success();
1301+
}
1302+
Error notifyRemovingResources(JITDylib&, ResourceKey) override {
1303+
return Error::success();
1304+
}
1305+
void notifyTransferringResources(JITDylib&, ResourceKey,
1306+
ResourceKey) override {}
1307+
};
1308+
# endif
1309+
#endif
12411310

12421311
RTDyldMemoryManager *createRTDyldMemoryManager(void) JL_NOTSAFEPOINT;
12431312

@@ -1950,15 +2019,26 @@ JuliaOJIT::JuliaOJIT()
19502019
OptSelLayer(ES, OptimizeLayer, static_cast<orc::ThreadSafeModule (*)(orc::ThreadSafeModule, orc::MaterializationResponsibility&)>(selectOptLevel))
19512020
{
19522021
#ifdef JL_USE_JITLINK
1953-
# if defined(LLVM_SHLIB)
2022+
# if JL_LLVM_VERSION < 210000
2023+
# if defined(LLVM_SHLIB)
19542024
// When dynamically linking against LLVM, use our custom EH frame registration code
19552025
// also used with RTDyld to inform both our and the libc copy of libunwind.
19562026
auto ehRegistrar = std::make_unique<JLEHFrameRegistrar>();
1957-
# else
2027+
# else
19582028
auto ehRegistrar = std::make_unique<jitlink::InProcessEHFrameRegistrar>();
1959-
# endif
2029+
# endif
19602030
ObjectLayer.addPlugin(std::make_unique<EHFrameRegistrationPlugin>(
19612031
ES, std::move(ehRegistrar)));
2032+
#else
2033+
// llvm's EHFrameRegistrationPlugin does not seem to have any customization
2034+
// hooks in 21+. Do our own registration with a separate plugin instead.
2035+
# if defined(LLVM_SHLIB)
2036+
// When dynamically linking against LLVM, use our custom EH frame registration code
2037+
// also used with RTDyld to inform both our and the libc copy of libunwind.
2038+
ObjectLayer.addPlugin(std::make_unique<JLEHFrameRegistrationPlugin>());
2039+
# endif
2040+
ObjectLayer.addPlugin(std::move(EHFrameRegistrationPlugin::Create(ES).get()));
2041+
#endif
19622042

19632043
ObjectLayer.addPlugin(std::make_unique<JLDebuginfoPlugin>());
19642044
ObjectLayer.addPlugin(std::make_unique<JLMemoryUsagePlugin>(&jit_bytes_size));

0 commit comments

Comments
 (0)