三个工具类

1、

/*** @author : LGQ* @date : 2020/05/11 14* @desc :*/
public class HCallback implements Handler.Callback{private final String TAG="HCallback";private Handler mHandler;public HCallback(Handler handler){mHandler=handler;}@Overridepublic boolean handleMessage(Message msg) {//这里为159,是因为EXECUTE_TRANSACTION字段的值为159if(msg.what==159){//r实际为clienttransactionObject r= msg.obj;try {Class clientClazz = r.getClass();Field fCallbacks = clientClazz.getDeclaredField("mActivityCallbacks");fCallbacks.setAccessible(true);//得到transactionz中的callbacks,为一个list,其中元素为LaunActivityItemList<?> lists = (List) fCallbacks.get(r);for(int i=0;i<lists.size();i++){Object item = lists.get(i);Class itemClazz = item.getClass();//拿到LaunActivityItem中的intent,进行替换Field mIntent = itemClazz.getDeclaredField("mIntent");mIntent.setAccessible(true);Intent intent = (Intent) mIntent.get(item);Intent target = intent.getParcelableExtra("target_intent");if(target!=null){intent.setComponent(target.getComponent());}}} catch (NoSuchFieldException e) {e.printStackTrace();} catch (IllegalAccessException e) {e.printStackTrace();}}mHandler.handleMessage(msg);return true;}
}

2、

public class HookHelper {private static  final String TAG="HookHelper";public static void hookAms() throws Exception {Class clazz = null;Field singletonIAMS = null;
//        Class clazz = ActivityManager.class;
//        Field singletonIAMS = clazz.getDeclaredField("IActivityManagerSingleton");if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) {clazz = ActivityManager.class;singletonIAMS = clazz.getDeclaredField("IActivityManagerSingleton");}else {clazz =Class.forName("android.app.ActivityManagerNative");singletonIAMS =clazz.getDeclaredField("gDefault");}singletonIAMS.setAccessible(true);Object defultSingleton = singletonIAMS.get(null);Class singletonClazz = Class.forName("android.util.Singleton");Field mInstance = singletonClazz.getDeclaredField("mInstance");mInstance.setAccessible(true);Object iAMs = mInstance.get(defultSingleton);Class iAmClazz =Class.forName("android.app.IActivityManager");Object proxy = Proxy.newProxyInstance(Thread.currentThread().getContextClassLoader(),new Class[]{iAmClazz},new IActivityManagerProxy(iAMs));mInstance.set(defultSingleton,proxy);}public static void hookHandler() throws Exception{try {// 获取ActivityThread实例Class activityThreadClass = Class.forName("android.app.ActivityThread");Field threadField = activityThreadClass.getDeclaredField("sCurrentActivityThread");threadField.setAccessible(true);Object sCurrentActivityThread = threadField.get(null);// 获取mH变量Field mHField = activityThreadClass.getDeclaredField("mH");mHField.setAccessible(true);final Object mH = mHField.get(sCurrentActivityThread);// 设置mCallback变量Field mCallbackField = Handler.class.getDeclaredField("mCallback");mCallbackField.setAccessible(true);Handler.Callback callback = new Handler.Callback() {@Overridepublic boolean handleMessage(Message msg) {if (msg.what == 100) {try {Field intentField = msg.obj.getClass().getDeclaredField("intent");intentField.setAccessible(true);Intent intent = (Intent) intentField.get(msg.obj);Intent raw = intent.getParcelableExtra("RawIntent");intent.setComponent(raw.getComponent());} catch (Exception e) {Log.e("hook", "hookActivityThreaderr"+ e);}}return false;}};mCallbackField.set(mH, callback);} catch (Exception e) {Log.e("hook", "hookActivityThreaderr"+ e);}}
}

3、

public class IActivityManagerProxy implements InvocationHandler {private Object activityManager;private static final String TAG="IActivityManagerProxy";public IActivityManagerProxy(Object activityManager){this.activityManager=activityManager;}@Overridepublic Object invoke(Object proxy, Method method, Object[] args) throws Throwable {if(method.getName().equals("startActivity")){Intent intent =null;int index=0;for(int i=0;i<args.length;i++){if(args[i] instanceof Intent){index=i;break;}}intent = (Intent) args[index];String packageName = "com.suny.hooktest";Intent subIntent = new Intent();//替换activity为已经注册的占坑activity
//            subIntent.setClassName(packageName,packageName+".SubActivity");Intent raw = (Intent) args[index];subIntent.setClassName(raw.getComponent().getPackageName(), StubActivity.class.getName());//同时将真正的intent保存在subintent中,绕过AMS的检查后,将真正的intent替换回来
//            subIntent.putExtra("target_intent",intent);subIntent.putExtra("RawIntent", raw);args[index]=subIntent;Log.d(TAG, "invoke: subIntent="+subIntent+"inteent="+intent);}return method.invoke(activityManager,args);}
}

初始化

public class MyApplication extends Application {@Overrideprotected void attachBaseContext(Context base) {super.attachBaseContext(base);try {HookHelper.hookAms();HookHelper.hookHandler();} catch (Exception e) {e.printStackTrace();}}
}

实现demo链接:https://download.csdn.net/download/meixi_android/12409214

bug在线交流:QQ1085220040

Android开发启动未注册的activity,Hook使用demo相关推荐

