You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Android 14中在std::thread内访问网络致应用崩溃求助

问题原因与解决方案

核心原因

崩溃的直接原因是你创建的std::thread对象在JNI函数返回时被销毁,但线程仍处于**可连接(joinable)**状态。根据C++标准,当std::thread的析构函数执行时,如果线程还未调用join()或detach(),会触发std::terminate(),最终调用abort()产生SIGABRT信号(对应日志里的Fatal signal 6)。

你的JNI函数stringFromJNI执行完毕返回时,栈上的t对象会被销毁,此时它内部的子线程还在执行gethostbyname,触发了上述的终止逻辑。而你第二个测试代码没有创建额外线程,直接在当前JNI线程执行网络调用,不存在线程对象析构的问题,所以运行正常。

解决方案

有两种方式修复这个问题:

1. 等待子线程完成(join)

修改Native代码,在返回前调用t.join(),确保子线程执行完毕再销毁线程对象:

extern "C" JNIEXPORT jstring JNICALL
Java_com_example_myapplication_MainActivity_stringFromJNI(
        JNIEnv* env,
        jobject /* this */) {
    std::string hello = "Hello from C++";
    std::thread t{[&]{
        gethostbyname("www.google.com");
    }};
    t.join(); // 等待子线程执行完成
    return env->NewStringUTF(hello.c_str());
}

这种方式会阻塞当前JNI所在的Java线程,直到网络调用完成,适合不需要异步执行的场景。

2. 分离线程(detach)

如果需要子线程后台异步执行,调用t.detach()将线程与对象分离,这样线程对象销毁时不会影响后台线程的运行:

extern "C" JNIEXPORT jstring JNICALL
Java_com_example_myapplication_MainActivity_stringFromJNI(
        JNIEnv* env,
        jobject /* this */) {
    std::string hello = "Hello from C++";
    std::thread t{[&]{
        gethostbyname("www.google.com");
    }};
    t.detach(); // 分离线程,后台执行
    return env->NewStringUTF(hello.c_str());
}

注意:分离后无法再通过线程对象控制或等待该线程,需要自行管理线程内的资源,避免内存泄漏或野指针问题。

额外说明

Android 14的网络权限或线程机制不是导致本次崩溃的原因,你已经声明了INTERNET权限,且Java线程调用网络正常,问题完全源于C++线程对象的生命周期管理。

内容的提问来源于stack exchange,提问作者larry

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.13 20:34:52