[llvm] [orc-rt] Reorganize regression tests, add JIT'd code support (PR #226356)

Lang Hames via llvm-commits llvm-commits at lists.llvm.org
Thu Sep 24 21:48:20 PDT 2026


https://github.com/lhames created https://github.com/llvm/llvm-project/pull/226356

Reorganize orc-rt/test/regression so that tests are placed by the question they ask, rather than by the kind of input they use:

  jit-free-foundations/  Tests of runtime facilities that can be
                         exercised without JIT'd code: ogre's command
                         line, process info, logging, and (in future)
                         connection lifecycle.
  languages/<language>/  Tests that source-language constructs behave
                         correctly when JIT'd under the ORC runtime.
  object-formats/<format>/<arch>/
                         Tests that object format features (e.g.
                         relocations, sections, and directives) are
                         handled correctly, written in assembly.

A README.md describes where tests should go, and the conventions for writing them. Existing tests move into jit-free-foundations/, and init.test is renamed to ogre-help.test to describe what it tests. The darwin/ and linux/ directories are removed: they contained no tests, and gated on the host rather than the runtime's target. Tests should gate on features instead.

Add lit support for compiling and running JIT'd code:

  %{jit}   Runs its inputs under ogre, with llvm-jitlink as the
           controller.
  %{ogre}  The path to ogre.
  %{cc}    Compiles C for the runtime's target.
  %{cxx}   Compiles C++ for the runtime's target.
  %{mc}    Assembles its input for the runtime's target, using
           llvm-mc.

%{cc} and %{cxx} default to clang and clang++ from the LLVM tools directory, and can be overridden with --param orc-rt-cc=<cc> and --param orc-rt-cxx=<cxx> to test the runtime against output from other compilers. %{mc} can't be overridden, so that object format tests always check the runtime against the same assembler.

Tests that use these substitutions are gated on the llvm-jitlink, llvm-mc, orc-rt-cc, and orc-rt-cxx features, so they are reported as unsupported (rather than failing) when the tools aren't available. clang, llvm-jitlink, and llvm-mc are added to the test dependencies if they're being built alongside the runtime. Object format tests are also gated on new target-arch=<arch> and target-object-format=<format> features, derived from the runtime's target triple.

jit-free-foundations/ removes the %{cc}, %{cxx}, %{mc}, and %{jit} substitutions, so that tests there can't accidentally depend on JIT'd code.

Add languages/c/return-zero.c and object-formats/mach-o/arm64/ return-zero.s as the first tests that run JIT'd code, establishing the pattern for each kind of test. They use llvm-jitlink's -show-jit-result option to check that the JIT'd main actually ran and returned zero.

>From f43e90be0d594d95f9fbc2184d94caf31510f42d Mon Sep 17 00:00:00 2001
From: Lang Hames <lhames at gmail.com>
Date: Fri, 25 Sep 2026 13:01:40 +1000
Subject: [PATCH] [orc-rt] Reorganize regression tests, add JIT'd code support

Reorganize orc-rt/test/regression so that tests are placed by the
question they ask, rather than by the kind of input they use:

  jit-free-foundations/  Tests of runtime facilities that can be
                         exercised without JIT'd code: ogre's command
                         line, process info, logging, and (in future)
                         connection lifecycle.
  languages/<language>/  Tests that source-language constructs behave
                         correctly when JIT'd under the ORC runtime.
  object-formats/<format>/<arch>/
                         Tests that object format features (e.g.
                         relocations, sections, and directives) are
                         handled correctly, written in assembly.

A README.md describes where tests should go, and the conventions for
writing them. Existing tests move into jit-free-foundations/, and
init.test is renamed to ogre-help.test to describe what it tests. The
darwin/ and linux/ directories are removed: they contained no tests,
and gated on the host rather than the runtime's target. Tests should
gate on features instead.

