背景
我們想啟動 APK 程序,有很多種方法,可以使用 Intent,也可以使用 adb shell 命令來啟動,還有通過反射來啟動 APk 程序。
我們這里主要討論通過反射的方式來啟動 apk 程序。Android10 之前,我們通過反射來啟動 APK,反射的是 startActivityAndWait(…) 方法,該方法是在 IActivityMessage.java 實現的,通過來啟動 APk 程序。
在 Android10 的時候,該方案不太適用,需要反射 shellCommand(…) 來啟動 Android 系統 10 的 APK 程序。
本方案是基于 AM 啟動 Activity 的方式來實現的。
核心技術方案和原理圖
Android 10 為了增加安全性 IActivityMessage.java 類去掉了,變為 IActivityMessage.aidl 文件,其中 startActivityAndWait(…) 方法轉移到了 ActivityManagerServer.java 服務類中。所以,我們不能使用 IActivityMessage.java 去執行 startActivityAndWait(…) 方法。
Android 10 AM.java 啟動源碼:
Android 10 原先 AM.java 功能邏輯轉移到 ActivityManagerShellCommand.java 源碼如下:
我們要反射 mAm.asBinder().shellCommand 來啟動 APK。方案實現時序圖如下:
技術優勢
兼容了 Android10 通過反射啟動 APK 。
技術實現
1.首先獲取 ActivityManagerNative 類對象。
2.獲取 IActivityManager 對象。
3.獲取當前的手機系統版本。
4.調用 IActivityManager 中的 asBinder 方法,可以通過該方法獲取 BinderProxy 對象。
5.反射獲取 ShellCallback 類對象和 ResultReceiver 類對象。
6.獲取 shellCommand 方法。
7.調用 shellCommand 方法。
整體實現代碼
效果展示
Android 10 手機
  運行成功 cmd 界面截圖
  啟動成功后的 APK 界面