summaryrefslogtreecommitdiff
path: root/llvm/lib/ExecutionEngine
diff options
context:
space:
mode:
authorDimitry Andric <dim@FreeBSD.org>2023-12-17 20:41:09 +0000
committerDimitry Andric <dim@FreeBSD.org>2023-12-17 20:41:09 +0000
commit312c0ed19cc5276a17bacf2120097bec4515b0f1 (patch)
treee6e4a4163840b73ba54bb0d3b70ee4899e4b7434 /llvm/lib/ExecutionEngine
parentb1c73532ee8997fe5dfbeb7d223027bdf99758a0 (diff)
Diffstat (limited to 'llvm/lib/ExecutionEngine')
-rw-r--r--llvm/lib/ExecutionEngine/JITLink/ELF_x86_64.cpp4
-rw-r--r--llvm/lib/ExecutionEngine/JITLink/MachOLinkGraphBuilder.cpp2
-rw-r--r--llvm/lib/ExecutionEngine/Orc/Debugging/DebugInfoSupport.cpp2
-rw-r--r--llvm/lib/ExecutionEngine/Orc/Debugging/DebuggerSupport.cpp2
-rw-r--r--llvm/lib/ExecutionEngine/Orc/Debugging/DebuggerSupportPlugin.cpp2
-rw-r--r--llvm/lib/ExecutionEngine/Orc/Debugging/LLJITUtilsCBindings.cpp22
-rw-r--r--llvm/lib/ExecutionEngine/Orc/ExecutionUtils.cpp6
-rw-r--r--llvm/lib/ExecutionEngine/Orc/IndirectionUtils.cpp2
-rw-r--r--llvm/lib/ExecutionEngine/Orc/LLJIT.cpp111
-rw-r--r--llvm/lib/ExecutionEngine/Orc/MachOPlatform.cpp208
-rw-r--r--llvm/lib/ExecutionEngine/Orc/ObjectFileInterface.cpp2
-rw-r--r--llvm/lib/ExecutionEngine/Orc/Shared/ObjectFormats.cpp2
-rw-r--r--llvm/lib/ExecutionEngine/RuntimeDyld/JITSymbol.cpp2
-rw-r--r--llvm/lib/ExecutionEngine/RuntimeDyld/RuntimeDyldCOFF.cpp3
-rw-r--r--llvm/lib/ExecutionEngine/RuntimeDyld/RuntimeDyldChecker.cpp52
-rw-r--r--llvm/lib/ExecutionEngine/RuntimeDyld/Targets/RuntimeDyldCOFFAArch64.h2
-rw-r--r--llvm/lib/ExecutionEngine/RuntimeDyld/Targets/RuntimeDyldCOFFI386.h2
-rw-r--r--llvm/lib/ExecutionEngine/RuntimeDyld/Targets/RuntimeDyldCOFFThumb.h2
-rw-r--r--llvm/lib/ExecutionEngine/RuntimeDyld/Targets/RuntimeDyldCOFFX86_64.h2
19 files changed, 222 insertions, 208 deletions
diff --git a/llvm/lib/ExecutionEngine/JITLink/ELF_x86_64.cpp b/llvm/lib/ExecutionEngine/JITLink/ELF_x86_64.cpp
index 46f8064bb168..a1fe9c5fcd73 100644
--- a/llvm/lib/ExecutionEngine/JITLink/ELF_x86_64.cpp
+++ b/llvm/lib/ExecutionEngine/JITLink/ELF_x86_64.cpp
@@ -349,11 +349,11 @@ identifyELFSectionStartAndEndSymbols(LinkGraph &G, Symbol &Sym) {
constexpr StringRef EndSymbolPrefix = "__end";
auto SymName = Sym.getName();
- if (SymName.startswith(StartSymbolPrefix)) {
+ if (SymName.starts_with(StartSymbolPrefix)) {
if (auto *Sec =
G.findSectionByName(SymName.drop_front(StartSymbolPrefix.size())))
return {*Sec, true};
- } else if (SymName.startswith(EndSymbolPrefix)) {
+ } else if (SymName.starts_with(EndSymbolPrefix)) {
if (auto *Sec =
G.findSectionByName(SymName.drop_front(EndSymbolPrefix.size())))
return {*Sec, false};
diff --git a/llvm/lib/ExecutionEngine/JITLink/MachOLinkGraphBuilder.cpp b/llvm/lib/ExecutionEngine/JITLink/MachOLinkGraphBuilder.cpp
index bcbc429cae12..bb21f633d982 100644
--- a/llvm/lib/ExecutionEngine/JITLink/MachOLinkGraphBuilder.cpp
+++ b/llvm/lib/ExecutionEngine/JITLink/MachOLinkGraphBuilder.cpp
@@ -73,7 +73,7 @@ Linkage MachOLinkGraphBuilder::getLinkage(uint16_t Desc) {
Scope MachOLinkGraphBuilder::getScope(StringRef Name, uint8_t Type) {
if (Type & MachO::N_EXT) {
- if ((Type & MachO::N_PEXT) || Name.startswith("l"))
+ if ((Type & MachO::N_PEXT) || Name.starts_with("l"))
return Scope::Hidden;
else
return Scope::Default;
diff --git a/llvm/lib/ExecutionEngine/Orc/Debugging/DebugInfoSupport.cpp b/llvm/lib/ExecutionEngine/Orc/Debugging/DebugInfoSupport.cpp
index b541db3672f4..f65ec27ff875 100644
--- a/llvm/lib/ExecutionEngine/Orc/Debugging/DebugInfoSupport.cpp
+++ b/llvm/lib/ExecutionEngine/Orc/Debugging/DebugInfoSupport.cpp
@@ -105,7 +105,7 @@ llvm::orc::createDWARFContext(LinkGraph &G) {
auto SecData = getSectionData(Sec);
auto Name = Sec.getName();
// DWARFContext expects the section name to not start with a dot
- if (Name.startswith("."))
+ if (Name.starts_with("."))
Name = Name.drop_front();
LLVM_DEBUG(dbgs() << "Creating DWARFContext section " << Name
<< " with size " << SecData.size() << "\n");
diff --git a/llvm/lib/ExecutionEngine/Orc/Debugging/DebuggerSupport.cpp b/llvm/lib/ExecutionEngine/Orc/Debugging/DebuggerSupport.cpp
index 9ba6dd90f50d..1668473c0eb4 100644
--- a/llvm/lib/ExecutionEngine/Orc/Debugging/DebuggerSupport.cpp
+++ b/llvm/lib/ExecutionEngine/Orc/Debugging/DebuggerSupport.cpp
@@ -39,7 +39,7 @@ Error enableDebuggerSupport(LLJIT &J) {
if (!Registrar)
return Registrar.takeError();
ObjLinkingLayer->addPlugin(std::make_unique<DebugObjectManagerPlugin>(
- ES, std::move(*Registrar), true, true));
+ ES, std::move(*Registrar), false, true));
return Error::success();
}
case Triple::MachO: {
diff --git a/llvm/lib/ExecutionEngine/Orc/Debugging/DebuggerSupportPlugin.cpp b/llvm/lib/ExecutionEngine/Orc/Debugging/DebuggerSupportPlugin.cpp
index c6ffd9f7c2e3..e387b06ee934 100644
--- a/llvm/lib/ExecutionEngine/Orc/Debugging/DebuggerSupportPlugin.cpp
+++ b/llvm/lib/ExecutionEngine/Orc/Debugging/DebuggerSupportPlugin.cpp
@@ -34,7 +34,7 @@ class MachODebugObjectSynthesizerBase
: public GDBJITDebugInfoRegistrationPlugin::DebugSectionSynthesizer {
public:
static bool isDebugSection(Section &Sec) {
- return Sec.getName().startswith("__DWARF,");
+ return Sec.getName().starts_with("__DWARF,");
}
MachODebugObjectSynthesizerBase(LinkGraph &G, ExecutorAddr RegisterActionAddr)
diff --git a/llvm/lib/ExecutionEngine/Orc/Debugging/LLJITUtilsCBindings.cpp b/llvm/lib/ExecutionEngine/Orc/Debugging/LLJITUtilsCBindings.cpp
new file mode 100644
index 000000000000..2df5aef733fb
--- /dev/null
+++ b/llvm/lib/ExecutionEngine/Orc/Debugging/LLJITUtilsCBindings.cpp
@@ -0,0 +1,22 @@
+//===--------- LLJITUtilsCBindings.cpp - Advanced LLJIT features ----------===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===----------------------------------------------------------------------===//
+
+#include "llvm-c/LLJIT.h"
+#include "llvm-c/LLJITUtils.h"
+
+#include "llvm/ExecutionEngine/Orc/Debugging/DebuggerSupport.h"
+#include "llvm/ExecutionEngine/Orc/LLJIT.h"
+
+using namespace llvm;
+using namespace llvm::orc;
+
+DEFINE_SIMPLE_CONVERSION_FUNCTIONS(LLJIT, LLVMOrcLLJITRef)
+
+LLVMErrorRef LLVMOrcLLJITEnableDebugSupport(LLVMOrcLLJITRef J) {
+ return wrap(llvm::orc::enableDebuggerSupport(*unwrap(J)));
+}
diff --git a/llvm/lib/ExecutionEngine/Orc/ExecutionUtils.cpp b/llvm/lib/ExecutionEngine/Orc/ExecutionUtils.cpp
index 7316b2dce8ab..8d5608cc4d4c 100644
--- a/llvm/lib/ExecutionEngine/Orc/ExecutionUtils.cpp
+++ b/llvm/lib/ExecutionEngine/Orc/ExecutionUtils.cpp
@@ -103,8 +103,8 @@ bool StaticInitGVIterator::isStaticInitGlobal(GlobalValue &GV) {
// FIXME: These section checks are too strict: We should match first and
// second word split by comma.
if (GV.hasSection() &&
- (GV.getSection().startswith("__DATA,__objc_classlist") ||
- GV.getSection().startswith("__DATA,__objc_selrefs")))
+ (GV.getSection().starts_with("__DATA,__objc_classlist") ||
+ GV.getSection().starts_with("__DATA,__objc_selrefs")))
return true;
}
@@ -503,7 +503,7 @@ Error DLLImportDefinitionGenerator::tryToGenerate(
DenseMap<StringRef, SymbolLookupFlags> ToLookUpSymbols;
for (auto &KV : Symbols) {
StringRef Deinterned = *KV.first;
- if (Deinterned.startswith(getImpPrefix()))
+ if (Deinterned.starts_with(getImpPrefix()))
Deinterned = Deinterned.drop_front(StringRef(getImpPrefix()).size());
// Don't degrade the required state
if (ToLookUpSymbols.count(Deinterned) &&
diff --git a/llvm/lib/ExecutionEngine/Orc/IndirectionUtils.cpp b/llvm/lib/ExecutionEngine/Orc/IndirectionUtils.cpp
index adf38659de3d..f9efff148df9 100644
--- a/llvm/lib/ExecutionEngine/Orc/IndirectionUtils.cpp
+++ b/llvm/lib/ExecutionEngine/Orc/IndirectionUtils.cpp
@@ -285,7 +285,7 @@ std::vector<GlobalValue *> SymbolLinkagePromoter::operator()(Module &M) {
// Rename if necessary.
if (!GV.hasName())
GV.setName("__orc_anon." + Twine(NextId++));
- else if (GV.getName().startswith("\01L"))
+ else if (GV.getName().starts_with("\01L"))
GV.setName("__" + GV.getName().substr(1) + "." + Twine(NextId++));
else if (GV.hasLocalLinkage())
GV.setName("__orc_lcl." + GV.getName() + "." + Twine(NextId++));
diff --git a/llvm/lib/ExecutionEngine/Orc/LLJIT.cpp b/llvm/lib/ExecutionEngine/Orc/LLJIT.cpp
index 90123b3f0a96..a19e17029810 100644
--- a/llvm/lib/ExecutionEngine/Orc/LLJIT.cpp
+++ b/llvm/lib/ExecutionEngine/Orc/LLJIT.cpp
@@ -84,65 +84,6 @@ Function *addHelperAndWrapper(Module &M, StringRef WrapperName,
return WrapperFn;
}
-class ORCPlatformSupport : public LLJIT::PlatformSupport {
-public:
- ORCPlatformSupport(orc::LLJIT &J) : J(J) {}
-
- Error initialize(orc::JITDylib &JD) override {
- using llvm::orc::shared::SPSExecutorAddr;
- using llvm::orc::shared::SPSString;
- using SPSDLOpenSig = SPSExecutorAddr(SPSString, int32_t);
- enum dlopen_mode : int32_t {
- ORC_RT_RTLD_LAZY = 0x1,
- ORC_RT_RTLD_NOW = 0x2,
- ORC_RT_RTLD_LOCAL = 0x4,
- ORC_RT_RTLD_GLOBAL = 0x8
- };
-
- auto &ES = J.getExecutionSession();
- auto MainSearchOrder = J.getMainJITDylib().withLinkOrderDo(
- [](const JITDylibSearchOrder &SO) { return SO; });
-
- if (auto WrapperAddr =
- ES.lookup(MainSearchOrder,
- J.mangleAndIntern("__orc_rt_jit_dlopen_wrapper"))) {
- return ES.callSPSWrapper<SPSDLOpenSig>(WrapperAddr->getAddress(),
- DSOHandles[&JD], JD.getName(),
- int32_t(ORC_RT_RTLD_LAZY));
- } else
- return WrapperAddr.takeError();
- }
-
- Error deinitialize(orc::JITDylib &JD) override {
- using llvm::orc::shared::SPSExecutorAddr;
- using SPSDLCloseSig = int32_t(SPSExecutorAddr);
-
- auto &ES = J.getExecutionSession();
- auto MainSearchOrder = J.getMainJITDylib().withLinkOrderDo(
- [](const JITDylibSearchOrder &SO) { return SO; });
-
- if (auto WrapperAddr =
- ES.lookup(MainSearchOrder,
- J.mangleAndIntern("__orc_rt_jit_dlclose_wrapper"))) {
- int32_t result;
- auto E = J.getExecutionSession().callSPSWrapper<SPSDLCloseSig>(
- WrapperAddr->getAddress(), result, DSOHandles[&JD]);
- if (E)
- return E;
- else if (result)
- return make_error<StringError>("dlclose failed",
- inconvertibleErrorCode());
- DSOHandles.erase(&JD);
- } else
- return WrapperAddr.takeError();
- return Error::success();
- }
-
-private:
- orc::LLJIT &J;
- DenseMap<orc::JITDylib *, orc::ExecutorAddr> DSOHandles;
-};
-
class GenericLLVMIRPlatformSupport;
/// orc::Platform component of Generic LLVM IR Platform support.
@@ -272,11 +213,11 @@ public:
// will trigger a lookup to materialize the module) and the InitFunctions
// map (which holds the names of the symbols to execute).
for (auto &KV : MU.getSymbols())
- if ((*KV.first).startswith(InitFunctionPrefix)) {
+ if ((*KV.first).starts_with(InitFunctionPrefix)) {
InitSymbols[&JD].add(KV.first,
SymbolLookupFlags::WeaklyReferencedSymbol);
InitFunctions[&JD].add(KV.first);
- } else if ((*KV.first).startswith(DeInitFunctionPrefix)) {
+ } else if ((*KV.first).starts_with(DeInitFunctionPrefix)) {
DeInitFunctions[&JD].add(KV.first);
}
}
@@ -656,6 +597,54 @@ public:
namespace llvm {
namespace orc {
+Error ORCPlatformSupport::initialize(orc::JITDylib &JD) {
+ using llvm::orc::shared::SPSExecutorAddr;
+ using llvm::orc::shared::SPSString;
+ using SPSDLOpenSig = SPSExecutorAddr(SPSString, int32_t);
+ enum dlopen_mode : int32_t {
+ ORC_RT_RTLD_LAZY = 0x1,
+ ORC_RT_RTLD_NOW = 0x2,
+ ORC_RT_RTLD_LOCAL = 0x4,
+ ORC_RT_RTLD_GLOBAL = 0x8
+ };
+
+ auto &ES = J.getExecutionSession();
+ auto MainSearchOrder = J.getMainJITDylib().withLinkOrderDo(
+ [](const JITDylibSearchOrder &SO) { return SO; });
+
+ if (auto WrapperAddr = ES.lookup(
+ MainSearchOrder, J.mangleAndIntern("__orc_rt_jit_dlopen_wrapper"))) {
+ return ES.callSPSWrapper<SPSDLOpenSig>(WrapperAddr->getAddress(),
+ DSOHandles[&JD], JD.getName(),
+ int32_t(ORC_RT_RTLD_LAZY));
+ } else
+ return WrapperAddr.takeError();
+}
+
+Error ORCPlatformSupport::deinitialize(orc::JITDylib &JD) {
+ using llvm::orc::shared::SPSExecutorAddr;
+ using SPSDLCloseSig = int32_t(SPSExecutorAddr);
+
+ auto &ES = J.getExecutionSession();
+ auto MainSearchOrder = J.getMainJITDylib().withLinkOrderDo(
+ [](const JITDylibSearchOrder &SO) { return SO; });
+
+ if (auto WrapperAddr = ES.lookup(
+ MainSearchOrder, J.mangleAndIntern("__orc_rt_jit_dlclose_wrapper"))) {
+ int32_t result;
+ auto E = J.getExecutionSession().callSPSWrapper<SPSDLCloseSig>(
+ WrapperAddr->getAddress(), result, DSOHandles[&JD]);
+ if (E)
+ return E;
+ else if (result)
+ return make_error<StringError>("dlclose failed",
+ inconvertibleErrorCode());
+ DSOHandles.erase(&JD);
+ } else
+ return WrapperAddr.takeError();
+ return Error::success();
+}
+
void LLJIT::PlatformSupport::setInitTransform(
LLJIT &J, IRTransformLayer::TransformFunction T) {
J.InitHelperTransformLayer->setTransform(std::move(T));
diff --git a/llvm/lib/ExecutionEngine/Orc/MachOPlatform.cpp b/llvm/lib/ExecutionEngine/Orc/MachOPlatform.cpp
index a155b39ae263..9057300bf043 100644
--- a/llvm/lib/ExecutionEngine/Orc/MachOPlatform.cpp
+++ b/llvm/lib/ExecutionEngine/Orc/MachOPlatform.cpp
@@ -15,6 +15,7 @@
#include "llvm/ExecutionEngine/Orc/DebugUtils.h"
#include "llvm/ExecutionEngine/Orc/ExecutionUtils.h"
#include "llvm/ExecutionEngine/Orc/LookupAndRecordAddrs.h"
+#include "llvm/ExecutionEngine/Orc/MachOBuilder.h"
#include "llvm/ExecutionEngine/Orc/Shared/ObjectFormats.h"
#include "llvm/Support/BinaryByteStream.h"
#include "llvm/Support/Debug.h"
@@ -115,100 +116,6 @@ std::unique_ptr<jitlink::LinkGraph> createPlatformGraph(MachOPlatform &MOP,
jitlink::getGenericEdgeKindName);
}
-// Generates a MachO header.
-class MachOHeaderMaterializationUnit : public MaterializationUnit {
-public:
- MachOHeaderMaterializationUnit(MachOPlatform &MOP,
- const SymbolStringPtr &HeaderStartSymbol)
- : MaterializationUnit(createHeaderInterface(MOP, HeaderStartSymbol)),
- MOP(MOP) {}
-
- StringRef getName() const override { return "MachOHeaderMU"; }
-
- void materialize(std::unique_ptr<MaterializationResponsibility> R) override {
- auto G = createPlatformGraph(MOP, "<MachOHeaderMU>");
- addMachOHeader(*G, MOP, R->getInitializerSymbol());
- MOP.getObjectLinkingLayer().emit(std::move(R), std::move(G));
- }
-
- void discard(const JITDylib &JD, const SymbolStringPtr &Sym) override {}
-
- static void addMachOHeader(jitlink::LinkGraph &G, MachOPlatform &MOP,
- const SymbolStringPtr &InitializerSymbol) {
- auto &HeaderSection = G.createSection("__header", MemProt::Read);
- auto &HeaderBlock = createHeaderBlock(G, HeaderSection);
-
- // Init symbol is header-start symbol.
- G.addDefinedSymbol(HeaderBlock, 0, *InitializerSymbol,
- HeaderBlock.getSize(), jitlink::Linkage::Strong,
- jitlink::Scope::Default, false, true);
- for (auto &HS : AdditionalHeaderSymbols)
- G.addDefinedSymbol(HeaderBlock, HS.Offset, HS.Name, HeaderBlock.getSize(),
- jitlink::Linkage::Strong, jitlink::Scope::Default,
- false, true);
- }
-
-private:
- struct HeaderSymbol {
- const char *Name;
- uint64_t Offset;
- };
-
- static constexpr HeaderSymbol AdditionalHeaderSymbols[] = {
- {"___mh_executable_header", 0}};
-
- static jitlink::Block &createHeaderBlock(jitlink::LinkGraph &G,
- jitlink::Section &HeaderSection) {
- MachO::mach_header_64 Hdr;
- Hdr.magic = MachO::MH_MAGIC_64;
- switch (G.getTargetTriple().getArch()) {
- case Triple::aarch64:
- Hdr.cputype = MachO::CPU_TYPE_ARM64;
- Hdr.cpusubtype = MachO::CPU_SUBTYPE_ARM64_ALL;
- break;
- case Triple::x86_64:
- Hdr.cputype = MachO::CPU_TYPE_X86_64;
- Hdr.cpusubtype = MachO::CPU_SUBTYPE_X86_64_ALL;
- break;
- default:
- llvm_unreachable("Unrecognized architecture");
- }
- Hdr.filetype = MachO::MH_DYLIB; // Custom file type?
- Hdr.ncmds = 0;
- Hdr.sizeofcmds = 0;
- Hdr.flags = 0;
- Hdr.reserved = 0;
-
- if (G.getEndianness() != llvm::endianness::native)
- MachO::swapStruct(Hdr);
-
- auto HeaderContent = G.allocateContent(
- ArrayRef<char>(reinterpret_cast<const char *>(&Hdr), sizeof(Hdr)));
-
- return G.createContentBlock(HeaderSection, HeaderContent, ExecutorAddr(), 8,
- 0);
- }
-
- static MaterializationUnit::Interface
- createHeaderInterface(MachOPlatform &MOP,
- const SymbolStringPtr &HeaderStartSymbol) {
- SymbolFlagsMap HeaderSymbolFlags;
-
- HeaderSymbolFlags[HeaderStartSymbol] = JITSymbolFlags::Exported;
- for (auto &HS : AdditionalHeaderSymbols)
- HeaderSymbolFlags[MOP.getExecutionSession().intern(HS.Name)] =
- JITSymbolFlags::Exported;
-
- return MaterializationUnit::Interface(std::move(HeaderSymbolFlags),
- HeaderStartSymbol);
- }
-
- MachOPlatform &MOP;
-};
-
-constexpr MachOHeaderMaterializationUnit::HeaderSymbol
- MachOHeaderMaterializationUnit::AdditionalHeaderSymbols[];
-
// Creates a Bootstrap-Complete LinkGraph to run deferred actions.
class MachOPlatformCompleteBootstrapMaterializationUnit
: public MaterializationUnit {
@@ -352,6 +259,7 @@ Expected<std::unique_ptr<MachOPlatform>>
MachOPlatform::Create(ExecutionSession &ES, ObjectLinkingLayer &ObjLinkingLayer,
JITDylib &PlatformJD,
std::unique_ptr<DefinitionGenerator> OrcRuntime,
+ MachOHeaderMUBuilder BuildMachOHeaderMU,
std::optional<SymbolAliasMap> RuntimeAliases) {
// If the target is not supported then bail out immediately.
@@ -382,8 +290,9 @@ MachOPlatform::Create(ExecutionSession &ES, ObjectLinkingLayer &ObjLinkingLayer,
// Create the instance.
Error Err = Error::success();
- auto P = std::unique_ptr<MachOPlatform>(new MachOPlatform(
- ES, ObjLinkingLayer, PlatformJD, std::move(OrcRuntime), Err));
+ auto P = std::unique_ptr<MachOPlatform>(
+ new MachOPlatform(ES, ObjLinkingLayer, PlatformJD, std::move(OrcRuntime),
+ std::move(BuildMachOHeaderMU), Err));
if (Err)
return std::move(Err);
return std::move(P);
@@ -392,6 +301,7 @@ MachOPlatform::Create(ExecutionSession &ES, ObjectLinkingLayer &ObjLinkingLayer,
Expected<std::unique_ptr<MachOPlatform>>
MachOPlatform::Create(ExecutionSession &ES, ObjectLinkingLayer &ObjLinkingLayer,
JITDylib &PlatformJD, const char *OrcRuntimePath,
+ MachOHeaderMUBuilder BuildMachOHeaderMU,
std::optional<SymbolAliasMap> RuntimeAliases) {
// Create a generator for the ORC runtime archive.
@@ -402,12 +312,11 @@ MachOPlatform::Create(ExecutionSession &ES, ObjectLinkingLayer &ObjLinkingLayer,
return Create(ES, ObjLinkingLayer, PlatformJD,
std::move(*OrcRuntimeArchiveGenerator),
- std::move(RuntimeAliases));
+ std::move(BuildMachOHeaderMU), std::move(RuntimeAliases));
}
Error MachOPlatform::setupJITDylib(JITDylib &JD) {
- if (auto Err = JD.define(std::make_unique<MachOHeaderMaterializationUnit>(
- *this, MachOHeaderStartSymbol)))
+ if (auto Err = JD.define(BuildMachOHeaderMU(*this)))
return Err;
return ES.lookup({&JD}, MachOHeaderStartSymbol).takeError();
@@ -522,8 +431,10 @@ MachOPlatform::flagsForSymbol(jitlink::Symbol &Sym) {
MachOPlatform::MachOPlatform(
ExecutionSession &ES, ObjectLinkingLayer &ObjLinkingLayer,
JITDylib &PlatformJD,
- std::unique_ptr<DefinitionGenerator> OrcRuntimeGenerator, Error &Err)
- : ES(ES), PlatformJD(PlatformJD), ObjLinkingLayer(ObjLinkingLayer) {
+ std::unique_ptr<DefinitionGenerator> OrcRuntimeGenerator,
+ MachOHeaderMUBuilder BuildMachOHeaderMU, Error &Err)
+ : ES(ES), PlatformJD(PlatformJD), ObjLinkingLayer(ObjLinkingLayer),
+ BuildMachOHeaderMU(std::move(BuildMachOHeaderMU)) {
ErrorAsOutParameter _(&Err);
ObjLinkingLayer.addPlugin(std::make_unique<MachOPlatformPlugin>(*this));
PlatformJD.addGenerator(std::move(OrcRuntimeGenerator));
@@ -586,8 +497,7 @@ MachOPlatform::MachOPlatform(
// the support methods callable. The bootstrap is now complete.
// Step (1) Add header materialization unit and request.
- if ((Err = PlatformJD.define(std::make_unique<MachOHeaderMaterializationUnit>(
- *this, MachOHeaderStartSymbol))))
+ if ((Err = PlatformJD.define(this->BuildMachOHeaderMU(*this))))
return;
if ((Err = ES.lookup(&PlatformJD, MachOHeaderStartSymbol).takeError()))
return;
@@ -1755,5 +1665,97 @@ Error MachOPlatform::MachOPlatformPlugin::addSymbolTableRegistration(
return Error::success();
}
+
+template <typename MachOTraits>
+jitlink::Block &createTrivialHeaderBlock(MachOPlatform &MOP,
+ jitlink::LinkGraph &G,
+ jitlink::Section &HeaderSection) {
+ auto HdrInfo =
+ getMachOHeaderInfoFromTriple(MOP.getExecutionSession().getTargetTriple());
+ MachOBuilder<MachOTraits> B(HdrInfo.PageSize);
+
+ B.Header.filetype = MachO::MH_DYLIB;
+ B.Header.cputype = HdrInfo.CPUType;
+ B.Header.cpusubtype = HdrInfo.CPUSubType;
+
+ auto HeaderContent = G.allocateBuffer(B.layout());
+ B.write(HeaderContent);
+
+ return G.createContentBlock(HeaderSection, HeaderContent, ExecutorAddr(), 8,
+ 0);
+}
+
+SimpleMachOHeaderMU::SimpleMachOHeaderMU(MachOPlatform &MOP,
+ SymbolStringPtr HeaderStartSymbol)
+ : MaterializationUnit(
+ createHeaderInterface(MOP, std::move(HeaderStartSymbol))),
+ MOP(MOP) {}
+
+void SimpleMachOHeaderMU::materialize(
+ std::unique_ptr<MaterializationResponsibility> R) {
+ auto G = createPlatformGraph(MOP, "<MachOHeaderMU>");
+ addMachOHeader(R->getTargetJITDylib(), *G, R->getInitializerSymbol());
+ MOP.getObjectLinkingLayer().emit(std::move(R), std::move(G));
+}
+
+void SimpleMachOHeaderMU::discard(const JITDylib &JD,
+ const SymbolStringPtr &Sym) {}
+
+void SimpleMachOHeaderMU::addMachOHeader(
+ JITDylib &JD, jitlink::LinkGraph &G,
+ const SymbolStringPtr &InitializerSymbol) {
+ auto &HeaderSection = G.createSection("__header", MemProt::Read);
+ auto &HeaderBlock = createHeaderBlock(JD, G, HeaderSection);
+
+ // Init symbol is header-start symbol.
+ G.addDefinedSymbol(HeaderBlock, 0, *InitializerSymbol, HeaderBlock.getSize(),
+ jitlink::Linkage::Strong, jitlink::Scope::Default, false,
+ true);
+ for (auto &HS : AdditionalHeaderSymbols)
+ G.addDefinedSymbol(HeaderBlock, HS.Offset, HS.Name, HeaderBlock.getSize(),
+ jitlink::Linkage::Strong, jitlink::Scope::Default, false,
+ true);
+}
+
+jitlink::Block &
+SimpleMachOHeaderMU::createHeaderBlock(JITDylib &JD, jitlink::LinkGraph &G,
+ jitlink::Section &HeaderSection) {
+ switch (MOP.getExecutionSession().getTargetTriple().getArch()) {
+ case Triple::aarch64:
+ case Triple::x86_64:
+ return createTrivialHeaderBlock<MachO64LE>(MOP, G, HeaderSection);
+ default:
+ llvm_unreachable("Unsupported architecture");
+ }
+}
+
+MaterializationUnit::Interface SimpleMachOHeaderMU::createHeaderInterface(
+ MachOPlatform &MOP, const SymbolStringPtr &HeaderStartSymbol) {
+ SymbolFlagsMap HeaderSymbolFlags;
+
+ HeaderSymbolFlags[HeaderStartSymbol] = JITSymbolFlags::Exported;
+ for (auto &HS : AdditionalHeaderSymbols)
+ HeaderSymbolFlags[MOP.getExecutionSession().intern(HS.Name)] =
+ JITSymbolFlags::Exported;
+
+ return MaterializationUnit::Interface(std::move(HeaderSymbolFlags),
+ HeaderStartSymbol);
+}
+
+MachOHeaderInfo getMachOHeaderInfoFromTriple(const Triple &TT) {
+ switch (TT.getArch()) {
+ case Triple::aarch64:
+ return {/* PageSize = */ 16 * 1024,
+ /* CPUType = */ MachO::CPU_TYPE_ARM64,
+ /* CPUSubType = */ MachO::CPU_SUBTYPE_ARM64_ALL};
+ case Triple::x86_64:
+ return {/* PageSize = */ 4 * 1024,
+ /* CPUType = */ MachO::CPU_TYPE_X86_64,
+ /* CPUSubType = */ MachO::CPU_SUBTYPE_X86_64_ALL};
+ default:
+ llvm_unreachable("Unrecognized architecture");
+ }
+}
+
} // End namespace orc.
} // End namespace llvm.
diff --git a/llvm/lib/ExecutionEngine/Orc/ObjectFileInterface.cpp b/llvm/lib/ExecutionEngine/Orc/ObjectFileInterface.cpp
index 7c8fa63477d0..0286b0c93197 100644
--- a/llvm/lib/ExecutionEngine/Orc/ObjectFileInterface.cpp
+++ b/llvm/lib/ExecutionEngine/Orc/ObjectFileInterface.cpp
@@ -72,7 +72,7 @@ getMachOObjectFileSymbolInfo(ExecutionSession &ES,
return SymFlags.takeError();
// Strip the 'exported' flag from MachO linker-private symbols.
- if (Name->startswith("l"))
+ if (Name->starts_with("l"))
*SymFlags &= ~JITSymbolFlags::Exported;
I.SymbolFlags[ES.intern(*Name)] = std::move(*SymFlags);
diff --git a/llvm/lib/ExecutionEngine/Orc/Shared/ObjectFormats.cpp b/llvm/lib/ExecutionEngine/Orc/Shared/ObjectFormats.cpp
index 1d9d23e64158..a407fcab6ae3 100644
--- a/llvm/lib/ExecutionEngine/Orc/Shared/ObjectFormats.cpp
+++ b/llvm/lib/ExecutionEngine/Orc/Shared/ObjectFormats.cpp
@@ -102,7 +102,7 @@ bool isELFInitializerSection(StringRef SecName) {
}
bool isCOFFInitializerSection(StringRef SecName) {
- return SecName.startswith(".CRT");
+ return SecName.starts_with(".CRT");
}
} // namespace orc
diff --git a/llvm/lib/ExecutionEngine/RuntimeDyld/JITSymbol.cpp b/llvm/lib/ExecutionEngine/RuntimeDyld/JITSymbol.cpp
index 210fbf6e43e3..c153b4464568 100644
--- a/llvm/lib/ExecutionEngine/RuntimeDyld/JITSymbol.cpp
+++ b/llvm/lib/ExecutionEngine/RuntimeDyld/JITSymbol.cpp
@@ -42,7 +42,7 @@ JITSymbolFlags llvm::JITSymbolFlags::fromGlobalValue(const GlobalValue &GV) {
const auto &DL = M->getDataLayout();
StringRef LPGP = DL.getLinkerPrivateGlobalPrefix();
if (!LPGP.empty() && GV.getName().front() == '\01' &&
- GV.getName().substr(1).startswith(LPGP))
+ GV.getName().substr(1).starts_with(LPGP))
Flags &= ~JITSymbolFlags::Exported;
}
diff --git a/llvm/lib/ExecutionEngine/RuntimeDyld/RuntimeDyldCOFF.cpp b/llvm/lib/ExecutionEngine/RuntimeDyld/RuntimeDyldCOFF.cpp
index 9255311f992d..25a2d8780fb5 100644
--- a/llvm/lib/ExecutionEngine/RuntimeDyld/RuntimeDyldCOFF.cpp
+++ b/llvm/lib/ExecutionEngine/RuntimeDyld/RuntimeDyldCOFF.cpp
@@ -83,7 +83,8 @@ uint64_t RuntimeDyldCOFF::getDLLImportOffset(unsigned SectionID, StubMap &Stubs,
StringRef Name,
bool SetSectionIDMinus1) {
LLVM_DEBUG(dbgs() << "Getting DLLImport entry for " << Name << "... ");
- assert(Name.startswith(getImportSymbolPrefix()) && "Not a DLLImport symbol?");
+ assert(Name.starts_with(getImportSymbolPrefix()) &&
+ "Not a DLLImport symbol?");
RelocationValueRef Reloc;
Reloc.SymbolName = Name.data();
auto I = Stubs.find(Reloc);
diff --git a/llvm/lib/ExecutionEngine/RuntimeDyld/RuntimeDyldChecker.cpp b/llvm/lib/ExecutionEngine/RuntimeDyld/RuntimeDyldChecker.cpp
index 68497305f06b..7fadbdd6a1ff 100644
--- a/llvm/lib/ExecutionEngine/RuntimeDyld/RuntimeDyldChecker.cpp
+++ b/llvm/lib/ExecutionEngine/RuntimeDyld/RuntimeDyldChecker.cpp
@@ -142,7 +142,7 @@ private:
std::tie(Token, Remaining) = parseNumberString(Expr);
else {
unsigned TokLen = 1;
- if (Expr.startswith("<<") || Expr.startswith(">>"))
+ if (Expr.starts_with("<<") || Expr.starts_with(">>"))
TokLen = 2;
Token = Expr.substr(0, TokLen);
}
@@ -177,9 +177,9 @@ private:
return std::make_pair(BinOpToken::Invalid, "");
// Handle the two 2-character tokens.
- if (Expr.startswith("<<"))
+ if (Expr.starts_with("<<"))
return std::make_pair(BinOpToken::ShiftLeft, Expr.substr(2).ltrim());
- if (Expr.startswith(">>"))
+ if (Expr.starts_with(">>"))
return std::make_pair(BinOpToken::ShiftRight, Expr.substr(2).ltrim());
// Handle one-character tokens.
@@ -242,7 +242,7 @@ private:
// On success, returns a pair containing the value of the operand, plus
// the expression remaining to be evaluated.
std::pair<EvalResult, StringRef> evalDecodeOperand(StringRef Expr) const {
- if (!Expr.startswith("("))
+ if (!Expr.starts_with("("))
return std::make_pair(unexpectedToken(Expr, Expr, "expected '('"), "");
StringRef RemainingExpr = Expr.substr(1).ltrim();
StringRef Symbol;
@@ -273,7 +273,7 @@ private:
"");
}
- if (!RemainingExpr.startswith(","))
+ if (!RemainingExpr.starts_with(","))
return std::make_pair(
unexpectedToken(RemainingExpr, RemainingExpr, "expected ','"), "");
RemainingExpr = RemainingExpr.substr(1).ltrim();
@@ -283,7 +283,7 @@ private:
if (OpIdxExpr.hasError())
return std::make_pair(OpIdxExpr, "");
- if (!RemainingExpr.startswith(")"))
+ if (!RemainingExpr.starts_with(")"))
return std::make_pair(
unexpectedToken(RemainingExpr, RemainingExpr, "expected ')'"), "");
RemainingExpr = RemainingExpr.substr(1).ltrim();
@@ -343,7 +343,7 @@ private:
// expression remaining to be evaluated.
std::pair<EvalResult, StringRef> evalNextPC(StringRef Expr,
ParseContext PCtx) const {
- if (!Expr.startswith("("))
+ if (!Expr.starts_with("("))
return std::make_pair(unexpectedToken(Expr, Expr, "expected '('"), "");
StringRef RemainingExpr = Expr.substr(1).ltrim();
StringRef Symbol;
@@ -354,7 +354,7 @@ private:
EvalResult(("Cannot decode unknown symbol '" + Symbol + "'").str()),
"");
- if (!RemainingExpr.startswith(")"))
+ if (!RemainingExpr.starts_with(")"))
return std::make_pair(
unexpectedToken(RemainingExpr, RemainingExpr, "expected ')'"), "");
RemainingExpr = RemainingExpr.substr(1).ltrim();
@@ -381,7 +381,7 @@ private:
// remaining to be evaluated.
std::pair<EvalResult, StringRef>
evalStubOrGOTAddr(StringRef Expr, ParseContext PCtx, bool IsStubAddr) const {
- if (!Expr.startswith("("))
+ if (!Expr.starts_with("("))
return std::make_pair(unexpectedToken(Expr, Expr, "expected '('"), "");
StringRef RemainingExpr = Expr.substr(1).ltrim();
@@ -392,7 +392,7 @@ private:
StubContainerName = RemainingExpr.substr(0, ComaIdx).rtrim();
RemainingExpr = RemainingExpr.substr(ComaIdx).ltrim();
- if (!RemainingExpr.startswith(","))
+ if (!RemainingExpr.starts_with(","))
return std::make_pair(
unexpectedToken(RemainingExpr, Expr, "expected ','"), "");
RemainingExpr = RemainingExpr.substr(1).ltrim();
@@ -400,7 +400,7 @@ private:
StringRef Symbol;
std::tie(Symbol, RemainingExpr) = parseSymbol(RemainingExpr);
- if (!RemainingExpr.startswith(")"))
+ if (!RemainingExpr.starts_with(")"))
return std::make_pair(
unexpectedToken(RemainingExpr, Expr, "expected ')'"), "");
RemainingExpr = RemainingExpr.substr(1).ltrim();
@@ -418,7 +418,7 @@ private:
std::pair<EvalResult, StringRef> evalSectionAddr(StringRef Expr,
ParseContext PCtx) const {
- if (!Expr.startswith("("))
+ if (!Expr.starts_with("("))
return std::make_pair(unexpectedToken(Expr, Expr, "expected '('"), "");
StringRef RemainingExpr = Expr.substr(1).ltrim();
@@ -429,7 +429,7 @@ private:
FileName = RemainingExpr.substr(0, ComaIdx).rtrim();
RemainingExpr = RemainingExpr.substr(ComaIdx).ltrim();
- if (!RemainingExpr.startswith(","))
+ if (!RemainingExpr.starts_with(","))
return std::make_pair(
unexpectedToken(RemainingExpr, Expr, "expected ','"), "");
RemainingExpr = RemainingExpr.substr(1).ltrim();
@@ -439,7 +439,7 @@ private:
SectionName = RemainingExpr.substr(0, CloseParensIdx).rtrim();
RemainingExpr = RemainingExpr.substr(CloseParensIdx).ltrim();
- if (!RemainingExpr.startswith(")"))
+ if (!RemainingExpr.starts_with(")"))
return std::make_pair(
unexpectedToken(RemainingExpr, Expr, "expected ')'"), "");
RemainingExpr = RemainingExpr.substr(1).ltrim();
@@ -480,7 +480,7 @@ private:
std::string ErrMsg("No known address for symbol '");
ErrMsg += Symbol;
ErrMsg += "'";
- if (Symbol.startswith("L"))
+ if (Symbol.starts_with("L"))
ErrMsg += " (this appears to be an assembler local label - "
" perhaps drop the 'L'?)";
@@ -501,7 +501,7 @@ private:
// pair representing the number and the expression remaining to be parsed.
std::pair<StringRef, StringRef> parseNumberString(StringRef Expr) const {
size_t FirstNonDigit = StringRef::npos;
- if (Expr.startswith("0x")) {
+ if (Expr.starts_with("0x")) {
FirstNonDigit = Expr.find_first_not_of("0123456789abcdefABCDEF", 2);
if (FirstNonDigit == StringRef::npos)
FirstNonDigit = Expr.size();
@@ -535,14 +535,14 @@ private:
// remaining to be parsed.
std::pair<EvalResult, StringRef> evalParensExpr(StringRef Expr,
ParseContext PCtx) const {
- assert(Expr.startswith("(") && "Not a parenthesized expression");
+ assert(Expr.starts_with("(") && "Not a parenthesized expression");
EvalResult SubExprResult;
StringRef RemainingExpr;
std::tie(SubExprResult, RemainingExpr) =
evalComplexExpr(evalSimpleExpr(Expr.substr(1).ltrim(), PCtx), PCtx);
if (SubExprResult.hasError())
return std::make_pair(SubExprResult, "");
- if (!RemainingExpr.startswith(")"))
+ if (!RemainingExpr.starts_with(")"))
return std::make_pair(
unexpectedToken(RemainingExpr, Expr, "expected ')'"), "");
RemainingExpr = RemainingExpr.substr(1).ltrim();
@@ -554,11 +554,11 @@ private:
// Return a pair containing the result, plus the expression remaining to be
// parsed.
std::pair<EvalResult, StringRef> evalLoadExpr(StringRef Expr) const {
- assert(Expr.startswith("*") && "Not a load expression");
+ assert(Expr.starts_with("*") && "Not a load expression");
StringRef RemainingExpr = Expr.substr(1).ltrim();
// Parse read size.
- if (!RemainingExpr.startswith("{"))
+ if (!RemainingExpr.starts_with("{"))
return std::make_pair(EvalResult("Expected '{' following '*'."), "");
RemainingExpr = RemainingExpr.substr(1).ltrim();
EvalResult ReadSizeExpr;
@@ -568,7 +568,7 @@ private:
uint64_t ReadSize = ReadSizeExpr.getValue();
if (ReadSize < 1 || ReadSize > 8)
return std::make_pair(EvalResult("Invalid size for dereference."), "");
- if (!RemainingExpr.startswith("}"))
+ if (!RemainingExpr.starts_with("}"))
return std::make_pair(EvalResult("Missing '}' for dereference."), "");
RemainingExpr = RemainingExpr.substr(1).ltrim();
@@ -625,7 +625,7 @@ private:
return std::make_pair(SubExprResult, RemainingExpr);
// Evaluate bit-slice if present.
- if (RemainingExpr.startswith("["))
+ if (RemainingExpr.starts_with("["))
std::tie(SubExprResult, RemainingExpr) =
evalSliceExpr(std::make_pair(SubExprResult, RemainingExpr));
@@ -645,7 +645,7 @@ private:
StringRef RemainingExpr;
std::tie(SubExprResult, RemainingExpr) = Ctx;
- assert(RemainingExpr.startswith("[") && "Not a slice expr.");
+ assert(RemainingExpr.starts_with("[") && "Not a slice expr.");
RemainingExpr = RemainingExpr.substr(1).ltrim();
EvalResult HighBitExpr;
@@ -654,7 +654,7 @@ private:
if (HighBitExpr.hasError())
return std::make_pair(HighBitExpr, RemainingExpr);
- if (!RemainingExpr.startswith(":"))
+ if (!RemainingExpr.starts_with(":"))
return std::make_pair(
unexpectedToken(RemainingExpr, RemainingExpr, "expected ':'"), "");
RemainingExpr = RemainingExpr.substr(1).ltrim();
@@ -665,7 +665,7 @@ private:
if (LowBitExpr.hasError())
return std::make_pair(LowBitExpr, RemainingExpr);
- if (!RemainingExpr.startswith("]"))
+ if (!RemainingExpr.starts_with("]"))
return std::make_pair(
unexpectedToken(RemainingExpr, RemainingExpr, "expected ']'"), "");
RemainingExpr = RemainingExpr.substr(1).ltrim();
@@ -846,7 +846,7 @@ bool RuntimeDyldCheckerImpl::checkAllRulesInBuffer(StringRef RulePrefix,
++LineEnd;
StringRef Line(LineStart, LineEnd - LineStart);
- if (Line.startswith(RulePrefix))
+ if (Line.starts_with(RulePrefix))
CheckExpr += Line.substr(RulePrefix.size()).str();
// If there's a check expr string...
diff --git a/llvm/lib/ExecutionEngine/RuntimeDyld/Targets/RuntimeDyldCOFFAArch64.h b/llvm/lib/ExecutionEngine/RuntimeDyld/Targets/RuntimeDyldCOFFAArch64.h
index a1151b81d141..66c9753a72fd 100644
--- a/llvm/lib/ExecutionEngine/RuntimeDyld/Targets/RuntimeDyldCOFFAArch64.h
+++ b/llvm/lib/ExecutionEngine/RuntimeDyld/Targets/RuntimeDyldCOFFAArch64.h
@@ -174,7 +174,7 @@ public:
unsigned TargetSectionID = -1;
uint64_t TargetOffset = -1;
- if (TargetName.startswith(getImportSymbolPrefix())) {
+ if (TargetName.starts_with(getImportSymbolPrefix())) {
TargetSectionID = SectionID;
TargetOffset = getDLLImportOffset(SectionID, Stubs, TargetName);
TargetName = StringRef();
diff --git a/llvm/lib/ExecutionEngine/RuntimeDyld/Targets/RuntimeDyldCOFFI386.h b/llvm/lib/ExecutionEngine/RuntimeDyld/Targets/RuntimeDyldCOFFI386.h
index 2a54728fd0bf..0d5afc289b8c 100644
--- a/llvm/lib/ExecutionEngine/RuntimeDyld/Targets/RuntimeDyldCOFFI386.h
+++ b/llvm/lib/ExecutionEngine/RuntimeDyld/Targets/RuntimeDyldCOFFI386.h
@@ -60,7 +60,7 @@ public:
unsigned TargetSectionID = -1;
uint64_t TargetOffset = -1;
- if (TargetName.startswith(getImportSymbolPrefix())) {
+ if (TargetName.starts_with(getImportSymbolPrefix())) {
TargetSectionID = SectionID;
TargetOffset = getDLLImportOffset(SectionID, Stubs, TargetName, true);
TargetName = StringRef();
diff --git a/llvm/lib/ExecutionEngine/RuntimeDyld/Targets/RuntimeDyldCOFFThumb.h b/llvm/lib/ExecutionEngine/RuntimeDyld/Targets/RuntimeDyldCOFFThumb.h
index a3e66c6bc0ec..c079d8896c1d 100644
--- a/llvm/lib/ExecutionEngine/RuntimeDyld/Targets/RuntimeDyldCOFFThumb.h
+++ b/llvm/lib/ExecutionEngine/RuntimeDyld/Targets/RuntimeDyldCOFFThumb.h
@@ -129,7 +129,7 @@ public:
unsigned TargetSectionID = -1;
uint64_t TargetOffset = -1;
- if (TargetName.startswith(getImportSymbolPrefix())) {
+ if (TargetName.starts_with(getImportSymbolPrefix())) {
TargetSectionID = SectionID;
TargetOffset = getDLLImportOffset(SectionID, Stubs, TargetName, true);
TargetName = StringRef();
diff --git a/llvm/lib/ExecutionEngine/RuntimeDyld/Targets/RuntimeDyldCOFFX86_64.h b/llvm/lib/ExecutionEngine/RuntimeDyld/Targets/RuntimeDyldCOFFX86_64.h
index 43ce64af8685..984a8d765c84 100644
--- a/llvm/lib/ExecutionEngine/RuntimeDyld/Targets/RuntimeDyldCOFFX86_64.h
+++ b/llvm/lib/ExecutionEngine/RuntimeDyld/Targets/RuntimeDyldCOFFX86_64.h
@@ -226,7 +226,7 @@ public:
unsigned TargetSectionID = 0;
uint64_t TargetOffset = 0;
- if (TargetName.startswith(getImportSymbolPrefix())) {
+ if (TargetName.starts_with(getImportSymbolPrefix())) {
assert(IsExtern && "DLLImport not marked extern?");
TargetSectionID = SectionID;
TargetOffset = getDLLImportOffset(SectionID, Stubs, TargetName);