0%

使用 Android NDK 保存重要的字符串

平时在开发过程中,像 client id、API keys 之类的字符串经常会直接写在客户端的 Java 代码中,这样别人在逆向 apk 过程中,这些字符串就会很容易地暴露在逆向者的眼中。本文介绍了使用 Android NDK 将字符串存放在 so 文件里,这样虽然不能完全防止被逆向,但是也能用混淆来制造些障碍。

操作方法

  • src/main 下创建一个 jni 目录。
  • jni 目录下分别创建 Android.mk 文件,内容如下:
1
2
3
4
5
6
7
8
LOCAL_PATH := $(call my-dir)

include $(CLEAR_VARS)

LOCAL_MODULE := keys
LOCAL_SRC_FILES := keys.c

include $(BUILD_SHARED_LIBRARY)

其中 LOCAL_MODULE := keys 是生成的 so 库名称,LOCAL_SRC_FILES := keys.c 是源代码的文件名。

  • jni 目录下创建 Application.mk 文件,内容如下:
1
APP_ABI := all

这里是 ABI 设置,ABI 表示应用二进制接口 (Application binary interface)

  • jni 目录下创建 keys.c 文件,内容如下:
1
2
3
4
5
6
#include <jni.h>

JNIEXPORT jstring JNICALL
Java_com_xie_jun_unitytest_MainActivity_getNativeKey(JNIEnv *env, jobject instance) {
return (*env)->NewStringUTF(env, "testkey");
}

Java_com_xie_jun_unitytest_MainActivity_getNativeKey 表示在 com.xie.jun.unitytest.MainActivity 这个类中有一个 native 方法,名字为 getNativeKey

  • MainActivity.java 文件中加入如下代码:
1
2
3
static {
System.loadLibrary("keys");
}
  • MainActivity.java 文件中声明 native 方法:
1
public native String getNativeKey();
  • build.gradle 文件中加入 NDK 配置:
1
2
3
4
5
6
7
8
9
android {
// ...
externalNativeBuild {
ndkBuild {
path 'src/main/jni/Android.mk'
}
}
// ...
}
  • 同步 gradle 成功后,可以使用 getNativeKey 方法来获取写在 keys.c 里的字符串:
1
Log.i("TAG", "native keys: " + getNativeKey());

运行即可看到打印:

参考链接