Add lit support for compiling and running JIT'd code:

  %{jit}   Runs its inputs under ogre, with llvm-jitlink as the
           controller.
  %{ogre}  The path to ogre.
  %{cc}    Compiles C for the runtime's target.
  %{cxx}   Compiles C++ for the runtime's target.
  %{mc}    Assembles its input for the runtime's target, using
           llvm-mc.

%{cc} and %{cxx} default to clang and clang++ from the LLVM tools
directory, and can be overridden with --param orc-rt-cc=<cc> and
--param orc-rt-cxx=<cxx> to test the runtime against output from other
compilers. %{mc} can't be overridden, so that object format tests
always check the runtime against the same assembler.

Tests that use these substitutions are gated on the llvm-jitlink,
llvm-mc, orc-rt-cc, and orc-rt-cxx features, so they are reported as
unsupported (rather than failing) when the tools aren't available.
clang, llvm-jitlink, and llvm-mc are added to the test dependencies if
they're being built alongside the runtime. Object format tests are
also gated on new target-arch=<arch> and target-object-format=<format>
features, derived from the runtime's target triple.

jit-free-foundations/ removes the %{cc}, %{cxx}, %{mc}, and %{jit}
substitutions, so that tests there can't accidentally depend on JIT'd
code.

Add languages/c/return-zero.c and object-formats/mach-o/arm64/
return-zero.s as the first tests that run JIT'd code, establishing the
pattern for each kind of test. They use llvm-jitlink's
-show-jit-result option to check that the JIT'd main actually ran and
returned zero.
---
 orc-rt/cmake/OrcRTTesting.cmake               |   8 ++
 orc-rt/test/regression/README.md              | 119 ++++++++++++++++++
 orc-rt/test/regression/darwin/lit.local.cfg   |   2 -
 .../check-rt-process-info.test                |   0
 .../jit-free-foundations/lit.local.cfg        |  13 ++
 .../logging/lit.local.cfg                     |   0
 .../logging/os_log/delivery.test              |   0
 .../logging/os_log/lit.local.cfg              |   0
 .../logging/os_log/no-printf-output.test      |   0
 .../logging/printf-backend/bad-level.test     |   0
 .../printf-backend/debug-compiled-out.test    |   0
 .../logging/printf-backend/debug-level.test   |   0
 .../logging/printf-backend/format.test        |   0
 .../logging/printf-backend/level-off.test     |   0
 .../logging/printf-backend/lit.local.cfg      |   0
 .../printf-backend/output-redirect.test       |   0
 .../logging/printf-backend/runtime-level.test |   0
 .../ogre-help.test}                           |   0
 .../smoke-check.test                          |   0
 .../test/regression/languages/c/lit.local.cfg |   7 ++
 .../test/regression/languages/c/return-zero.c |   8 ++
 orc-rt/test/regression/linux/lit.local.cfg    |   2 -
 orc-rt/test/regression/lit.cfg.py             |  81 ++++++++++++
 .../regression/object-formats/lit.local.cfg   |  11 ++
 .../object-formats/mach-o/arm64/lit.local.cfg |   4 +
 .../object-formats/mach-o/arm64/return-zero.s |  15 +++
 .../object-formats/mach-o/lit.local.cfg       |   4 +
 27 files changed, 270 insertions(+), 4 deletions(-)
 create mode 100644 orc-rt/test/regression/README.md
 delete mode 100644 orc-rt/test/regression/darwin/lit.local.cfg
 rename orc-rt/test/regression/{ => jit-free-foundations}/check-rt-process-info.test (100%)
 create mode 100644 orc-rt/test/regression/jit-free-foundations/lit.local.cfg
 rename orc-rt/test/regression/{ => jit-free-foundations}/logging/lit.local.cfg (100%)
 rename orc-rt/test/regression/{ => jit-free-foundations}/logging/os_log/delivery.test (100%)
 rename orc-rt/test/regression/{ => jit-free-foundations}/logging/os_log/lit.local.cfg (100%)
 rename orc-rt/test/regression/{ => jit-free-foundations}/logging/os_log/no-printf-output.test (100%)
 rename orc-rt/test/regression/{ => jit-free-foundations}/logging/printf-backend/bad-level.test (100%)
 rename orc-rt/test/regression/{ => jit-free-foundations}/logging/printf-backend/debug-compiled-out.test (100%)
 rename orc-rt/test/regression/{ => jit-free-foundations}/logging/printf-backend/debug-level.test (100%)
 rename orc-rt/test/regression/{ => jit-free-foundations}/logging/printf-backend/format.test (100%)
 rename orc-rt/test/regression/{ => jit-free-foundations}/logging/printf-backend/level-off.test (100%)
 rename orc-rt/test/regression/{ => jit-free-foundations}/logging/printf-backend/lit.local.cfg (100%)
 rename orc-rt/test/regression/{ => jit-free-foundations}/logging/printf-backend/output-redirect.test (100%)
 rename orc-rt/test/regression/{ => jit-free-foundations}/logging/printf-backend/runtime-level.test (100%)
 rename orc-rt/test/regression/{init.test => jit-free-foundations/ogre-help.test} (100%)
 rename orc-rt/test/regression/{ => jit-free-foundations}/smoke-check.test (100%)
 create mode 100644 orc-rt/test/regression/languages/c/lit.local.cfg
 create mode 100644 orc-rt/test/regression/languages/c/return-zero.c
 delete mode 100644 orc-rt/test/regression/linux/lit.local.cfg
 create mode 100644 orc-rt/test/regression/object-formats/lit.local.cfg
 create mode 100644 orc-rt/test/regression/object-formats/mach-o/arm64/lit.local.cfg
 create mode 100644 orc-rt/test/regression/object-formats/mach-o/arm64/return-zero.s
 create mode 100644 orc-rt/test/regression/object-formats/mach-o/lit.local.cfg

diff --git a/orc-rt/cmake/OrcRTTesting.cmake b/orc-rt/cmake/OrcRTTesting.cmake
index b26a02eede25e6..bd1812a3f72fe0 100644
--- a/orc-rt/cmake/OrcRTTesting.cmake
+++ b/orc-rt/cmake/OrcRTTesting.cmake
@@ -34,3 +34,11 @@ if (NOT ORC_RT_NOT_EXECUTABLE)
   message(STATUS "Cannot find 'not'. Please put it in your PATH, set ORC_RT_NOT_EXECUTABLE to its full path, or point ORC_RT_LLVM_TOOLS_DIR to its directory.")
   set(ORC_RT_LLVM_TOOLS_AVAILABLE FALSE)
 endif()
+
+# Add dependencies on optional tools, if they're being built alongside us.
+# Tests that need these tools are gated on lit features, so they're not required.
+foreach(tool clang llvm-jitlink llvm-mc)
+  if (TARGET ${tool})
+    list(APPEND ORC_RT_TEST_DEPS ${tool})
+  endif()
+endforeach()
diff --git a/orc-rt/test/regression/README.md b/orc-rt/test/regression/README.md
new file mode 100644
index 00000000000000..e29cbf280b36c2
--- /dev/null
+++ b/orc-rt/test/regression/README.md
@@ -0,0 +1,119 @@
+# ORC Runtime Regression Tests
+
+End-to-end tests of the ORC runtime. Run them with `ninja check-orc-rt`. For
+tests of individual APIs, write unit tests under `test/unit` instead.
+
+## Where does my test go?
+
+Place a test by the *question it asks*, not by the kind of input file it uses:
+
+* **`jit-free-foundations/`**: Tests that don't compile, link, or run any
+  JIT'd code, e.g. tests of ogre's command line, process info, logging, and
+  connection lifecycle.
+* **`languages/<language>/`** (e.g. `languages/c/`): Tests that a
+  source-language construct behaves correctly when JIT'd.
+* **`object-formats/<format>/<arch>/`** (e.g. `object-formats/mach-o/arm64/`):
+  Tests that a specific object format feature (e.g. a relocation, section, or
+  directive) is handled correctly. These are written in assembly.
+
+The `jit-free-foundations/` rule is enforced: the `%{cc}`, `%{cxx}`, `%{mc}`,
+and `%{jit}` substitutions are unavailable there.
+
+## Writing tests that run JIT'd code
+
+A typical test:
+
+```c
+// Check that a trivial C program can be compiled and run under ogre.
+//
+// RUN: %{cc} -c -o %t.o %s
+// RUN: %{jit} -show-jit-result %t.o | FileCheck %s
+
+// CHECK: JIT result: 0
+
+int main(void) { return 0; }
+```
+
+Conventions:
+
+* **Return 0 on success, and a distinct non-zero value from each check.**
+  A failure then reports which check failed (`JIT result: 3`), not just that
+  the test failed.
+* **Check behavior, not object contents.** Language tests should keep passing
+  if the compiler changes how a construct is lowered, and only fail if the
+  new lowering doesn't work under the runtime.
+* **Write freestanding sources.** Don't include system headers; declare any
+  library functions you need yourself. This keeps tests usable when
+  cross-compiling for targets without a sysroot.
+
+### Substitutions
+
+* **`%{cc}`**: Compiles C for the runtime's target.
+* **`%{cxx}`**: Compiles C++ for the runtime's target.
+* **`%{mc}`**: Assembles its input into an object file for the runtime's
+  target, using `llvm-mc`. Unlike `%{cc}` and `%{cxx}`, this can't be
+  overridden, so object format tests always check the runtime against the
+  same assembler.
+* **`%{jit}`**: Links and runs its inputs under ogre, using `llvm-jitlink` as
+  the controller. Pass `-show-jit-result` to print `JIT result: <value>`.
+* **`%{ogre}`**: Path to the ogre executable.
+
+Don't spell out a target triple or connection method in a test unless that's
+what the test is about: the substitutions provide these, so that the same
+tests can be run with different compilers and targets. Flags that select a
+feature under test (e.g. `-mattr=`, `-mcmodel=`, `-fPIC`) are fine, but gate
+the test on the target architecture and CPU features they require.
+
+`%{cc}` and `%{cxx}` accept clang-style options, and tests must restrict
+themselves to this subset: `-c`, `-o`, `-I`, `-D`, `-O<n>`, `-g`, `-std=`,
+`-x`, `-fexceptions`, and `-fno-exceptions`. If a test needs another option,
+add it to this list, so that anyone writing a wrapper for another compiler
+knows which options to support.
+
+### Features
+
+Directories and tests gate on lit features describing the build, rather than
+the host:
+
+* **`orc-rt-cc`**: `%{cc}` is usable.
+* **`orc-rt-cxx`**: `%{cxx}` is usable.
+* **`llvm-mc`**: `%{mc}` is usable.
+* **`llvm-jitlink`**: `%{jit}` is usable.
+* **`target-arch=<arch>`**: The runtime's target architecture (`arm64` and
+  `aarch64` are aliases).
+* **`target-object-format=<coff|elf|mach-o>`**: The runtime's target object
+  format.
+* **`orc-rt-log-backend-<backend>`**, **`orc-rt-log-level-<level>`**: The
+  runtime was built with the given logging backend / level.
+
+`languages/c/` requires `orc-rt-cc` and `llvm-jitlink`, so tests there don't
+need to repeat those requirements. Likewise, `object-formats/` requires
+`llvm-mc` and `llvm-jitlink`, and each `<format>/<arch>/` subdirectory
+requires the matching `target-object-format=` and `target-arch=` features.
+
+## Running with a different compiler
+
+By default `%{cc}` and `%{cxx}` are the `clang` and `clang++` in the LLVM
+tools directory, i.e. `bin/` in the LLVM build given by `-DLLVM_BINARY_DIR`
+(or `-DORC_RT_LLVM_TOOLS_DIR`). If no clang is found, the C tests are reported
+as unsupported.
+
+To test the runtime against another compiler's output, pass:
+
+```
+llvm-lit --param orc-rt-cc=<cc> --param orc-rt-cxx=<cxx> \
+  <path-to-build>/orc-rt/test/regression
+```
+
+The compiler must accept the clang-style options above and must target the
+runtime's target without being told to. Write a wrapper script if your
+compiler needs different options. Treat results from other compilers as
+reports rather than expectations: don't add `XFAIL`s for them in-tree.
+
+## Tips
+
+To print each test's result instead of a progress bar:
+
+```
+LIT_OPTS="--no-progress-bar --print-result-after=all" ninja check-orc-rt
+```
diff --git a/orc-rt/test/regression/darwin/lit.local.cfg b/orc-rt/test/regression/darwin/lit.local.cfg
deleted file mode 100644
index 4539e9a1b9bd72..00000000000000
--- a/orc-rt/test/regression/darwin/lit.local.cfg
+++ /dev/null
@@ -1,2 +0,0 @@
-if "system-darwin" not in config.available_features:
-  config.unsupported = True
\ No newline at end of file
diff --git a/orc-rt/test/regression/check-rt-process-info.test b/orc-rt/test/regression/jit-free-foundations/check-rt-process-info.test
similarity index 100%
rename from orc-rt/test/regression/check-rt-process-info.test
rename to orc-rt/test/regression/jit-free-foundations/check-rt-process-info.test
diff --git a/orc-rt/test/regression/jit-free-foundations/lit.local.cfg b/orc-rt/test/regression/jit-free-foundations/lit.local.cfg
new file mode 100644
index 00000000000000..e7d7506a9f4fc4
--- /dev/null
+++ b/orc-rt/test/regression/jit-free-foundations/lit.local.cfg
@@ -0,0 +1,13 @@
+# Tests of ORC runtime facilities that can be exercised without JIT'd code:
+# ogre's command line, process info, logging, connection lifecycle, and the
+# test-support tools themselves.
+#
+# Tests here must not compile, link, or run JIT'd code. Tests that do belong
+# under languages/ or object-formats/ (see README.md). To enforce this, the
+# substitutions for compiling and running JIT'd code are removed here.
+
+config.substitutions = [
+    (pattern, replacement)
+    for (pattern, replacement) in config.substitutions
+    if pattern not in ("%{cc}", "%{cxx}", "%{mc}", "%{jit}")
+]
diff --git a/orc-rt/test/regression/logging/lit.local.cfg b/orc-rt/test/regression/jit-free-foundations/logging/lit.local.cfg
similarity index 100%
rename from orc-rt/test/regression/logging/lit.local.cfg
rename to orc-rt/test/regression/jit-free-foundations/logging/lit.local.cfg
diff --git a/orc-rt/test/regression/logging/os_log/delivery.test b/orc-rt/test/regression/jit-free-foundations/logging/os_log/delivery.test
similarity index 100%
rename from orc-rt/test/regression/logging/os_log/delivery.test
rename to orc-rt/test/regression/jit-free-foundations/logging/os_log/delivery.test
diff --git a/orc-rt/test/regression/logging/os_log/lit.local.cfg b/orc-rt/test/regression/jit-free-foundations/logging/os_log/lit.local.cfg
similarity index 100%
rename from orc-rt/test/regression/logging/os_log/lit.local.cfg
rename to orc-rt/test/regression/jit-free-foundations/logging/os_log/lit.local.cfg
diff --git a/orc-rt/test/regression/logging/os_log/no-printf-output.test b/orc-rt/test/regression/jit-free-foundations/logging/os_log/no-printf-output.test
similarity index 100%
rename from orc-rt/test/regression/logging/os_log/no-printf-output.test
rename to orc-rt/test/regression/jit-free-foundations/logging/os_log/no-printf-output.test
diff --git a/orc-rt/test/regression/logging/printf-backend/bad-level.test b/orc-rt/test/regression/jit-free-foundations/logging/printf-backend/bad-level.test
similarity index 100%
rename from orc-rt/test/regression/logging/printf-backend/bad-level.test
rename to orc-rt/test/regression/jit-free-foundations/logging/printf-backend/bad-level.test
diff --git a/orc-rt/test/regression/logging/printf-backend/debug-compiled-out.test b/orc-rt/test/regression/jit-free-foundations/logging/printf-backend/debug-compiled-out.test
similarity index 100%
rename from orc-rt/test/regression/logging/printf-backend/debug-compiled-out.test
rename to orc-rt/test/regression/jit-free-foundations/logging/printf-backend/debug-compiled-out.test
diff --git a/orc-rt/test/regression/logging/printf-backend/debug-level.test b/orc-rt/test/regression/jit-free-foundations/logging/printf-backend/debug-level.test
similarity index 100%
rename from orc-rt/test/regression/logging/printf-backend/debug-level.test
rename to orc-rt/test/regression/jit-free-foundations/logging/printf-backend/debug-level.test
diff --git a/orc-rt/test/regression/logging/printf-backend/format.test b/orc-rt/test/regression/jit-free-foundations/logging/printf-backend/format.test
similarity index 100%
rename from orc-rt/test/regression/logging/printf-backend/format.test
rename to orc-rt/test/regression/jit-free-foundations/logging/printf-backend/format.test
diff --git a/orc-rt/test/regression/logging/printf-backend/level-off.test b/orc-rt/test/regression/jit-free-foundations/logging/printf-backend/level-off.test
similarity index 100%
rename from orc-rt/test/regression/logging/printf-backend/level-off.test
rename to orc-rt/test/regression/jit-free-foundations/logging/printf-backend/level-off.test
diff --git a/orc-rt/test/regression/logging/printf-backend/lit.local.cfg b/orc-rt/test/regression/jit-free-foundations/logging/printf-backend/lit.local.cfg
similarity index 100%
rename from orc-rt/test/regression/logging/printf-backend/lit.local.cfg
rename to orc-rt/test/regression/jit-free-foundations/logging/printf-backend/lit.local.cfg
diff --git a/orc-rt/test/regression/logging/printf-backend/output-redirect.test b/orc-rt/test/regression/jit-free-foundations/logging/printf-backend/output-redirect.test
similarity index 100%
rename from orc-rt/test/regression/logging/printf-backend/output-redirect.test
rename to orc-rt/test/regression/jit-free-foundations/logging/printf-backend/output-redirect.test
diff --git a/orc-rt/test/regression/logging/printf-backend/runtime-level.test b/orc-rt/test/regression/jit-free-foundations/logging/printf-backend/runtime-level.test
similarity index 100%
rename from orc-rt/test/regression/logging/printf-backend/runtime-level.test
rename to orc-rt/test/regression/jit-free-foundations/logging/printf-backend/runtime-level.test
diff --git a/orc-rt/test/regression/init.test b/orc-rt/test/regression/jit-free-foundations/ogre-help.test
similarity index 100%
rename from orc-rt/test/regression/init.test
rename to orc-rt/test/regression/jit-free-foundations/ogre-help.test
diff --git a/orc-rt/test/regression/smoke-check.test b/orc-rt/test/regression/jit-free-foundations/smoke-check.test
similarity index 100%
rename from orc-rt/test/regression/smoke-check.test
rename to orc-rt/test/regression/jit-free-foundations/smoke-check.test
diff --git a/orc-rt/test/regression/languages/c/lit.local.cfg b/orc-rt/test/regression/languages/c/lit.local.cfg
new file mode 100644
index 00000000000000..f3ecd77ac1b3cd
--- /dev/null
+++ b/orc-rt/test/regression/languages/c/lit.local.cfg
@@ -0,0 +1,7 @@
+# Tests that C source constructs behave correctly when JIT'd under the ORC
+# runtime. Tests compile with %{cc} and run the result with %{jit}.
+
+config.suffixes = [".c"]
+
+if not {"orc-rt-cc", "llvm-jitlink"} <= config.available_features:
+    config.unsupported = True
diff --git a/orc-rt/test/regression/languages/c/return-zero.c b/orc-rt/test/regression/languages/c/return-zero.c
new file mode 100644
index 00000000000000..0cdd655414dc96
--- /dev/null
+++ b/orc-rt/test/regression/languages/c/return-zero.c
@@ -0,0 +1,8 @@
+// Check that a trivial C program can be compiled and run under ogre.
+//
+// RUN: %{cc} -c -o %t.o %s
+// RUN: %{jit} -show-jit-result %t.o | FileCheck %s
+
+// CHECK: JIT result: 0
+
+int main(void) { return 0; }
diff --git a/orc-rt/test/regression/linux/lit.local.cfg b/orc-rt/test/regression/linux/lit.local.cfg
deleted file mode 100644
index e85a58569fbb67..00000000000000
--- a/orc-rt/test/regression/linux/lit.local.cfg
+++ /dev/null
@@ -1,2 +0,0 @@
-if "system-linux" not in config.available_features:
-  config.unsupported = True
\ No newline at end of file
diff --git a/orc-rt/test/regression/lit.cfg.py b/orc-rt/test/regression/lit.cfg.py
index 8c010d4fe2dc87..0208382baa495d 100644
--- a/orc-rt/test/regression/lit.cfg.py
+++ b/orc-rt/test/regression/lit.cfg.py
@@ -30,6 +30,87 @@
 
 llvm_config.use_default_substitutions()
 
