Build #12's instrumented pthread_shim gave us the definitive diagnosis: WZP_pthread_shim: dlsym(RTLD_DEFAULT, pthread_create) returned NULL: libdl.a is a stub --- use libdl.so instead Tauri-cli invokes `aarch64-linux-android24-clang` as the linker and the API-24 NDK sysroot ships *stub* libdl.a / libc.a: they compile fine but every symbol crashes if called, because they're meant to coexist with a separate dynamic .so that the dynamic linker provides at runtime. Rust's pre-built libstd.rlib has static calls into those stubs baked in, so no matter what we do at link time the broken code lands in the .so. Env-var overrides of CARGO_TARGET_AARCH64_LINUX_ANDROID_LINKER don't stick — tauri-cli resets them before invoking cargo. So instead of fighting the env, we put a wrapper on $PATH, literally named `aarch64-linux-android24-clang`, that exec()s the android26 version. When tauri-cli looks up android24-clang via PATH, it gets our wrapper, our wrapper runs android26-clang, and suddenly the whole build is using the API-26 NDK sysroot with real dynamic bindings to libc.so / libdl.so. Wrappers are installed for all four ABIs (aarch64, armv7, x86_64, i686) × both suffixes (clang, clang++) directly inside the docker bash -c preamble before any cargo invocation. Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
13 KiB
Executable File
13 KiB
Executable File