Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion README.md
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@ C library.

```toml
[dependencies]
openkal-llvm-runtime = "0.16.8"
openkal-llvm-runtime = "0.16.9"
```

> **Engine floor (mcpp 2026.9.20.1):** this version of this package pins
Expand Down
6 changes: 3 additions & 3 deletions examples/image-cxx/mcpp.toml
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
# The C++ runtime inside an ok image (target `<arch>-openkal', openkal SPEC
# clause 12): one image per architecture, run through okrun on Linux, macOS and
# Windows. `import std', an exception, a thread, a thread-local variable and the
# containers, above openkal-musl's image form.
# Windows. `import std', an exception, a thread, thread-local variables (one
# with a destructor) and the containers, above openkal-musl's image form.
[package]
name = "image-cxx"
version = "0.1.0"
Expand All @@ -10,7 +10,7 @@ version = "0.1.0"
openkal-llvm-runtime = { path = "../.." }

[build-dependencies]
openkal-tools = { version = "0.1.3", tools = ["okld", "okrun"] }
openkal-tools = { version = "0.1.4", tools = ["okld", "okrun"] }

[targets.image-cxx]
kind = "bin"
Expand Down
8 changes: 8 additions & 0 deletions examples/image-cxx/src/main.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,8 @@ void check(bool held, std::string_view what) {
if (!held) ++failures;
}
thread_local int tl = 7;
std::atomic<int> tls_dtor_ran{0};
struct TlsProbe { int v; ~TlsProbe() { tls_dtor_ran.store(v); } };
}

int main(int argc, char** argv) {
Expand All @@ -24,6 +26,12 @@ int main(int argc, char** argv) {
t.join();
check(seen == 7 && tl == 7, "a thread has its own thread-local variable");

// A thread_local with a destructor needs `__cxa_thread_atexit`, which the
// image's runtime provides; the image would not link without it.
std::thread d([] { thread_local TlsProbe p{7}; (void)p; });
d.join();
check(tls_dtor_ran.load() == 7, "a thread_local's destructor runs when its thread ends");

std::map<std::string, int> m{{"a", 1}, {"b", 2}};
std::vector<int> v(100);
std::iota(v.begin(), v.end(), 1);
Expand Down
16 changes: 12 additions & 4 deletions llvm/libcxxabi/src/cxa_thread_atexit.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -179,14 +179,19 @@ namespace {
//
// THE FALLBACK BELOW WAS ALREADY COMPLETE; only the export was missing. What
// was NOT complete is where it kept its list --- see `run_dtors` above.
//
// THE OK IMAGE IS THE FOURTH SUCH TARGET. Its triple names no operating system,
// so the guard reads `OPENKAL_TARGET_IMAGE`, which `mcpp.toml` states for
// `cfg(os = "openkal")` as it states `OPENKAL_TARGET_WINDOWS` for PE.
#if defined(__linux__) || defined(__Fuchsia__) \
|| defined(OPENKAL_TARGET_WINDOWS) || defined(__APPLE__)
|| defined(OPENKAL_TARGET_WINDOWS) || defined(OPENKAL_TARGET_IMAGE) \
|| defined(__APPLE__)
extern "C" {

_LIBCXXABI_FUNC_VIS int __cxa_thread_atexit(Dtor dtor, void* obj, void* dso_symbol) throw() {
#ifdef HAVE___CXA_THREAD_ATEXIT_IMPL
return __cxa_thread_atexit_impl(dtor, obj, dso_symbol);
#elif defined(__APPLE__)
#elif defined(__APPLE__) || defined(OPENKAL_TARGET_IMAGE)
// NO WEAK PROBE ON MACH-O, AND THE REASON IS THE OBJECT FORMAT.
//
// The `else` branch below declares `__cxa_thread_atexit_impl` weak and
Expand All @@ -198,7 +203,10 @@ extern "C" {
// ld64.lld: error: undefined symbol: __cxa_thread_atexit_impl
//
// The test is also pointless here: what would define that symbol is
// libSystem, and libSystem is what this stack replaces.
// libSystem, and libSystem is what this stack replaces. An ok image takes
// the same branch: nothing beneath it defines the symbol either, and an
// image may import nothing but `kal_*`, which an unresolved weak reference
// would put in question.
(void)dso_symbol;
return register_dtor(dtor, obj);
#else
Expand Down Expand Up @@ -229,5 +237,5 @@ extern "C" {
#endif

} // extern "C"
#endif // defined(__linux__) || defined(__Fuchsia__)
#endif // the targets that export __cxa_thread_atexit
} // namespace __cxxabiv1
16 changes: 14 additions & 2 deletions mcpp.toml
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
[package]
namespace = "mcpplibs"
name = "openkal-llvm-runtime"
version = "0.16.8"
version = "0.16.9"
description = "LLVM's C++ runtime libraries — libc++, libc++abi and libunwind — configured for openkal-musl rather than for a host C library."
license = "Apache-2.0"
authors = ["mcpplibs"]
Expand Down Expand Up @@ -220,7 +220,7 @@ cflags = ["-DDISABLE_AARCH64_FMV=1"]
# runtime itself (`mcpp:compiler-runtime=compiler-rt' above), and on an ok image
# (`<arch>-openkal') that feature would bring a second supplier of the same layer
# --- which a build refuses rather than picks between.
openkal-musl = { version = "0.22.8", default-features = false, features = ["posix"] }
openkal-musl = { version = "0.22.9", default-features = false, features = ["posix"] }

[build]

Expand Down Expand Up @@ -523,6 +523,18 @@ sources = [
"!llvm/compiler-rt/lib/builtins/*xc3.c",
]

[target.'cfg(os = "openkal")'.build]
# WHICH TARGET THIS IS, FOR THE ONE FILE THAT MUST KNOW IT IS AN OK IMAGE.
#
# An ok image's triple is `<arch>-unknown-none-elf`: no `__linux__`, no
# `__APPLE__`, nothing a source can read the target off. `cxa_thread_atexit.cpp`
# exports `__cxa_thread_atexit` on the targets where no other runtime does, and
# without this define the ok image was not one of them: every image holding a
# `thread_local` with a destructor was refused by `okld check` for the undefined
# symbol (measured building clangd as an ok image, 2026-10-29).
cflags = ["-DOPENKAL_TARGET_IMAGE=1"]
cxxflags = ["-DOPENKAL_TARGET_IMAGE=1"]

[target.'cfg(windows)'.build]
# WHICH TARGET THIS IS, STATED HERE RATHER THAN READ OFF `_WIN32`.
#
Expand Down
Loading