当前位置: 首页 > 工具软件 > ANR-WatchDog > 使用案例 >

ANR原理,不是WatchDog

羊舌富
2023-12-01

ANR 窗口

对于绝大数Android开发者都知道 ANR弹框,ANR全程是 Application Not Response。

ANR 的界面

在Android Q中 ANR窗口的构建是在 AppErrors.java 类中的 handleShowAnrUi(Message msg) 函数去做逻辑处理,
该对话框是一个继承 Dialog 的 AppNotRespondingDialog,AppNotRespondingDialog 负责了窗口的布局,输入事件等等行为,具体可以阅读 AppNotRespondingDialog.java.

ANR 对话框产生

这里需要抓住ANR一个关键函数 ProcessRecord.java 里的 appNotResponding(tring activityShortComponentName, ApplicationInfo aInfo,String parentShortComponentName, WindowProcessController parentProcess,
boolean aboveSystem, String annotation, boolean onlyDumpSelf) 该方法时发起ANR的唯一入口,而调用该接口的方法有

  1. ActivityServices.serviceTimeout()
  2. ActivityServices.serviceForegroundTimeout()
  3. ActivityManagerService.appNotRespondingViaProvider(IBinder connection)
  4. ActivityManagerService.inputDispatchingTimedOut()
  5. BroadcastQueue.AppNotResponding

上述对应的常量:

  • ActiveServices:SERVICE_TIMEOUT = 20_000
  • ActiveServices: SERVICE_BACKGROUND_TIMEOUT = SERVICE_TIMEOUT * 10;
  • ActiveServices:SERVICE_START_FOREGROUND_TIMEOUT = 10*1000;
  • WindowManagerService: DEAFULT_INPUT_DISPATCHING_TIMEOUT_NANOS = 5000*1000000L
  • BroadcastConstants:DEAFULT_TIMEOUT = 10_000
  • 对应content provider 来说需要自己通过ContentProviderClient.java的setDetectNotResponding(long )设置,此为系统APP 才可使用,可以参考 Bluetooth 里的BluetoothMapAccountLoader.java的 parseAccounts()

ANR 检测思路

对于service、provider、broadcast而言,可以在service 启动阶段发送一个延时message,然后在启动完成后removemessage
对于输入而言,就是通过时间差与超时时间进行比对,大于超时时间就弹框。
参考 InputDispatcher.cpp 里的 handleTargetsNotReadyLocked(…)以及 onANRLocked(…)方法

 类似资料: