我正在尝试将NDK与C ++一起使用,似乎无法使方法命名约定正确。我的原生方法如下:
extern "C" {
JNIEXPORT void JNICALL Java_com_test_jnitest_SurfaceRenderer_drawFromJni
(JNIEnv* env, jclass c)
{
//
}
}
标题包含在extern“C”{} aslo中。
一切编译得很好,创建一个.so文件并复制到我的项目下的libs文件夹中,但是当我在Eclipse中调试并运行时,我不断收到一条日志cat消息“没有找到本机的实现......”。因为所有NDK示例都在C中,我有什么遗漏吗?
感谢。
答案 0 :(得分:119)
有一些事情可能导致“没有找到实施”。一个是使函数原型名称错误,另一个是无法加载.so。您确定在使用该方法之前调用了System.loadLibrary()
吗?
如果您没有定义JNI_OnLoad
函数,您可能需要创建一个函数并让它发出日志消息,以验证是否已成功引入了库。
你已经避开了最常见的问题 - 忘记使用extern "C"
- 所以它是上面的或者是一些轻微的拼写错误。 Java声明是什么样的?
答案 1 :(得分:16)
此错误的另一个原因:未修饰的本机方法名称不得包含下划线!
例如,我想导出一个名为AudioCapture_Ping()
的C函数。这是我在C中的出口声明:
JNI_EXPORT int Java_com_obsidian_mobilehashhost_MainActivity_AudioCapture_Ping(JNIEnv *pJniEnv, jobject object); //Notice the underscore before Ping
这是我的Java类导入函数:
package com.obsidian.mobileaudiohashhost;
...
public class MainActivity extends Activity {
private native int AudioCapture_Ping(); // FAILS
...
在删除下划线之前,我无法让Android动态链接到我的原生方法:
JNI_EXPORT int Java_com_obsidian_mobilehashhost_MainActivity_AudioCapturePing(JNIEnv *pJniEnv, jobject object);
package com.obsidian.mobileaudiohashhost;
...
public class MainActivity extends Activity {
private native int AudioCapturePing(); // THIS WORKS!
...
答案 2 :(得分:13)
我遇到了同样的问题,但对我来说,错误发生在Android.mk文件中。我有它:
LOCAL_SRC_FILES := A.cpp
LOCAL_SRC_FILES := B.cpp
但应该有这个:
LOCAL_SRC_FILES := A.cpp
LOCAL_SRC_FILES += B.cpp
请注意细节 + = ,而不是:=
我希望有所帮助。
答案 3 :(得分:4)
被称为extern" C"如自动生成的Studio示例中所提供的,但忘记在{}括号中包装文件的其余部分,包括以下函数。只有第一个功能起作用。
答案 4 :(得分:3)
ndk中的应用程序下有一个cpp示例: https://android.googlesource.com/platform/development/+/marshmallow-release/ndk/platforms/android-5/samples/hello-gl2/jni/gl_code.cpp
答案 5 :(得分:3)
另一个原因:在android.mk中使用LOCAL_WHOLE_STATIC_LIBRARIES而不是LOCAL_STATIC_LIBRARIES。这会阻止库优化未使用的API调用,因为NDK无法检测到java代码中本机绑定的使用。
答案 6 :(得分:1)
使用javah(Java SDK的一部分)。它正是这个工具(从.class文件生成.h标题)。
答案 7 :(得分:1)
如果您的包名包含_字符,则应在_字符后面写1(一),如下所示:
MainActivity.java
package com.example.testcpp_2;
本机lib.cpp
JNICALL
Java_com_example_testcpp_12_MainActivity_stringFromJNI(
答案 8 :(得分:0)
我尝试了以上所有解决方案,但没有人可以解决我的构建错误(jni java.lang.UnsatisfiedLinkError:找不到...的实现), 最后我发现我忘记将我的verify.cpp源文件添加到CMakeList.txt add_library segement(verify.cpp是通过Ctrl + Enter自动生成短键,也许是其他文件名),希望我的回复可以帮助一些人。< / p>
我的构建环境:Gradle + CMake
答案 9 :(得分:0)
我面临同样的问题,在我的情况下,原因是我在包名“RFID_Test”中有下划线 我重新命名了包,它起作用了。 谢谢user1222021
答案 10 :(得分:-1)
我两次遇到相同的问题。碰巧,我尝试从Android Studio启动应用程序的手机使用了我尚未在Android Studio中下载的 API级别。