--------- beginning of crash
2021-09-07 17:48:10.877 25905-25905/xxx.xxx.xxx E/AndroidRuntime: FATAL EXCEPTION: main
Process: xxx.xxx.xxx, PID: 25905
java.lang.RuntimeException: Unable to instantiate application xxx.xxx.xxx.base.BaseApplication: java.lang.ClassNotFoundException: Didn't find class "xxx.xxx.xxx.base.BaseApplication" on path: DexPathList[[zip file "/data/app/xxx.xxx.xxx/base.apk"],nativeLibraryDirectories=[/data/app/xxx.xxx.xxx/lib/arm64, /data/app/xxx.xxx.xxx/base.apk!/lib/arm64-v8a, /system/lib64, /vendor/lib64]]
at android.app.LoadedApk.makeApplication(LoadedApk.java:846)
at android.app.ActivityThread.handleBindApplication(ActivityThread.java:5850)
at android.app.ActivityThread.-wrap3(ActivityThread.java)
at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1699)
at android.os.Handler.dispatchMessage(Handler.java:102)
at android.os.Looper.loop(Looper.java:154)
at android.app.ActivityThread.main(ActivityThread.java:6682)
at java.lang.reflect.Method.invoke(Native Method)
at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:1520)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:1410)
Caused by: java.lang.ClassNotFoundException: Didn't find class "xxx.xxx.xxx.base.BaseApplication" on path: DexPathList[[zip file "/data/app/xxx.xxx.xxx/base.apk"],nativeLibraryDirectories=[/data/app/xxx.xxx.xxx/lib/arm64, /data/app/xxx.xxx.xxx/base.apk!/lib/arm64-v8a, /system/lib64, /vendor/lib64]]
at dalvik.system.BaseDexClassLoader.findClass(BaseDexClassLoader.java:56)
at java.lang.ClassLoader.loadClass(ClassLoader.java:380)
at java.lang.ClassLoader.loadClass(ClassLoader.java:312)
at android.app.Instrumentation.newApplication(Instrumentation.java:1000)
at android.app.LoadedApk.makeApplication(LoadedApk.java:835)
at android.app.ActivityThread.handleBindApplication(ActivityThread.java:5850)
at android.app.ActivityThread.-wrap3(ActivityThread.java)
at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1699)
at android.os.Handler.dispatchMessage(Handler.java:102)
at android.os.Looper.loop(Looper.java:154)
at android.app.ActivityThread.main(ActivityThread.java:6682)
at java.lang.reflect.Method.invoke(Native Method)
at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:1520)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:1410)
Suppressed: java.io.IOException: Failed to open dex files from /data/app/xxx.xxx.xxx/base.apk because: Failed to open dex file '/data/app/xxx.xxx.xxx/base.apk' from memory: Unrecognized version number in /data/app/xxx.xxx.xxx/base.apk: 0 3 9
at dalvik.system.DexFile.openDexFileNative(Native Method)
at dalvik.system.DexFile.openDexFile(DexFile.java:373)
at dalvik.system.DexFile.<init>(DexFile.java:113)
at dalvik.system.DexFile.<init>(DexFile.java:78)
at dalvik.system.DexPathList.loadDexFile(DexPathList.java:359)
at dalvik.system.DexPathList.makeElements(DexPathList.java:323)
at dalvik.system.DexPathList.makeDexElements(DexPathList.java:263)
at dalvik.system.DexPathList.<init>(DexPathList.java:126)
at dalvik.system.BaseDexClassLoader.<init>(BaseDexClassLoader.java:48)
at dalvik.system.PathClassLoader.<init>(PathClassLoader.java:64)
at com.android.internal.os.PathClassLoaderFactory.createClassLoader(PathClassLoaderFactory.java:43)
at android.app.ApplicationLoaders.getClassLoader(ApplicationLoaders.java:58)
at android.app.LoadedApk.createOrUpdateClassLoaderLocked(LoadedApk.java:535)
at android.app.LoadedApk.getClassLoader(LoadedApk.java:568)
at android.app.ActivityThread.getTopLevelResources(ActivityThread.java:2042)
at android.app.LoadedApk.getResources(LoadedApk.java:787)
at android.app.ContextImpl.<init>(ContextImpl.java:2262)
at android.app.ContextImpl.createAppContext(ContextImpl.java:2206)
at android.app.ContextImpl.createAppContext(ContextImpl.java:2192)
at android.app.ActivityThread.handleBindApplication(ActivityThread.java:5767)
... 8 more
现象:
在6.0~8.0系统的手机上进入app闪退。部分手机无法正常安装提示未签名,签名证书问题
排查步骤:
1.远程jenkins同样的分支构建出来的apk正常,本地android Studio 构建出来的apk有以上问题。本地打包后针对具体崩溃的机型,通过云真机验证是否可以必现
2.远程jenkins同分支构建出来的apk,在同一款云真机上是否可以必现
3.检查dex 0 3 9 的和含义 见[引用10链接]
问题定位:
4.通过关键词搜索到,见[引用11链接],几种可能出现问题的场景,
检索到的其他原因:jdk环境不匹配,检查后发现jdk不一致。统一jdk后未解决
5.反编译apk后检查dex文件后发现BaseApplication类,并非不存在。 通过4~9源码可以梳理出来。
问题发生在 makeApplication(boolean forceDefaultAppClass,Instrumentation instrumentation) 方法内。
创建Application 过程中,通过classLoader加载指定的Applicaiton类路径进行初始化Application对象抛出 ClassNotFoundException 需要加载的类在Dex中存在,classLoader 无法找到?!是不是指定的dex路径不存在,或者HotSwap 缓存导致。
复现:
1.通过多次更改BaseApplication 代码出包。模拟HotSwap 缓存问题
2.关闭HotSwap,多次更改是否可以复现
3.adb 连接 9.0 及以上的手机进行增量代码更新。使用build 出来的apk,安装在低于9.0系统的手机上。必现该问题。
梳理:
Android studio 默认开启代码热更来减少编译apk时间。早期称为Instant run。该功能会附带一些坏的影响。
进入File–Setting–Build,Execution,Deploymeng–hotSwap,可以看到,关于开启HotSwap的影响说明。
May cause serialization issue in the debugged application,(开启后会对序列化有影响之类),并且会出现
某一个类无法找到问题。避免类似问题出现,有几种处理方式。最简单的是关闭hotswap 开关。或者每次编译前,关闭上一次构建缓存
。用gradle脚本编译也可以
引用路径:
1.https://www.jianshu.com/p/bf1c1c594cfa Android Studio升级3.5后,Instant Run去哪了?
2.https://www.jianshu.com/p/a620e368389a Android动态加载之ClassLoader详解
3.https://docs.gradle.org/current/userguide/performance.html#parallel_execution 提高 Gradle 构建的性能
4.https://source.android.google.cn/setup/develop?hl=zh-cn androidSource 5.https://www.androidos.net.cn/androidossearch?query=LoadedApk 6.https://www.androidos.net.cn/android/9.0.0_r8/xref/frameworks/base/core/java/android/app/LoadedApk.java# 7.https://www.androidos.net.cn/android/9.0.0_r8/xref/frameworks/base/core/java/android/app/AppComponentFactory.java 8.https://www.androidos.net.cn/android/9.0.0_r8/xref/frameworks/base/core/java/android/app/Instrumentation.java
9.https://www.androidos.net.cn/android/9.0.0_r8/xref/frameworks/base/core/java/android/app/ActivityThread.java 10.https://source.android.com/devices/tech/dalvik/dex-format dex格式
11.https://stackoverflow.com/questions/41223502/failed-to-open-dex-file-unrecognized-version-number [Failed to open dex file, unrecognized version number]