从Android 7.0开始,不再可能链接到非ndk共享库(参见NDK Apps Linking to Platform Libraries).
一种可能的解决方法是将库包含在apk中(参见Update your app).
您尝试链接的库可能依赖于其他非ndk库.在这种情况下,您也应该包括这些库.
就我而言,我一直在开发一个使用OpenCL的应用程序.在ARM设备上,具有正确符号的库是libGLES_mali.so.该应用程序适用于Android< 7.0但它在Android> = 7.0的设备上崩溃.我在logcat中可以读到的错误是:
java.lang.UnsatisfiedLinkError: dlopen failed: library "android.hardware.graphics.common@1.0.so" not found
使用命令
readelf -d libGLES_mali.so | grep NEEDED
我可以读取libGLES_mali.so所依赖的库的名称,并且可以预见android.hardware.graphics.common@1.0.so就是其中之一:
0x0000000000000001 (NEEDED) Shared library: [android.hardware.graphics.common@1.0.so]
0x0000000000000001 (NEEDED) Shared library: [liblog.so]
0x0000000000000001 (NEEDED) Shared library: [libnativewindow.so]
0x0000000000000001 (NEEDED) Shared library: [libz.so]
0x0000000000000001 (NEEDED) Shared library: [libc++.so]
0x0000000000000001 (NEEDED) Shared library: [libutils.so]
0x0000000000000001 (NEEDED) Shared library: [libcutils.so]
0x0000000000000001 (NEEDED) Shared library: [libm.so]
0x0000000000000001 (NEEDED) Shared library: [libc.so]
0x0000000000000001 (NEEDED) Shared library: [libdl.so]
我已经尝试在apk中包含上述库但我得到了同样的错误.奇怪的是,该库是VNDK-SP的一部分(见SP-HAL),因此我理解私有库可以*地依赖它.
有什么建议吗?
编辑31/01/2019:在Android> = 7.0上运行的经过测试的设备都是华为.它可能是供应商相关的问题吗?
解决方法:
Alex Cohn评论是对的.为了解决这个问题,我做了以下几点:
1)在libfoo.so中重命名为android.hardware.graphics.common@1.0.so
2)在CMakeLists.txt中添加了libfoo.so,如下所示:
add_library( foo
SHARED
IMPORTED )
set_target_properties( foo
PROPERTIES IMPORTED_LOCATION
${PROJECT_SOURCE_DIR}/src/main/jniLibs/${ANDROID_ABI}/libfoo.so )
3)针对libfoo.so的目标链接MyLibrary,其中包含OpenCL调用(当然,还有libGLES_mali.so)
target_link_libraries (MyLibrary GLES_mali foo)
4)尽快加载libfoo.so.为此,我在MainActivity中创建了一个静态方法,一旦应用程序进入onCreate(),我就会调用它.
private static void loadLibrary() {
System.loadLibrary("foo");
}
@Override
protected void onCreate(Bundle savedInstanceState) {
loadLibrary();
...
}
此时应用程序崩溃抱怨它找不到一些库.使用readelf命令:
./readelf -d /Users/rodolforocco/AndroidProjects/OvermindClient/app/libs/arm64-v8a/android-27/libfoo.so | grep NEEDED
我能够看到这些确实是libfoo.so所依赖的库.这些库还依赖于无法找到的其他库.我将它们全部从我的设备中的/ system / lib64 /文件夹复制到文件夹${PROJECT_SOURCE_DIR} / src / main / jniLibs / ${ANDROID_ABI} /,其中libfoo.so是.
5)最后,和以前一样,我在需要时加载了MyLibrary.
应用程序不再崩溃并按预期工作.非常感谢!