Tencent / tinker

Tinker is a hot-fix solution library for Android, it supports dex, library and resources update without reinstall apk.
Other
17.14k stars 3.33k forks source link

关于tinker源码中,判断为system_ota之后会执行TinkerDexOptimizer.optimizeAll()。这里为什么主动去对这部分dexfile做dex2oat呢? #867

Closed Logwangwei closed 5 years ago

Logwangwei commented 6 years ago

Issue/提问须知

在提交issue之前,我们应该先查询是否已经有相关的issue以及常见问题。提交issue时,我们需要写明issue的原因,以及编译或运行过程的日志(加载进程以及Patch进程)。issue需要以下面的格式:

异常类型:app运行时异常/编译异常

手机型号:如:Nexus 5(如是编译异常,则可以不填)

手机系统版本:如:Android 5.0 (如是编译异常,则可以不填)

tinker版本:如:1.7.7

gradle版本:如:2.10

是否使用热更新SDK: 如 TinkerPatch SDK 或者 Bugly SDK

系统:如:Mac

堆栈/日志:
1. 如是编译异常,请在执行gradle命令时,加上--stacktrace;
2. 日志我们需要过滤"Tinker."关键字;
3. 对于合成失败的情况,请给出:patch进程的日志,这里需要将Android Moniter右上角设为No Filter。

提问题时若使用不能用/没效果/有问题/报错此类模糊表达,但又没给出任何代码截图报错的,将绝对不会有任何反馈。这种issue也是一律直接关闭的,大家可以参阅提问的智慧

Tinker是一个开源项目,希望大家遇到问题时要学会先思考,看看sample与Tinker的源码,更鼓励大家给我们提pr.

tys282000 commented 6 years ago

这里有个背景,就是ota之后用户再次启动patch之后的app的时候,因为boot.oat发生了变化,导致之前patch dex对应的oat过期,系统就会再次触发dex2oat对patch dex做全量AOT编译,此时主进程要等待dex2oat执行完才能接着执行,就会导致app启动的时候黑屏甚至aar。

于是tinker判断发生了ota之后,在patch之后的app启动时会先在主进程里手动构造命令行调用一次解释模式的dex2oat,因为解释模式的dex2oat执行时间比全量AOT要短得多(500ms~2s),所以不会导致app黑屏或anr。但此后为了避免解释模式下art vm可能存在的坑,tinker就会拉起后台进程去做真正的全量AOT的dex2oat,也就是你看到的代码了。

Logwangwei commented 6 years ago

额,大部分厂商在N的系统上都改回了解释模式,[我们也是] 从我们的手机项目跟踪的情况来看,ota之后首次启动过程dex2oat耗时:微信-10s,qq浏览器-6s; 我倒是有另一个想法,从OpenDexFilesFromOat的实现来讲,做dex2oat无非就是为了从oat_file去拿到dex_file[提供一个类查询的库],如果oat文件中没有得到这个对象就会回滚去load最原始的dex文件,所以,个人认为其实这里可以不用去call dex2oat,删除之前的oat文件,让系统去load最原始的dex文件,然后再异步做供下次使用的oat file。