Android9.0动态链接库加载链接完全解读(1)--System.loadLibrary到dlopen

什么是Android Linker

Android 的加载/链接器linker 主要用于实现共享库的加载与链接。

从 System.loadLibrary 追溯

jni 开发的 so load

平时我们进行JNI开发 要链接我们的so库只需要执行System.loadLibrary函数即可

static {
   
        try {
   
            CLogUtils.e("开始加载 Test so文件 ");
            System.loadLibrary("Test");
            init();
        } catch (Throwable e) {
   
            CLogUtils.e("加载So出现异常 " + e.toString());
            e.printStackTrace();
        }
    }

或许你没有想过 为什么这样就可以将so加载进来了。

我们继续跟进代码

本次采用SDK28的代码 也就是安卓9.0的代码分析

System.loadLibrary("Test");->Runtime loadLibrary0

loadLibrary0方法跟进

...
String filename = System.mapLibraryName(libraryName);
        List<String> candidates = new ArrayList<String>();
        String lastError = null;
        for (String directory : getLibPaths()) {
            String candidate = directory + filename;
            candidates.add(candidate);

            if (IoUtils.canOpenReadOnly(candidate)) {
                String error = nativeLoad(candidate, loader);
                if (error == null) {
                    return; // We successfully loaded the library. Job done.
                }
                lastError = error;
            }
        }
 ...

走到了 nativeLoad 方法

nativeLoad

private static native String nativeLoad(String filename, ClassLoader loader);显然是一个Native方法

我们要找到他对应的cpp代码。通过查找资料得知他的文件路径在

libcore/ojluni/src/main/native/Runtime.c

打开源码阅读网站分析:
runtime.c

核心的代码部分

JNIEXPORT jstring JNICALL
Runtime_nativeLoad(JNIEnv* env, jclass ignored, jstring javaFilename,
                   jobject javaLoader)
{
    return JVM_NativeLoad(env, javaFilename, javaLoader);
}

转到了 JVM_NativeLoad(env, javaFilename, javaLoader);方法中

JVM_NativeLoad

这个方法在libcore/ojluni/src/main/native/jvm.h

jvm.h

方法申明

JNIEXPORT jstring JVM_NativeLoad(JNIEnv* env, jstring javaFilename,
                                 jobject javaLoader);

具体的方法实现要看谁实现这个方法申明

art/openjdkjvm/OpenjdkJvm.cc

art/openjdkjvm/OpenjdkJvm.cc

JNIEXPORT jstring JVM_NativeLoad(JNIEnv* env,
                                 jstring javaFilename,
                                 jobject javaLoader) {
   
  ScopedUtfChars filename(env, javaFilename);
  if (filename.c_str() == NULL) {
   
    return NULL;
  }

  std::string error_msg;
  {
   
    art::JavaVMExt* vm = art::Runtime::Current()->
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值