停更了一段时间,最近主要是玩光遇去了,还有谈恋爱,最近有人问我关于Shizuku的原理,我就来说一下。
奥对了,下期出搭建Qexo的教程
什么是 Shizuku?
Shizuku 是一款开源的 Android 工具,旨在让普通应用能够在无需 Root 权限的情况下,直接调用系统级别的 API(应用程序接口)。通常情况下,Android 系统对应用的权限限制非常严格,许多高级功能(比如管理其他应用的权限、静默安装 APK 或调整系统设置)需要 Root 权限或通过 ADB(Android Debug Bridge)命令间接实现。而 Shizuku 的出现,提供了一种更高效、更优雅的解决方案。
简单来说,Shizuku 就像一个“中间人”,通过启动一个特权进程并利用 Android 的 Binder 机制,帮助普通应用与系统服务直接通信。这样,开发者或用户就可以在不修改设备(Root)的情况下,完成一些需要高权限的操作。
Shizuku 的工作原理
要理解 Shizuku 如何工作,我们需要拆解它的核心机制。以下是详细的原理说明:
1. 启动特权服务
Shizuku 的核心是一个运行在高权限环境下的服务。这个服务必须以某种方式获得系统级别的权限,启动方式有两种:
- 通过 ADB 启动
- ADB 是 Android 提供的调试工具,通常用于开发者与设备之间的通信。
- 在 Android 11 及以上版本,Shizuku 支持通过“无线调试”功能启动服务。你可以在设备的开发者选项中启用无线调试,然后通过 Shizuku 应用生成一个配对码和启动命令,无需连接电脑即可完成。
- 在 Android 10 或更早版本,需要用 USB 连接电脑,通过 ADB 命令启动服务。例如:
adb shell sh /storage/emulated/0/Android/data/moe.shizuku.privileged.api/start.sh
- 这种方式的好处是不需要 Root,适合大多数普通用户。
- 通过 Root 启动
- 如果你的设备已经 Root,只需在 Shizuku 应用中点击“使用 Root 启动”,它会直接利用 Root 权限运行服务。
- 这对于已经解锁设备的用户来说更简单,但需要设备已 Root。
启动后,Shizuku 服务会基于 Android 的app_process
(一个用于运行 Java 进程的工具)创建一个特权进程。这个进程运行在系统环境中,拥有比普通应用更高的权限。
2. Binder 通信机制
- 什么是 Binder?
Binder 是 Android 系统用于进程间通信(IPC,Inter-Process Communication)的一种高效机制。它允许不同进程之间快速传递数据和调用方法,比传统的 Shell 命令或 Socket 通信更加稳定和快速。 - Shizuku 如何使用 Binder?
- Shizuku 服务启动后,会暴露一个 Binder 接口。
- 需要使用 Shizuku 的应用通过这个接口与 Shizuku 服务建立连接。
- 一旦连接建立,应用就可以通过 Shizuku 服务,向 Android 的系统服务(如 PackageManager、ActivityManager 等)发送请求。
- 为什么 Binder 重要?
相比传统的权限提升方式(比如通过su
命令执行 Shell 脚本),Binder 不需要启动额外的进程,也不需要解析文本输出,因此效率更高,延迟更低。
3. 代理系统 API 调用
- Shizuku 服务本质上是一个“代理”。它接收来自应用的请求,然后以自己的特权身份调用系统 API,最后将结果返回给应用。
- 例如,假设你想授予某个应用存储权限,通常需要系统级权限。通过 Shizuku,应用可以发送请求给 Shizuku 服务,由它代为调用
IPackageManager.grantRuntimePermission()
方法完成操作。
Shizuku 的工作原理可以用一句话概括:通过一个特权进程和 Binder 机制,代理普通应用的系统 API 调用。它避免了 Root 的复杂性,同时比 Shell 命令更高效,是 Android 开发中的一大创新。
如何调用 Shizuku?
如果你是开发者,想在自己的应用中集成 Shizuku,下面是详细步骤:
1. 添加 Shizuku API 依赖
- 在项目的
build.gradle
文件中添加 Shizuku API 依赖:repositories { maven { url 'https://jitpack.io' } } dependencies { implementation 'com.github.RikkaApps:Shizuku-api:<最新版本号>' }
- 前往 Shizuku GitHub Releases 查看最新版本号。
2. 检查 Shizuku 可用性并获取 Binder
- 在你的代码中,首先检查 Shizuku 服务是否可用,并获取 Binder 对象:
import moe.shizuku.api.ShizukuClient; import android.os.IBinder; public class ShizukuHelper { public static boolean isShizukuAvailable() { return ShizukuClient.checkSelfPermission() == ShizukuClient.PERMISSION_GRANTED; } public static IBinder getShizukuBinder() { return ShizukuClient.getBinder(); } }
3. 调用系统 API
- 使用 Binder 调用系统服务。例如,授予某个应用的运行时权限:
import moe.shizuku.api.ShizukuBinderWrapper; import android.content.pm.IPackageManager; IBinder binder = ShizukuHelper.getShizukuBinder(); if (binder != null) { IPackageManager pm = IPackageManager.Stub.asInterface(new ShizukuBinderWrapper(binder)); try { pm.grantRuntimePermission("com.example.app", "android.permission.READ_EXTERNAL_STORAGE", 0); } catch (Exception e) { e.printStackTrace(); } }
4. 处理服务中断
- Shizuku 服务可能会因设备重启或意外终止而断开,因此需要监听 Binder 的状态:
binder.linkToDeath(new IBinder.DeathRecipient() { @Override public void binderDied() { // 服务断开,提示用户重新启动 Shizuku Log.e("Shizuku", "Binder died, please restart Shizuku service"); } }, 0);
