Xposed 原理

xposed,原理 · 浏览次数 : 46

小编点评

**Xposed 初始化过程** Xposed 使用 `app_process` 方法来代理原来的流程并加载 `XposedBridge.jar`。主要在 `initialize()` 方法中执行以下步骤: 1. **参数处理**:接收 `zygote`、`startSystemServer`、`className` 和 `argc` 和 `argv` 等参数。 2. **Xposed Bridge 加载**:使用 `addJarToClasspath()` 方法将 `XposedBridge.jar`加载到类路径中。 3. **初始化 Xposed framework**:调用 `initXResources()` 方法初始化框架和模块。 4. **加载 Xposed 模块**:调用 `XposedInit.loadModules()` 方法加载框架中定义的模块。 5. **初始化 Zygote 模式**:如果 `zygote` 为真,调用 `XposedInit.hookResources()` 和 `XposedInit.initForZygote()` 方法初始化 Zygote 模式。 6. **调用 `main()` 方法**:调用 `runtime.getRuntime().exec()` 方法启动应用程序的 `main()` 方法。 **Xposed Bridge 加载检查** 当 Xposed Bridge 被加载时,会反射调用 `xposed-installer` apk 的某些核心类。如果可以反射找到,说明 Xposed Bridge 已安装。 **总结** Xposed 通过 `app_process` 方法代理了原来的流程,加载了 `XposedBridge.jar` 并初始化了框架。通过检查 Xposed Bridge 的加载,可以检测是否已安装 Xposed Bridge。

正文

Xposed 使用替换app_process的方式(这是个二进制文件)

xposed 的 app_main2.cpp中做了xposed的初始化
image

/** Initialize Xposed (unless it is disabled). */
bool initialize(bool zygote, bool startSystemServer, const char* className, int argc, char* const argv[]) {
 
    // 参数接管
    xposed->zygote = zygote;
    xposed->startSystemServer = startSystemServer;
    xposed->startClassName = className;
    xposed->xposedVersionInt = xposedVersionInt;
 
    // XposedBridge.jar 加载到 ClassPath 中
    return addJarToClasspath();
}

主要是在这里代理了原来的流程,并加载了XposedBridge.jar到classpath中

初始化完成后进入魔改的runtimeStart:
调用 XPOSED_CLASS_DOTS_ZYGOTE,即XposedBridge.jar中的 XposedBridge 类的 main 方法

protected static void main(String[] args) {
    // Initialize the Xposed framework and modules
    try {
        if (!hadInitErrors()) {
            initXResources();
 
            SELinuxHelper.initOnce();
            SELinuxHelper.initForProcess(null);
 
            runtime = getRuntime();
            XPOSED_BRIDGE_VERSION = getXposedVersion();
 
            // Xposed初始化
            if (isZygote) {
                XposedInit.hookResources();
                XposedInit.initForZygote();
            }
 			// 加载 Xposed 模块
            XposedInit.loadModules(); 
        } else {
            Log.e(TAG, "Not initializing Xposed because of previous errors");
        }
    } catch (Throwable t) {
        Log.e(TAG, "Errors during Xposed initialization", t);
        disableHooks = true;
    }
 
    // Call the original startup code  => 原始执行链
    if (isZygote) {
        ZygoteInit.main(args);
    } else {
        RuntimeInit.main(args);
    }
}

它会在此加载Xposed的资源文件,以此完成后续的Hook操作。

那么也就有了对Xposed的检测方法

  1. 检查内存中是否有XposedBridge.jar
  2. 检查是否有xposed-installer 这个apk
  3. 反射调用xposed的一些核心类,如果可以反射找到,说明注入了XposedBridge.jar

与Xposed 原理 相似的内容: