Android Rescue party

什么是Rescue Party?
官方解释救援程序[https://source.android.com/devices/tech/debug/rescue-party]
“当该功能注意到核心系统组件陷入崩溃循环僵局时,就会派出“救援程序”。然后救援程序会通过一系列操作来上报相关情况,以期恢复设备。最后的解决方法是,救援程序使设备重新启动并进入恢复模式,然后提示用户恢复出厂设置。”

实现
在 Android 8.0 中,救援程序默认处于启用状态,其实现位于 /services/core/java/com/android/server/RescueParty.java 中。 在出现以下情况时,救援程序会收到有关启动和崩溃事件的信息,然后即会启动:
system_server 在 5 分钟内重启 5 次以上。
永久性系统应用在 30 秒内崩溃 5 次以上。
当检测到上述某种情况时,救援程序会将其上报给下一救援级别、处理与该级别相关联的任务,并让设备继续运行,看看能否恢复。清除或重置内容的程度随级别而增加。最高级别会提示用户将设备恢复出厂设置。

所有的救援操作都会记录到“/data/system/uiderrors.txt”中的永久性的PackageManager日志中。

界面
会显示下面的字串:
“Can`t load Android system. Your data may be corrupt. If you continue to get this message, you may need to perfrom a factory data reset and erase all user data stored on this device.”

相关代码
frameworks/base/services/core/java/com/android/server/RescueParty.java
启动相关的代码:
system/core/bootstat/

大体套路就是,先检查对应的标志位是否足够触发重启了(incrementAndTest),如果足够,先重置标志位,然后升级Rescue Level(不是每个level都会触发factory reset)。执行对应等级对应的操作(executeRescueLevel)

/**
 * Take note of a boot event. If we notice too many of these events
 * happening in rapid succession, we'll send out a rescue party.
 */
public static void noteBoot(Context context) {
    if (isDisabled()) return;
    if (sBoot.incrementAndTest()) {
        sBoot.reset();
        incrementRescueLevel(sBoot.uid);
        executeRescueLevel(context);
    }
}

/**
 * Take note of a persistent app or apex module crash. If we notice too many of these
 * events happening in rapid succession, we'll send out a rescue party.
 */
public static void noteAppCrash(Context context, int uid) {
    if (isDisabled()) return;
    Threshold t = sApps.get(uid);
    if (t == null) {
        t = new AppThreshold(uid);
        sApps.put(uid, t);
    }
    if (t.incrementAndTest()) {
        t.reset();
        incrementRescueLevel(t.uid);
        executeRescueLevel(context);
    }
}

注意里面的incrementAndTest()/incrementRescueLevel/executeRescueLevel三个接口。

Rescue Level

看看,从LEVEL_NONE升级到最后,一定会触发LEVEL_FACTORY_RESET的。

static final int LEVEL_NONE = 0;
static final int LEVEL_RESET_SETTINGS_UNTRUSTED_DEFAULTS = 1;
static final int LEVEL_RESET_SETTINGS_UNTRUSTED_CHANGES = 2;
static final int LEVEL_RESET_SETTINGS_TRUSTED_DEFAULTS = 3;
static final int LEVEL_FACTORY_RESET = 4;

对于persistent应用来说,应用的crash会触发noteAppCrash:

frameworks/base/services/core/java/com/android/server/am/AppErrors.java
if (r.isPersistent() || isApexModule) {
    // If a persistent app or apex module is stuck in a crash loop, the device isn't
    // very usable, so we want to consider sending out a rescue party.
    RescueParty.noteAppCrash(mContext, r.uid);
}

什么是永久性系统应用,其实就是persist应用(always keep this application running?)。

参考:
官方解释救援程序[https://source.android.com/devices/tech/debug/rescue-party]

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值