浪费了半天的时间试图构建两个共享库,例如mod1
和mod2
(其中Android NDK编译为libmod1.so
和libmod2.so
),来自jni文件夹和子文件夹中的源,然后让mod1从mod2调用一个函数。关于如何使构建工作,但然后运行时动态链接无效的答案很多,应用程序在启动时崩溃。Android NDK - 使两个本地共享库互相调用
决定发布这个问题,并立即回答它,这样Q和A在整个过程中在一起,并希望别人不会再浪费一天时间研究它。
浪费了半天的时间试图构建两个共享库,例如mod1
和mod2
(其中Android NDK编译为libmod1.so
和libmod2.so
),来自jni文件夹和子文件夹中的源,然后让mod1从mod2调用一个函数。关于如何使构建工作,但然后运行时动态链接无效的答案很多,应用程序在启动时崩溃。Android NDK - 使两个本地共享库互相调用
决定发布这个问题,并立即回答它,这样Q和A在整个过程中在一起,并希望别人不会再浪费一天时间研究它。
正确的构建过程相对容易,我的问题是使libmod1.so依赖libmod2.so导致启动时不满意的链接 - mod1代码找不到mod2共享库,即使两者都存在于同一个文件夹中最终的APK,下库/ armeabi,林达/ 86等。但是,让我的答案完整:
把你的C或C++在你的Android项目源和头文件下的JNI目录的子目录,例如文件夹mod1 /和mod2/
根据NDK指令,创建Application.mk文件,例如,我的是:
NDK_TOOLCHAIN_VERSION = 4.7
APP_PLATFORM:= Android的8
APP_ABI:= armeabi armeabi-V7A 86
LOCAL_PATH:= $(叫我-DIR)
包括$(CLEAR_VARS)
LOCAL_SHARED_LIBRARIES:= MOD2 #这使得libmod1.so依赖libmod2.so
LOCAL_MODULE:= MOD1
LOCAL_SRC_FILES:= MOD1 /file1.c
LOCAL_SRC_FILES + = MOD1/file2.cpp
...
包括$(BUILD_SHARED_LIBRARY) #这实际上建立libmod1.so
包括$(CLEAR_VARS)
LOCAL_MODULE:= MOD2
LOCAL_SRC_FILES:= MOD2/file1.cc
LOCAL_SRC_FILES + =模2/file2.cc
...
包括$(BUILD_SHARED_LIBRARY) #此建立libmod2 .so
就是这样,所有的构建都没有使用ndkbuild脚本的抱怨。你只需要一个C封装来从Java调用一些函数。这是我的问题。因为我只有在libmod1中才有可从Java调用的函数。所以,在Java中我的C包装类是这样的:
public class CWrapper {
static {
System.loadLibrary("mod1");
}
public static native int func1(String aParam);
...
}
这似乎完全合乎逻辑的,我 - 我称之为从Java到libmod1.so,所以我用的System.loadLibrary(“MOD1”),并自libmod1。所以知道它取决于libmod2.so,并且这两个文件都在同一个文件夹中,libmod1将知道如何查找并加载libmod2,对不对?错误!它在应用程序启动时以“不满意的链接”崩溃。确切的错误信息是:
java.lang.UnsatisfiedLinkError: Cannot load library: soinfo_link_image(linker.cpp:1635): could not load library "libmod2.so" needed by "libmod1.so"; caused by load_library(linker.cpp:745): library "libmod2.so" not found
我到处寻找更多的代码添加到Android.mk解决这个徒劳无功。最后尤里卡!我修改了CWrapper类,如下所示:
public class CWrapper {
static {
System.loadLibrary("mod2"); // must be first, as mod1 depends on mod2!
System.loadLibrary("mod1");
}
public static native int func1(String aParam);
...
}
,事情开始像一个魅力的工作...
格雷格
由此我们可以得出结论,该系统的动态加载程序并加载依赖(标准行为),而Java加载程序则不行。 – Samveen
这是一个很好的观察,@Samveen。也许我应该在新版本的Android下重新测试,看看他们最近是否有改进。 – gregko