起因
最近接到一个新的项目,需要开发Xposed模块相关代码,之前没有开发过Xposed模块,只能看着网上的教程简单开发个demo,
熟悉一下Xposed模块开发流程.
环境
下载安装Android Studio 并且有java开发环境
一台支持Xposed环境的手机
使用到的案例app wuaipojie 和 xp api.jar
链接: https://pan.baidu.com/s/1I7mJBrYT3ZzaKYqKd1DGMg?pwd=69di 提取码: 69di
创建项目
添加相关配置
修改AndroidManifest.xml
android:name="xposedmodule" android:value="true" /> android:name="xposeddescription" android:value="xp模块测试" /> android:name="xposedminversion" android:value="54" /> 添加xp api.jar 添加xposed_init package com.example.myapp; import de.robv.android.xposed.IXposedHookLoadPackage; import de.robv.android.xposed.callbacks.XC_LoadPackage; public class TestHook implements IXposedHookLoadPackage { @Override public void handleLoadPackage(XC_LoadPackage.LoadPackageParam loadPackageParam) throws Throwable { } } 编写hook代码 先看下目标app 需要hook的地方 手机打开usb调试链接电脑 package com.example.myapp; import android.util.Log; // Android 系统日志工具 import de.robv.android.xposed.IXposedHookLoadPackage; // Xposed核心接口 import de.robv.android.xposed.XC_MethodHook; // 方法hook基础类 import de.robv.android.xposed.XposedBridge; // Xposed专用日志工具 import de.robv.android.xposed.XposedHelpers; // Xposed反射辅助工具 import de.robv.android.xposed.callbacks.XC_LoadPackage; // 加载包回调参数 public class TestHook implements IXposedHookLoadPackage { @Override public void handleLoadPackage(XC_LoadPackage.LoadPackageParam loadPackageParam) throws Throwable { // 1. 检查是否为目标进程(防止误hook其他应用) if (!loadPackageParam.packageName.equals("com.zj.wuaipojie")) { return; // 非目标包直接跳过 } // 2. 获取目标进程的类加载器(关键!) ClassLoader targetClassLoader = loadPackageParam.classLoader; // 3. 执行方法hook(精确匹配方法签名) XposedHelpers.findAndHookMethod( "com.zj.wuaipojie.Demo", // 目标类全称 targetClassLoader, // 必须使用目标进程的类加载器 "a", // 要hook的方法名 String.class, // 方法参数类型(按顺序) new XC_MethodHook() { // 方法回调处理 @Override protected void beforeHookedMethod(MethodHookParam param) throws Throwable { super.beforeHookedMethod(param); // === 方法执行前逻辑 === // 第一种日志方式:Android标准日志(可能被系统过滤) Log.d("zj2595", "第一种日志记录方式," + "方法 a 被调用未修改参数: " + param.args[0].toString() ); // 第二种日志方式:Xposed专用日志(稳定输出) XposedBridge.log( "第二种日志记录方式," + "方法 a 被调用未修改参数: " + param.args[0].toString() ); // 修改方法参数(通过反射直接操作参数数组) param.args[0] = "被HOOK过"; // 输出修改后的参数值 Log.d("zj2595", "第一种日志记录方式," + "方法 a 修改后的参数: " + param.args[0].toString() ); } @Override protected void afterHookedMethod(MethodHookParam param) throws Throwable { super.afterHookedMethod(param); // === 方法执行后逻辑 === // 可在此处收集返回值或执行清理操作 // 示例:Log.d("zj2595", "方法a返回值: " + param.getResult()); } } ); } } 实现简单的hook 打包成apk 参考 https://www.bilibili.com/video/BV1b94y1u7gq/?spm_id_from=333.337.search-card.all.click https://www.bilibili.com/video/BV1VT411C7Sr/?spm_id_from=888.80997.embed_other.whitelist&t=472.311224&bvid=BV1VT411C7Sr&vd_source=71255b7f1df42f35a9ec4d880389817c