【问题标题】:JNI. different behavior between different Android OS versionsJNI。不同 Android 操作系统版本之间的不同行为
【发布时间】:2013-04-17 17:02:53
【问题描述】:

我的应用程序运行以下代码:

void BmrDeviceInfo_convertToC(JNIEnv *pEnv, jobject jBmrDeviceInfo, BmrDeviceInfo& cBmrDeviceInfo){

__android_log_print(ANDROID_LOG_INFO, "BEAMER_JNI", "g_classBmrDeviceInfo is = %s", (g_classBmrDeviceInfo == NULL) ? "NULL" : "OK"); //g_classBmrDeviceInfo is initialize on JNI_OnLoad

jfieldID fieldName = pEnv->GetFieldID(g_classBmrDeviceInfo, "m_strName", "Ljava/lang/String;"); // OK for Android 4.2 and crash for Android 3.1 or less

..................................
}

崩溃案例的 LogCat 输出:

04-17 16:28:44.118: I/BEAMER_JNI(446): g_classBmrDeviceInfo is = OK
04-17 16:28:44.118: W/dalvikvm(446): JNI WARNING: 0x4053dc70 is not a valid JNI reference
04-17 16:28:44.118: W/dalvikvm(446):              in Lcom/xxxxxxx/xxxxxx/controller/CoreController;.Init (Lcom/xxxxxxx/xxxxxx/listviews/DeviceInfo;Ljava/lang/String;)I (GetFieldID)
04-17 16:28:44.118: I/dalvikvm(446): "main" prio=5 tid=1 RUNNABLE
04-17 16:28:44.118: I/dalvikvm(446):   | group="main" sCount=0 dsCount=0 obj=0x4001f1a8 self=0xce48
04-17 16:28:44.118: I/dalvikvm(446):   | sysTid=446 nice=0 sched=0/0 cgrp=default handle=-1345006528
04-17 16:28:44.118: I/dalvikvm(446):   | schedstat=( 276745040 468907344 84 )

感谢您的帮助!

【问题讨论】:

标签: android android-ndk java-native-interface jnienv


【解决方案1】:

接受对象的 JNI 函数需要本地或全局引用。在 ICS 之前,这些是原始指针,但在 ICS 中更改为表索引系统。

您没有说用于生成问题中的输出的版本。十六进制值 0x4053dc70 看起来像一个原始指针,所以我假设这是前 ICS。查看错误信息,似乎g_classBmrDeviceInfo 无效;出错的常见方法是未能使用NewGlobalRef 将本地引用转换为全局引用。

一般来说,JNI 在 ICS 中变得更加严格,所以这在 4.x 中会成功但在 3.x 中失败是很奇怪的,除非你在玩弱全局变量。 p>

【讨论】:

  • 我不确定我自己是否在关注这个,你知道这在哪里改变了吗?
  • NM 这解释了一点...android-developers.blogspot.com/2011/11/…。所以基本上他正在使用一个 ref,当他稍后(在 ICS 之前)尝试访问它时,该对象已经被 GC 移动,因此是无效的。基本上是这样吗?
  • Dalvik GC,至少通过 Jellybean,不会移动对象。类对象永远不会被丢弃,所以这个失败看起来像是一个坏的全局或完全坏的指针。 ICS 之前的 CheckJNI 实现尝试通过在全局和本地 ref 表中搜索引用来检查对象的有效性,但有可能“伪造”这一点。 >= ICS“间接引用”方法更准确,因为它不再分发原始指针,所以允许 GC 移动对象要容易得多(这是这项工作的主要动机)。
猜你喜欢
  • 1970-01-01
  • 2012-04-05
  • 2020-01-24
  • 1970-01-01
  • 1970-01-01
  • 2017-11-29
  • 2011-12-01
  • 2012-09-08
  • 1970-01-01
相关资源
最近更新 更多