0

我正在尝试使用 qt c++ 代码中的 android AccountManager。要添加一个帐户,我想创建一个实例android.accounts.Account,我正在尝试使用以下代码执行此操作:

jstring jUsername = QAndroidJniObject::fromString(username).object<jstring>();
jstring jPassword = QAndroidJniObject::fromString(password).object<jstring>();
jstring jType = QAndroidJniObject::fromString(type).object<jstring>();
qDebug()<<"Creating";
QAndroidJniObject accountObject("android.accounts.Account","(Ljava/lang/String;Ljava/lang/String;)V",jUsername,jType);
qDebug()<<"Inserting";

代码在accountObject创建的行出现段错误(打印“Creating”,而不是“Inserting”):

JNI ERROR (app bug): accessed deleted global reference 0x100e46
JNI ERROR (app bug): accessed deleted global reference 0xe46

我读到这种情况,如果我调用一个签名错误的方法,但签名是正确的(见这里)。

4

1 回答 1

2

从外观上看,您创建字符串的方式导致了您的问题。

jstring jUsername = QAndroidJniObject::fromString(username).object<jstring>();

它的作用是创建一个匿名临时文件QAndroidJniObject(由 返回fromString),然后您从中提取包装jobject(并将其转换为 a jstring)。当该语句的执行完成时,它的生命周期QAndroidJniObject已经结束,并且它对被包装的引用jobject将被释放。

您可以将代码更改为以下内容:

auto qjUsername = QAndroidJniObject::fromString(username);
auto jUsername = qjUsername.object<jstring>();

或者:

jstring jUsername = env->NewLocalRef(QAndroidJniObject::fromString(username).object<jstring>());

假设你有办法获得JNIEnv*. 如果您创建一个新参考,您可能也应该DeleteLocalRef在不再需要它时将其删除。

于 2016-01-10T19:02:46.340 回答