2014-02-14 2 views
1

Я пытаюсь использовать JNI в Android, но продолжаю получать «UnsatisfiedLinkError - Native method not found». Я потратил несколько часов на поиск решений, но все еще испытываю проблемы. Спасибо за любую помощь.JNI UnsatisfiedLinkError - родной метод не найден

Мой код выглядит следующим образом:

Java класс:

package com.example.icam; 

public class Native { 
    static{ 
     System.loadLibrary("nativeLib"); 
    } 
    public static native int nativeFunction(); 
} 

Заголовочный файл (генерируется с использованием javah):

/* DO NOT EDIT THIS FILE - it is machine generated */ 
#include <jni.h> 
/* Header for class com_example_icam_Native */ 

#ifndef _Included_com_example_icam_Native 
#define _Included_com_example_icam_Native 
#ifdef __cplusplus 
extern "C" { 
#endif 
/* 
* Class:  com_example_icam_Native 
* Method: nativeFunction 
* Signature:()I 
*/ 
JNIEXPORT jint JNICALL Java_com_example_icam_Native_nativeFunction 
    (JNIEnv *, jclass); 

#ifdef __cplusplus 
} 
#endif 
#endif 

C++ исходный файл:

#include "com_example_icam_Native.h" 

JNIEXPORT jint JNICALL Java_com_example_icam_Native_nativeFunction(JNIEnv * env, jclass clazz){ 
    return (jint)1; 
} 

Мой Android.mk

LOCAL_PATH := $(call my-dir) 
include $(CLEAR_VARS) 

OPENCV_CAMERA_MODULES:=on 
OPENCV_INSTALL_MODULES:=on 
#OPENCV_LIB_TYPE:=SHARED 
APP_ABI := armeabi-v7a 
LOCAL_SRC_FILES := native.cpp 

include C:\OpenCV-2.4.8-android-sdk\sdk\native\jni\OpenCV.mk 
LOCAL_LDLIBS  += -llog -ldl 

LOCAL_MODULE  := nativeLib 

include $(BUILD_SHARED_LIBRARY) 

Я очень новичок в JNI, может быть, я что-то упустил?

Сообщение об ошибке:

02-14 03:44:37.501: E/AndroidRuntime(23484): java.lang.UnsatisfiedLinkError: Native method not found: com.example.icam.Native.nativeFunction:()I 
02-14 03:44:37.501: E/AndroidRuntime(23484): at com.example.icam.Native.nativeFunction(Native Method) 
02-14 03:44:37.501: E/AndroidRuntime(23484): at com.example.icam.MainActivity.onCreate(MainActivity.java:81) 
02-14 03:44:37.501: E/AndroidRuntime(23484): at android.app.Activity.performCreate(Activity.java:5231) 
02-14 03:44:37.501: E/AndroidRuntime(23484): at android.app.Instrumentation.callActivityOnCreate(Instrumentation.java:1087) 
02-14 03:44:37.501: E/AndroidRuntime(23484): at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:2159) 
02-14 03:44:37.501: E/AndroidRuntime(23484): at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:2245) 
02-14 03:44:37.501: E/AndroidRuntime(23484): at android.app.ActivityThread.access$800(ActivityThread.java:135) 
02-14 03:44:37.501: E/AndroidRuntime(23484): at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1196) 
02-14 03:44:37.501: E/AndroidRuntime(23484): at android.os.Handler.dispatchMessage(Handler.java:102) 
02-14 03:44:37.501: E/AndroidRuntime(23484): at android.os.Looper.loop(Looper.java:136) 
02-14 03:44:37.501: E/AndroidRuntime(23484): at android.app.ActivityThread.main(ActivityThread.java:5017) 
02-14 03:44:37.501: E/AndroidRuntime(23484): at java.lang.reflect.Method.invokeNative(Native Method) 
02-14 03:44:37.501: E/AndroidRuntime(23484): at java.lang.reflect.Method.invoke(Method.java:515) 
02-14 03:44:37.501: E/AndroidRuntime(23484): at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:779) 
02-14 03:44:37.501: E/AndroidRuntime(23484): at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:595) 
02-14 03:44:37.501: E/AndroidRuntime(23484): at dalvik.system.NativeStart.main(Native Method) 
+0

Теперь, когда вы изменили часть ошибки из вашего вопроса, пожалуйста, напишите все сообщение, которое вы получили за исключением. – EJP

+1

Вы должны подтвердить, что символ присутствует в вашем .so-файле, а правый .so-файл находится на вашем устройстве. Запустите 'arm-linux-androideabi-nm -D nativeLib.so' (где бинарный файл nm живет где-то в каталоге NDK« toolchains », а« nativeLib.so »- это библиотека, извлеченная из вашего устройства с помощью« adb pull ») см. таблицу символов. Также посмотрите выше исключения в выводе logcat, чтобы увидеть, что VM говорит что-нибудь интересное. – fadden

+0

Я побежал выше, и символ действительно присутствовал. Теперь код действительно работает, я не совсем уверен, что я сделал. Теперь я просто должен начать писать свой реальный код с поддержкой неона C++ :) – user3019612

ответ

3

Функция объявлена ​​в файле .c не функция, объявленная в файле .h, или в качестве нативного метода в коде Java либо. Вы изменили имя где-то вдоль линии, не синхронизируя все.

+0

Это было немного глупо со мной, но это не исправляет проблему (я обновил описание). Я решил изменить имена методов и т. Д. Объявления, чтобы увидеть, будет ли что-то работать (следовательно, опечатка). Я попытался не использовать файл заголовка (но не включил jni.h в исходный файл), но ничего не делает. – user3019612

+1

Повторите свое редактирование, у вас все еще нет одинаковых вызывающих последовательностей в файле .h и файле .c.Пожалуйста, опубликуйте все сообщение об исключении. Я не знаю, почему вы считали, что использование файла заголовка не будет хорошей идеей. Это не так. – EJP

+0

Я видел несколько примеров (например, в Android NDK, которые не использовали заголовочный файл). Я добавил сообщение об ошибке в моем исходном сообщении. Благодарю. – user3019612

0

У меня та же проблема, я установил ее, изменив

JNIEXPORT JINT JNICALL Java_com_example_icam_Native_nativeFunction (JNIEnv *, JClass);

к

JNIEXPORT JINT JNICALL Java_com_example_icam_Native_nativeFunction (JNIEnv *, jobject);

+0

Причина является общедоступной ** static ** native int nativeFunction(); – zzq

+0

Это ответ, это было не очевидно из-за неудобной фразировки. – RandomSeed

-1

Вы должны снова создать файл .so по ndk_build

Смежные вопросы