  1. Activity启动流程:Hook实现启动未注册Activity

    Android中插件化的简单实现:启动未注册的Activity 前言 本文介绍在Android中启动未在AndroidManifest中注册的Activity的一个解决方案.主要需要掌握以下知识点: ...

  2. 【Android开发】使用Bottom Navigation Activity去掉顶部栏(标题栏)

    [Android开发]使用Bottom Navigation Activity去掉顶部栏(标题栏)    在使用android自带的模板Botton Navigation Activity后,页面顶部 ...

  3. Android开发:登录/注册界面的编写

    目录 新建一个空项目(或Activity) 在xml中绘制登录界面 关掉ActionBar 运行(最终效果图) 后记 在实际开发中,几乎所有的APP都会涉及到用户注册/登录页面的制作,因此本文以And ...

  4. android开发启动画面,Android开发笔记——如何正确实现App启动页

    启动页在当前的Android APP中有着广泛的使用,在Material Design规范出来之前,Android官方是不推荐使用启动页的,理由是让用户在启动APP后干等是一种浪费时间的行为.Mate ...

  5. Android开发,登录注册界面中如何添加视频背景,亲测可用

    此篇文章属个人查阅资料整理所著,希望能对您有所帮助,欢迎各位留言指正,抱拳了 一. 首先在res文件夹下添加raw文件夹并将要添加的背景视频放进去: 二.在MyViewpager.java(此为要显示 ...

  6. 【android开发】手势滑动关闭Activity(随手指消失)的辅助类的实现

    [CSDN抽风,把我写一个多小时的东西覆盖了.真的是哔了狗了,自己又没有备份...重写吧...] 这个类主要是实现向右滑动关闭Activity,效果如下: 老套路,先写思路: 1)将Activity的 ...

  7. Android开发八 “尚未注册网络”错误信息的解决办法

    打开Android模拟器时,出现无信号,拔打电话或发短信时,提示"尚未注册网络"错误信息的解决方案如下.场景一:你的电脑没有连接上互联网,同时也没有在局域网.   解决办法:右键点 ...

  8. 【Android】Android开发启动app弹出一张广告图片,Dialog可以查看大图,查看某个图片功能...

    作者:程序员小冰,GitHub主页:https://github.com/QQ986945193 新浪微博:http://weibo.com/mcxiaobing 首先给大家看一下我们今天这个最终实现 ...

  9. Android开发:4-2、不同Activity数据的传递

    4-2.不同Activity数据的传递 Activity数据传递的启动方式 不带返回值的启动Activity并传递数据 带返回值启动Activity: Activity数据传递的启动方式 1. 2. ...

最新文章

  1. Oracle日常巡检
  2. Python单元测试--使用装饰器实现测试跳过和预期故障
  3. mybatis知识点
  4. 微軟专为Visual Studio 2019设计出一套容器工具擴充套件
  5. nginx 在ubuntu 上的启动,停止,重启
  6. Ajax(2)--Ajax核心工作机制 你忘记了吗?
  7. 原生javaScript中使用Ajax实现异步通信
  8. 形式化方法对软件开发的挑战:一些历史与现实
  9. 怎么解决每次打开Office 2013都提示配置进度
  10. 劫持无处不在,如何应对镜像劫持?三大手段应对重定向
  11. 在开发板显示24位的bmp格式图片
  12. azure mysql on vnet_Azure Database for MySQL (2) VNET rules
  13. 论文笔记 EMNLP 2018|Jointly Multiple Events Extraction via Attention-based Graph Information Aggregation
  14. Kubernetes pod的生命周期
  15. 每日一练 — 2022.01.30
  16. 100道linux运维笔试题
  17. 倍福控制器报1804错误解决方法
  18. halcon NCC模板匹配读写算子
  19. 日本鲭川CRAFSIS进军中国市场 无界眼镜独家代理
  20. Makecode编程软件打不开

热门文章

  1. [jQuery] jQuery的队列是如何实现的?队列可以用在哪些地方?
  2. [css] 举例说明你知道的css技巧有哪些?
  3. [css] 怎么去掉点击a链接或者图片出现的边框?
  4. 前端学习(2584):ant design pro
  5. 前端学习(2157):webpack-dev-server搭建本地服务
  6. 前端学习(2122):项目演示
  7. oracle之高级子查询1
  8. (总结)HTTP常见错误返回代码
  9. MATLAB K-means聚类代码讲解
  10. 树莓派移植SX1278 LoRa通信--使用wiringPiSPI移植SPI通信接口