您的位置:首页 > 运维架构 > Linux

〖Linux〗Android NDK调用已编译好的C/C++动态连接库(so文件)

2014-01-10 03:20 579 查看
一、背景:假定已有应用程序zigbeeclient.cpp,内容如下:

...
extern "C" {
int getresult(int argc, char **argv);
}

int getresult(int argc, char **argv)
{
...
}


  这个文件生成一个动态链接库libzigbee.so

$(CXX) $(CXXFLAGS) $(MYCLIENTCFLAGS) $(LDFALGS) $(INCLUDE) -fPIC -llog -shared $^ -o libzigbee.so


二、期望:能在Android任意一个的NDK应用程序中,可调用此库中的getresult()函数

  1. 编写NDK的C语言文件zigbeeclient.c,内容如下:

#include <string.h>
#include <stdio.h>
#include <stdlib.h>
#include <jni.h>

/*-----------------------------------------------------------------------------
*  从libzigbee.so中调用进来的函数
*-----------------------------------------------------------------------------*/
int getresult(int argc, char **argv);

/*-----------------------------------------------------------------------------
*  String to char*
*-----------------------------------------------------------------------------*/
char* jstring_to_pchar(JNIEnv* env, jstring str)
{
char* pstr = NULL;
jclass clsstring = (*env)->FindClass(env, "java/lang/String");
jstring strencode = (*env)->NewStringUTF(env, "utf-8");
jmethodID mid = (*env)->GetMethodID(env, clsstring, "getBytes",
"(Ljava/lang/String;)[B");
jbyteArray byteArray = (jbyteArray)(
(*env)->CallObjectMethod(env, str, mid, strencode));
jsize size = (*env)->GetArrayLength(env, byteArray);
jbyte* pbyte = (*env)->GetByteArrayElements(env, byteArray, JNI_FALSE);
if (size > 0)
{
pstr = (char*) malloc(size);
memcpy(pstr, pbyte, size);
}
return pstr;
}

jstring
Java_com_scue_zigbeeclient_ZigbeeActivity_getResultJni( JNIEnv* env, jobject thiz ,
jstring subdev, jstring ctrltype, jstring mod, jstring server)
{
int ret=0;
int argc = 4;
char *argv[4];
argv[0]=jstring_to_pchar(env, subdev);
argv[1]=jstring_to_pchar(env, ctrltype);
argv[2]=jstring_to_pchar(env, mod);
argv[3]=jstring_to_pchar(env, server);
ret = getresult(argc, argv);
char cret[10]="";
sprintf(cret, "%d", ret);
return (*env)->NewStringUTF(env, cret);
}


  2. 编写Android.mk文件:

# Copyright (C) 2009 The Android Open Source Project
#
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
# You may obtain a copy of the License at
#
#      http://www.apache.org/licenses/LICENSE-2.0 #
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS,
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
# See the License for the specific language governing permissions and
# limitations under the License.
#
LOCAL_PATH := $(call my-dir)

include $(CLEAR_VARS)
LOCAL_MODULE := zigbee-prebult
LOCAL_SRC_FILES := libs/libzigbee.so
include $(PREBUILT_SHARED_LIBRARY)

include $(CLEAR_VARS)
LOCAL_MODULE    := hello-jni
LOCAL_SRC_FILES := hello-jni.c
LOCAL_SHARED_LIBRARIES := zigbee-prebult
include $(BUILD_SHARED_LIBRARY)


  3. 在Java程序文件中,load动态库的顺序有讲究(后一个依赖于前一个):

public native String  getResultJni(String subdev, String ctrltype, String mod, String server);
static {
System.loadLibrary("zigbee");
System.loadLibrary("zigbeeclient");
}


  4. 其他的细节可以下载我打包好的tar文件:Android_NDK_Extra_So.tgz
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: