为什么 app_process run java 方法在调用 JNI 后被杀死
这就是我所做的:
- 使用 android studio 模板创建一个 Native C++ 项目
- 创建一个类 com.jnitest.app.JNIInterface
package com.jnitest.app;
public class JNIInterface {
public static native String getString();
public static native String getName();
}
使用 native-lib.cpp
#include <jni.h>
#include <string>
extern "C" JNIEXPORT jstring JNICALL
Java_com_jnitest_app_JNIInterface_getString(JNIEnv *env, jclass thiz) {
std::string name = "return String from JNIInterface";
return env->NewStringUTF(name.c_str());
}
extern "C"
JNIEXPORT jstring JNICALL
Java_com_jnitest_app_JNIInterface_getName(JNIEnv *env, jclass clazz) {
std::string name = "return name from JNIInterface";
return env->NewStringUTF(name.c_str());
}
- 创建一个测试类 com.jnitest.app.JNITest
package com.jnitest.app;
public class JNITest {
{
System.loadLibrary("app");
}
public static void main(String[] args) {
System.out.println("Hello from JNITest");
System.out.println("String from JNI: " + JNIInterface.getString());
}
}
- 构建推送并运行
adb push .\build\intermediates\apk\debug\app-debug.apk /data/local/tmp/app-debug.jar
adb shell CLASSPATH=/data/local/tmp/app-debug.jar app_process ./ com.jnitest.app.JNITest
- 获取输出
Hello from JNITest
Killed
为什么我无法得到正确的结果?
Here is what I do :
- create a Native C++ project use android studio template
- create a class com.jnitest.app.JNIInterface
package com.jnitest.app;
public class JNIInterface {
public static native String getString();
public static native String getName();
}
with the native-lib.cpp
#include <jni.h>
#include <string>
extern "C" JNIEXPORT jstring JNICALL
Java_com_jnitest_app_JNIInterface_getString(JNIEnv *env, jclass thiz) {
std::string name = "return String from JNIInterface";
return env->NewStringUTF(name.c_str());
}
extern "C"
JNIEXPORT jstring JNICALL
Java_com_jnitest_app_JNIInterface_getName(JNIEnv *env, jclass clazz) {
std::string name = "return name from JNIInterface";
return env->NewStringUTF(name.c_str());
}
- create a test class com.jnitest.app.JNITest
package com.jnitest.app;
public class JNITest {
{
System.loadLibrary("app");
}
public static void main(String[] args) {
System.out.println("Hello from JNITest");
System.out.println("String from JNI: " + JNIInterface.getString());
}
}
- build push and run
adb push .\build\intermediates\apk\debug\app-debug.apk /data/local/tmp/app-debug.jar
adb shell CLASSPATH=/data/local/tmp/app-debug.jar app_process ./ com.jnitest.app.JNITest
- get output
Hello from JNITest
Killed
Why I cannot get the right result ?
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(2)
我相信,由于在较新的Android版本(&GT; 23)中,因此在安装后,APK中的SO文件根本不会被压缩。
为确保这些文件不会被压缩,请更改build.gradle脚本,以下是:
在我的项目中,我使用的gradle版本为6.7.1,而相应的com.android.tool.tools.build版本是4.2.0。其他较新的组合也应应用此
jnilibs
块。之后,您可以将APK或JAR视为
特殊文件夹
,通过附加拼写标记(!
)。如果要访问APK中的文件夹的内容(包含SO文件的文件夹),则可以运行一个命令,例如:
ld_library_path =/path/to/apk/apk/temp.ap.ap.ap.ap./lib/abi class =/ path/to/apk/temp.ap.apk app_process/system/bin com.package.name.name.main
其中
lib/abi
insem temp.ap.apk包含您想在com中使用的so files .package.name.main。一个很棒的技巧。就像魅力一样。
I believe since in newer android version(>23), the so files inside apk will not be compressed at all for fewer space occupation after installation.
To make sure those so files will not be compressed, change the build.gradle script of the app module to this:
In my project, the gradle version I used is 6.7.1, and the corresponding com.android.tools.build version is 4.2.0. Other newer combination should also apply this
jniLibs
block.After this, you could treat the apk or jar as a
special folder
by appending an exclamation mark(!
).If you want to access the content of the folder inside apk (a folder containing so files), you could run a command like:
LD_LIBRARY_PATH=/path/to/apk/temp.apk!/lib/abi CLASSPATH=/path/to/apk/temp.apk app_process /system/bin com.package.name.Main
Where the
lib/abi
inside temp.apk contains the so files you wanna use in com.package.name.Main.A fantastic trick. Works like a charm.
我也遇到了这个问题。 Classloader找不到本地库。尝试以下内容。
uselegacyPackaging false
需要添加到build.gradle
,以便不压缩LIB,并且可以直接从内部APK加载。I had this problem too. Native library is not found by ClassLoader. Try the following.
useLegacyPackaging false
needs to be added tobuild.gradle
so that libs are not compressed and can be directly loaded from inside apk.