+# %{jit} runs JIT'd code under ogre, with llvm-jitlink as the controller. Tests
+# that use it must be gated on the llvm-jitlink feature.
+ogre = os.path.join(config.orc_rt_obj_root, "tools", "ogre", "ogre")
+config.substitutions.append(("%{ogre}", ogre))
+llvm_jitlink = llvm_config.use_llvm_tool("llvm-jitlink")
+if llvm_jitlink:
+    config.available_features.add("llvm-jitlink")
+    config.substitutions.append(
+        ("%{jit}", "{} -oop-launch={}".format(llvm_jitlink, ogre))
+    )
+
+# %{cc} and %{cxx} compile C and C++ for the runtime's target. They default to
+# clang and clang++ from the LLVM tools directory. Pass --param orc-rt-cc=<cc>
+# or --param orc-rt-cxx=<cxx> to use a different compiler: it must accept
+# clang-style options and target the runtime's target without being told to
+# (use a wrapper script if necessary). Tests that use %{cc} or %{cxx} must be
+# gated on the orc-rt-cc or orc-rt-cxx feature respectively.
+def add_compiler(name, clang_name):
+    override = lit_config.params.get(name)
+    if override:
+        compiler = lit.util.which(override)
+        if compiler is None:
+            lit_config.fatal(
+                "{} compiler '{}' not found".format(name, override)
+            )
+        lit_config.note("using {} override: {}".format(name, compiler))
+    else:
+        compiler = llvm_config.use_llvm_tool(clang_name)
+        if compiler:
+            compiler += " --target=" + config.target_triple
+    if compiler:
+        config.available_features.add(name)
+        substitution = "%{" + name[len("orc-rt-"):] + "}"
+        config.substitutions.append((substitution, compiler))
+
+add_compiler("orc-rt-cc", "clang")
+add_compiler("orc-rt-cxx", "clang++")
+
+# %{mc} assembles its input into an object file for the runtime's target.
+# Unlike %{cc}, it can't be overridden, so that object format tests always
+# check the runtime against the same assembler. Tests that use it must be
+# gated on the llvm-mc feature.
+llvm_mc = llvm_config.use_llvm_tool("llvm-mc")
+if llvm_mc:
+    config.available_features.add("llvm-mc")
+    config.substitutions.append(
+        (
+            "%{mc}",
+            "{} -triple={} -filetype=obj".format(llvm_mc, config.target_triple),
+        )
+    )
+
+# Describe the runtime's target architecture and object format, so that object
+# format tests can gate on them:
+#   target-arch=<arch>             (arm64 and aarch64 are aliases)
+#   target-object-format=<coff|elf|mach-o>
+# No object format feature is added for targets not recognized below.
+ELF_OS_NAMES = ("linux", "freebsd", "netbsd", "openbsd", "fuchsia", "none",
+                "elf")
+
+def add_target_features():
+    arch, _, rest = config.target_triple.partition("-")
+    if arch in ("arm64", "aarch64"):
+        config.available_features.update(
+            ["target-arch=arm64", "target-arch=aarch64"]
+        )
+    else:
+        config.available_features.add("target-arch=" + arch)
+    components = rest.split("-")
+    if "apple" in components:
+        object_format = "mach-o"
+    elif any(c.startswith("windows") for c in components):
+        object_format = "coff"
+    elif any(c.startswith(n) for c in components for n in ELF_OS_NAMES):
+        object_format = "elf"
+    else:
+        return
+    config.available_features.add("target-object-format=" + object_format)
+
+add_target_features()
+
 
 def run_test_tool(name, *args):
     """Run a test-support tool from test/tools and return its stdout.
diff --git a/orc-rt/test/regression/object-formats/lit.local.cfg b/orc-rt/test/regression/object-formats/lit.local.cfg
new file mode 100644
index 00000000000000..508174ed69e217
--- /dev/null
+++ b/orc-rt/test/regression/object-formats/lit.local.cfg
@@ -0,0 +1,11 @@
+# Tests that object format features (e.g. relocations, sections, and
+# directives) are handled correctly by the ORC runtime. Tests are assembled
+# with %{mc}, and the result run with %{jit}.
+#
+# Tests live in <format>/<arch>/ subdirectories, which gate on the runtime's
+# target.
+
+config.suffixes = [".s"]
+
+if not {"llvm-mc", "llvm-jitlink"} <= config.available_features:
+    config.unsupported = True
diff --git a/orc-rt/test/regression/object-formats/mach-o/arm64/lit.local.cfg b/orc-rt/test/regression/object-formats/mach-o/arm64/lit.local.cfg
new file mode 100644
index 00000000000000..391658dbd000d8
--- /dev/null
+++ b/orc-rt/test/regression/object-formats/mach-o/arm64/lit.local.cfg
@@ -0,0 +1,4 @@
+# Tests of MachO object format features on arm64.
+
+if "target-arch=arm64" not in config.available_features:
+    config.unsupported = True
diff --git a/orc-rt/test/regression/object-formats/mach-o/arm64/return-zero.s b/orc-rt/test/regression/object-formats/mach-o/arm64/return-zero.s
new file mode 100644
index 00000000000000..7373bdcc3be0da
--- /dev/null
+++ b/orc-rt/test/regression/object-formats/mach-o/arm64/return-zero.s
@@ -0,0 +1,15 @@
+// Check that a trivial MachO arm64 object can be linked and run under ogre.
+//
+// RUN: %{mc} -o %t.o %s
+// RUN: %{jit} -show-jit-result %t.o | FileCheck %s
+
+// CHECK: JIT result: 0
+
+	.section	__TEXT,__text,regular,pure_instructions
+	.globl	_main
+	.p2align	2
+_main:
+	mov	w0, #0
+	ret
+
+	.subsections_via_symbols
diff --git a/orc-rt/test/regression/object-formats/mach-o/lit.local.cfg b/orc-rt/test/regression/object-formats/mach-o/lit.local.cfg
new file mode 100644
index 00000000000000..8fa5879e2c4d7d
--- /dev/null
+++ b/orc-rt/test/regression/object-formats/mach-o/lit.local.cfg
@@ -0,0 +1,4 @@
+# Tests of MachO object format features.
+
+if "target-object-format=mach-o" not in config.available_features:
+    config.unsupported = True



More information about the llvm-commits mailing list