重载ClassLoader一个构造方法给BaseDexClass

2020-01-11  本文已影响0人  修符道人

最近,在研究Android的dex加载相关的源码,想在DexClassLoader、BaseDexClassLoader、ClassLoader加点日志。但是日志又不能直接加,得通过dexPath限制一下,否则系统起不来,因为ClassLoader会被频繁调用。

BaseDexClassLoader

源码目录:libcore/dalvik/src/main/java/dalvik/system
编译目录:libcore


basedex.jpg

ClassLoader

源码目录:libcore/libdvm/src/main/java/java/lang
编译目录:libcore


classloader.jpg

编译

image.png

我想着,是不是BaseDexClassLoader和ClassLoader不能同时修改,我先把BaseDexClassLoader保持不修改(使用原来的不带dexPath的super方法),编译一次之后,再修改。结果还是如此。

是不是由于构造方法的特殊性导致编译不通过呢?我尝试着在ClassLoader里新增个方法,BaseDexClassLoader仍然一样无法调用。

所以,上面的问题的本质归结为:同一目录下,两个Java类A和B,假如B增加个方法,A引用B的这个方法,编译不通过,报A找不到B的这个方法。
百度了半天也没有任何的资料说明相关的问题,只有自己一点点试探了。

模拟最简单的场景

https://www.jianshu.com/p/8b77c62273c0,这里正常生成Jar包。可见是libcore的特定环境导致了编译失败。

问题终于解决

搞了好几天,终于明白了,看编译日志是编译core-libart.jar包,是art!!!
而ClassLoader有两个类:

image.png
我只改了libdvm下的ClassLoader,而现在编译的是core-libart.jar,所以把两个目录下的ClassLoader都改一下就好了。
但是,发现安装app的时候,安装不上去,报错:
I/dalvikvm( 2564): java.lang.NullPointerException:

I/dalvikvm( 2564):  at java.util.logging.Logger.log(Logger.java:1036)

I/dalvikvm( 2564):  at java.util.logging.Logger$1.publish(Logger.java:81)

I/dalvikvm( 2564):  at java.util.logging.Logger.log(Logger.java:924)

I/dalvikvm( 2564):  at java.util.logging.Logger.warning(Logger.java:853)

I/dalvikvm( 2564):  at dalvik.system.DexFile.log(DexFile.java:93)

I/dalvikvm( 2564):  at dalvik.system.DexFile.openDexFile(DexFile.java:315)

I/dalvikvm( 2564):  at dalvik.system.DexFile.<init>(DexFile.java:82)

I/dalvikvm( 2564):  at dalvik.system.DexFile.<init>(DexFile.java:61)

I/dalvikvm( 2564):  at dalvik.system.DexPathList.loadDexFile(DexPathList.java:263)

在ClassLoader里引用Logger打日志,就会报上面的错误。所以把Logger里加个null判断。


log.jpg
上一篇 下一篇

猜你喜欢

热点阅读