DetachCurrentThread 有时会在 NDK 中崩溃
DetachCurrentThread crashes sometimes in NDK
我很抱歉问了一个非常模糊的问题,但是,我有一个纯原生的 NDK 应用程序,它应该在 沉浸模式(即全屏)下执行。
通过 APP_CMD_RESUME
恢复应用程序时执行沉浸式模式 JNI 代码段。这在大多数情况下都有效,但是,我的 SetImmersiveMode()
代码段中的命令 activity->vm->DetachCurrentThread()
偶尔会崩溃并出现致命异常:
FATAL EXCEPTION: Thread-10
Process: com.toppluva.portis.LocalDebug, PID: 5474
android.view.ViewRootImpl$CalledFromWrongThreadException: Only the original thread that created a view hierarchy can touch its views.
at android.view.ViewRootImpl.checkThread(ViewRootImpl.java:7380)
at android.view.ViewRootImpl.recomputeViewAttributes(ViewRootImpl.java:3478)
at android.view.View.setSystemUiVisibility(View.java:22587)
这真的让我感到困惑,主要是因为它时不时地发生,我如何检测我是否从这个原始线程执行?
请注意,根据文档 APP_CMD_RESUME
从主线程执行。
View.setSystemUiVisibility() 只能从主线程调用。 如果没有看到您的代码,很难判断 DetachCurrentThread() 是否在其中发挥了作用。
文档,ANativeActivity::env 是应用程序主线程的 JNI 上下文。
您应该在终止附加到 JVM 的本机线程之前调用 DetachCurrentThread()
。
您不应在 Java 中生成的线程上调用 DetachCurrentThread)
,例如UI 线程。
请注意,您可以随时在任何线程上调用 AttachCurrentThread()
。它将等同于 Java 线程或附加线程上的 NOP。
这些 attach/detach 没有像括号那样配对。任何数量的附加调用都会被单个分离逆转。 recommended实践:
use pthread_key_create
to define a destructor function that will be called before the thread exits, and call DetachCurrentThread
from there. (Use that key with pthread_setspecific
to store the JNIEnv in thread-local-storage; that way it'll be passed into your destructor as the argument.)
查看 WebRTC 如何在 git Web repo.
中处理 attach/detach
我很抱歉问了一个非常模糊的问题,但是,我有一个纯原生的 NDK 应用程序,它应该在 沉浸模式(即全屏)下执行。
通过 APP_CMD_RESUME
恢复应用程序时执行沉浸式模式 JNI 代码段。这在大多数情况下都有效,但是,我的 SetImmersiveMode()
代码段中的命令 activity->vm->DetachCurrentThread()
偶尔会崩溃并出现致命异常:
FATAL EXCEPTION: Thread-10
Process: com.toppluva.portis.LocalDebug, PID: 5474
android.view.ViewRootImpl$CalledFromWrongThreadException: Only the original thread that created a view hierarchy can touch its views.
at android.view.ViewRootImpl.checkThread(ViewRootImpl.java:7380)
at android.view.ViewRootImpl.recomputeViewAttributes(ViewRootImpl.java:3478)
at android.view.View.setSystemUiVisibility(View.java:22587)
这真的让我感到困惑,主要是因为它时不时地发生,我如何检测我是否从这个原始线程执行?
请注意,根据文档 APP_CMD_RESUME
从主线程执行。
View.setSystemUiVisibility() 只能从主线程调用。 如果没有看到您的代码,很难判断 DetachCurrentThread() 是否在其中发挥了作用。
文档,ANativeActivity::env 是应用程序主线程的 JNI 上下文。
您应该在终止附加到 JVM 的本机线程之前调用 DetachCurrentThread()
。
您不应在 Java 中生成的线程上调用 DetachCurrentThread)
,例如UI 线程。
请注意,您可以随时在任何线程上调用 AttachCurrentThread()
。它将等同于 Java 线程或附加线程上的 NOP。
这些 attach/detach 没有像括号那样配对。任何数量的附加调用都会被单个分离逆转。 recommended实践:
use
pthread_key_create
to define a destructor function that will be called before the thread exits, and callDetachCurrentThread
from there. (Use that key withpthread_setspecific
to store the JNIEnv in thread-local-storage; that way it'll be passed into your destructor as the argument.)
查看 WebRTC 如何在 git Web repo.
中处理 attach/detach