[llvm] Revisit advanced LLJIT examples and tests (PR #76236)
Stefan Gränitz via llvm-commits
llvm-commits at lists.llvm.org
Fri Dec 22 05:42:37 PST 2023
https://github.com/weliveindetail created https://github.com/llvm/llvm-project/pull/76236
Some maintenance on implementation and tests
>From 8820c5f22b1b9561888552a26e576899773124aa Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Stefan=20Gr=C3=A4nitz?= <stefan.graenitz at gmail.com>
Date: Fri, 22 Dec 2023 11:43:18 +0100
Subject: [PATCH 1/2] [Orc][examples] Drop manual TargetMachineBuilder setup
(NFC)
---
.../LLJITWithRemoteDebugging.cpp | 15 ---------------
1 file changed, 15 deletions(-)
diff --git a/llvm/examples/OrcV2Examples/LLJITWithRemoteDebugging/LLJITWithRemoteDebugging.cpp b/llvm/examples/OrcV2Examples/LLJITWithRemoteDebugging/LLJITWithRemoteDebugging.cpp
index 9001125060583f..3d626e0ed9ab77 100644
--- a/llvm/examples/OrcV2Examples/LLJITWithRemoteDebugging/LLJITWithRemoteDebugging.cpp
+++ b/llvm/examples/OrcV2Examples/LLJITWithRemoteDebugging/LLJITWithRemoteDebugging.cpp
@@ -174,25 +174,10 @@ int main(int argc, char *argv[]) {
TSMs.push_back(ExitOnErr(parseExampleModuleFromFile(Path)));
}
- std::string TT;
- StringRef MainModuleName;
- TSMs.front().withModuleDo([&MainModuleName, &TT](Module &M) {
- MainModuleName = M.getName();
- TT = M.getTargetTriple();
- if (TT.empty())
- TT = sys::getProcessTriple();
- });
-
- // Create a target machine that matches the input triple.
- JITTargetMachineBuilder JTMB((Triple(TT)));
- JTMB.setCodeModel(CodeModel::Small);
- JTMB.setRelocationModel(Reloc::PIC_);
-
// Create LLJIT and destroy it before disconnecting the target process.
outs() << "Initializing LLJIT for remote executor\n";
auto J = ExitOnErr(LLJITBuilder()
.setExecutorProcessControl(std::move(EPC))
- .setJITTargetMachineBuilder(std::move(JTMB))
.setObjectLinkingLayerCreator([&](auto &ES, const auto &TT) {
return std::make_unique<ObjectLinkingLayer>(ES);
})
>From 42cb9bc52d039768ca56dd75a6696d27acecd34b Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Stefan=20Gr=C3=A4nitz?= <stefan.graenitz at gmail.com>
Date: Fri, 22 Dec 2023 14:36:02 +0100
Subject: [PATCH 2/2] [Orc][examples] Check that debug support plugins append
jit_code_entry
---
.../RemoteJITUtils.cpp | 9 ++-
.../lljit-with-remote-debugging.test | 12 +++-
.../llvm-jitlink-executor.cpp | 55 ++++++++++++++++++-
3 files changed, 70 insertions(+), 6 deletions(-)
diff --git a/llvm/examples/OrcV2Examples/LLJITWithRemoteDebugging/RemoteJITUtils.cpp b/llvm/examples/OrcV2Examples/LLJITWithRemoteDebugging/RemoteJITUtils.cpp
index 49f5fcdbef8dfe..47abba2c8fc335 100644
--- a/llvm/examples/OrcV2Examples/LLJITWithRemoteDebugging/RemoteJITUtils.cpp
+++ b/llvm/examples/OrcV2Examples/LLJITWithRemoteDebugging/RemoteJITUtils.cpp
@@ -111,11 +111,15 @@ launchLocalExecutor(StringRef ExecutablePath) {
close(FromExecutor[ReadEnd]);
// Execute the child process.
- std::unique_ptr<char[]> ExecPath, FDSpecifier;
+ std::unique_ptr<char[]> ExecPath, FDSpecifier, TestOutputFlag;
{
ExecPath = std::make_unique<char[]>(ExecutablePath.size() + 1);
strcpy(ExecPath.get(), ExecutablePath.data());
+ const char *TestOutputFlagStr = "test-jitloadergdb";
+ TestOutputFlag = std::make_unique<char[]>(strlen(TestOutputFlagStr) + 1);
+ strcpy(TestOutputFlag.get(), TestOutputFlagStr);
+
std::string FDSpecifierStr("filedescs=");
FDSpecifierStr += utostr(ToExecutor[ReadEnd]);
FDSpecifierStr += ',';
@@ -124,7 +128,8 @@ launchLocalExecutor(StringRef ExecutablePath) {
strcpy(FDSpecifier.get(), FDSpecifierStr.c_str());
}
- char *const Args[] = {ExecPath.get(), FDSpecifier.get(), nullptr};
+ char *const Args[] = {ExecPath.get(), TestOutputFlag.get(),
+ FDSpecifier.get(), nullptr};
int RC = execvp(ExecPath.get(), Args);
if (RC != 0)
return make_error<StringError>(
diff --git a/llvm/test/Examples/OrcV2Examples/lljit-with-remote-debugging.test b/llvm/test/Examples/OrcV2Examples/lljit-with-remote-debugging.test
index b0b33503a1eece..9f20dbac58408f 100644
--- a/llvm/test/Examples/OrcV2Examples/lljit-with-remote-debugging.test
+++ b/llvm/test/Examples/OrcV2Examples/lljit-with-remote-debugging.test
@@ -1,15 +1,21 @@
-# This test makes sure that the example builds and executes as expected.
+# Check that the debug support plugin appends a jit_code_entry to the
+# jit_descriptor of the child process.
+
# Instructions for debugging can be found in LLJITWithRemoteDebugging.cpp
# REQUIRES: default_triple
# UNSUPPORTED: target=powerpc64{{.*}}
-# RUN: LLJITWithRemoteDebugging %p/Inputs/argc_sub1_elf.ll | FileCheck --check-prefix=CHECK0 %s
+# RUN: LLJITWithRemoteDebugging %p/Inputs/argc_sub1_elf.ll 2>&1 | FileCheck --check-prefix=CHECK0 %s
+# CHECK0: __jit_debug_descriptor.last_entry = [[BEFORE0:0x[0-9a-f]+]]
# CHECK0: Parsing input IR code from: {{.*}}/Inputs/argc_sub1_elf.ll
# CHECK0: Running: main()
# CHECK0: Exit code: 0
+# CHECK0-NOT: __jit_debug_descriptor.last_entry = [[BEFORE0]]
-# RUN: LLJITWithRemoteDebugging %p/Inputs/argc_sub1_elf.ll --args 2nd 3rd 4th | FileCheck --check-prefix=CHECK3 %s
+# RUN: LLJITWithRemoteDebugging %p/Inputs/argc_sub1_elf.ll --args 2nd 3rd 4th 2>&1 | FileCheck --check-prefix=CHECK3 %s
+# CHECK3: __jit_debug_descriptor.last_entry = [[BEFORE3:0x[0-9a-f]+]]
# CHECK3: Parsing input IR code from: {{.*}}/Inputs/argc_sub1_elf.ll
# CHECK3: Running: main("2nd", "3rd", "4th")
# CHECK3: Exit code: 3
+# CHECK3-NOT: __jit_debug_descriptor.last_entry = ![[BEFORE3]]
diff --git a/llvm/tools/llvm-jitlink/llvm-jitlink-executor/llvm-jitlink-executor.cpp b/llvm/tools/llvm-jitlink/llvm-jitlink-executor/llvm-jitlink-executor.cpp
index 71c83f2badb8ff..3a05c9b5be24dc 100644
--- a/llvm/tools/llvm-jitlink/llvm-jitlink-executor/llvm-jitlink-executor.cpp
+++ b/llvm/tools/llvm-jitlink/llvm-jitlink-executor/llvm-jitlink-executor.cpp
@@ -112,6 +112,44 @@ int openListener(std::string Host, std::string PortStr) {
#endif // LLVM_ON_UNIX
}
+// This must be kept in sync with gdb/gdb/jit.h .
+extern "C" {
+
+typedef enum {
+ JIT_NOACTION = 0,
+ JIT_REGISTER_FN,
+ JIT_UNREGISTER_FN
+} jit_actions_t;
+
+struct jit_code_entry {
+ struct jit_code_entry *next_entry;
+ struct jit_code_entry *prev_entry;
+ const char *symfile_addr;
+ uint64_t symfile_size;
+};
+
+struct jit_descriptor {
+ uint32_t version;
+ // This should be jit_actions_t, but we want to be specific about the
+ // bit-width.
+ uint32_t action_flag;
+ struct jit_code_entry *relevant_entry;
+ struct jit_code_entry *first_entry;
+};
+
+// We put information about the JITed function in this global, which the
+// debugger reads. Make sure to specify the version statically, because the
+// debugger checks the version before we can set it during runtime.
+extern struct jit_descriptor __jit_debug_descriptor;
+
+static void *findLastDebugDescriptorEntryPtr() {
+ struct jit_code_entry *Last = __jit_debug_descriptor.first_entry;
+ while (Last && Last->next_entry)
+ Last = Last->next_entry;
+ return Last;
+}
+}
+
int main(int argc, char *argv[]) {
#if LLVM_ENABLE_THREADS
@@ -121,10 +159,11 @@ int main(int argc, char *argv[]) {
int InFD = 0;
int OutFD = 0;
+ std::vector<StringRef> TestOutputFlags;
+
if (argc < 2)
printErrorAndExit("insufficient arguments");
else {
-
StringRef ConnectArg = argv[FirstProgramArg++];
#ifndef NDEBUG
if (ConnectArg == "debug") {
@@ -133,6 +172,11 @@ int main(int argc, char *argv[]) {
}
#endif
+ while (ConnectArg.starts_with("test-")) {
+ TestOutputFlags.push_back(ConnectArg);
+ ConnectArg = argv[FirstProgramArg++];
+ }
+
StringRef SpecifierType, Specifier;
std::tie(SpecifierType, Specifier) = ConnectArg.split('=');
if (SpecifierType == "filedescs") {
@@ -156,6 +200,10 @@ int main(int argc, char *argv[]) {
printErrorAndExit("invalid specifier type \"" + SpecifierType + "\"");
}
+ if (llvm::is_contained(TestOutputFlags, "test-jitloadergdb"))
+ fprintf(stderr, "__jit_debug_descriptor.last_entry = 0x%016" PRIx64 "\n",
+ pointerToJITTargetAddress(findLastDebugDescriptorEntryPtr()));
+
auto Server =
ExitOnErr(SimpleRemoteEPCServer::Create<FDSimpleRemoteEPCTransport>(
[](SimpleRemoteEPCServer::Setup &S) -> Error {
@@ -173,6 +221,11 @@ int main(int argc, char *argv[]) {
InFD, OutFD));
ExitOnErr(Server->waitForDisconnect());
+
+ if (llvm::is_contained(TestOutputFlags, "test-jitloadergdb"))
+ fprintf(stderr, "__jit_debug_descriptor.last_entry = 0x%016" PRIx64 "\n",
+ pointerToJITTargetAddress(findLastDebugDescriptorEntryPtr()));
+
return 0;
#else
More information about the llvm-commits
mailing list