从本机c代码(JNI)传递java中回调函数的多个参数

时间:2017-11-28 10:14:52

标签: java android c++ c java-native-interface

下面的代码在本地c代码中调用java中的回调函数,将一些字符串数据作为参数传递。

原生C层

{
    "Version": "2012-10-17",
    "Statement": [
        {
            "Effect": "Allow",
            "Action": [
                "dynamodb:BatchGetItem",
                "dynamodb:BatchWriteItem",
                "dynamodb:DeleteItem",
                "dynamodb:GetItem",
                "dynamodb:PutItem",
                "dynamodb:Query",
                "dynamodb:UpdateItem"
            ],
            "Resource": [
                "arn:aws:dynamodb:us-east-1:018671674304:table/auflyer-mobilehub-1884545339-Cusonmers",
                "arn:aws:dynamodb:us-east-1:018671674304:table/auflyer-mobilehub-1884545339-Cusonmers/index/searchByLastName",
                "arn:aws:dynamodb:us-east-1:018671674304:table/auflyer-mobilehub-1884545339-Cusonmers/index/searchByFirstName",
                "arn:aws:dynamodb:us-east-1:018671674304:table/auflyer-mobilehub-1884545339-Cusonmers/index/userId-fullName",
                "arn:aws:dynamodb:us-east-1:018671674304:table/auflyer-mobilehub-1884545339-Cusonmers/index/*"
            ],
            "Condition": {
                "ForAllValues:StringEquals": {
                    "dynamodb:LeadingKeys": [
                        "${cognito-identity.amazonaws.com:sub}",
                        "${accounts.google.com:sub}"
                    ]
                }
            }
        },
        {
            "Effect": "Allow",
            "Action": [
                "dynamodb:BatchGetItem",
                "dynamodb:BatchWriteItem",
                "dynamodb:DeleteItem",
                "dynamodb:GetItem",
                "dynamodb:PutItem",
                "dynamodb:Query",
                "dynamodb:UpdateItem"
            ],
            "Resource": [
                "arn:aws:dynamodb:us-east-1:018671674304:table/auflyer-mobilehub-1884545339-Cusonmers",
                "arn:aws:dynamodb:us-east-1:018671674304:table/auflyer-mobilehub-1884545339-Cusonmers/index/searchByLastName",
                "arn:aws:dynamodb:us-east-1:018671674304:table/auflyer-mobilehub-1884545339-Cusonmers/index/searchByFirstName",
                "arn:aws:dynamodb:us-east-1:018671674304:table/auflyer-mobilehub-1884545339-Cusonmers/index/userId-fullName",
                "arn:aws:dynamodb:us-east-1:018671674304:table/auflyer-mobilehub-1884545339-Cusonmers/index/*"
            ],
            "Condition": {
                "ForAllValues:StringEquals": {
                    "dynamodb:LeadingKeys": [
                        "${cognito-identity.amazonaws.com:sub}",
                        "${accounts.google.com:sub}"
                    ]
                }
            }
        }
    ]
}

Android / Java(回调处理程序)

jmethodID statusId = env->GetMethodID(pctx->jniHelperClz, "CallbackHandler", "(Ljava/lang/String;)V");
jstring string_data = env->NewStringUTF((const char*)"SOME_STRING_DATA");
env->CallVoidMethod(pctx->jniHelperObj, statusId, string_data);
env->DeleteLocalRef(string_data);

除了字符串,我还想传递一个int类型的数据。我的java Callback处理程序如下所示。我应该在我的原生图层中更改哪些内容以支持两个参数。

@Keep
private void CallbackHandler(String string_data) {
    // Some Code
}

1 个答案:

答案 0 :(得分:0)

您需要将方法签名从(Ljava/lang/String;)V更改为(Ljava/lang/String;I)V

jmethodID statusId = env->GetMethodID(pctx->jniHelperClz, “CallbackHandler”, "(Ljava/lang/String;I)V”);

此外,您使用DeleteLocalRef()的方式不正确。此方法用于删除通过NewLocalRef()创建的本地引用,但NewStringUTF()不创建它们。方法NewStringUTF()在垃圾收集器控制下的java堆中创建jstring对象。您无需手动删除它。

注意:

  

本地引用在本机方法调用期间有效。在本机方法返回后,它们自动释放。每个本地引用都会花费一定量的Java虚拟机资源。程序员需要确保本机方法不会过度分配本地引用。尽管在本机方法返回到Java之后会自动释放本地引用,但过度分配本地引用可能会导致VM在执行本机方法期间耗尽内存。

您需要使用DeleteLocalRef()立即删除大对象(例如循环中)。