记一次BUG查找

缘起

[#1314729 java.lang.NullPointerException]
Attempt to invoke virtual method 'void android.webkit.WebView.loadUrl(java.lang.String)' on a null object reference
com.hao.ad.e.e$1.run(FragmentHelper.java:22)

很明显,就是一个普通的空指针异常,但是不同之处在于反编译出来的包里面竟然找不到com.hao.ad这个包,公司开发组一直也没有解决掉这个问题。

发展

本人接到任务,优化APP的启动,在Profiler中又再次发现了这个奇怪的包,关键是他的启动占据了我们宝贵的UI线程接近1s的时间:

com.hao.ad启动占据1S的宝贵时间

可以推测com.hao.ad是通过context获取到mainLooper,再构造一个handler绑定mainLooper,最后在通过handler.post(runnable)的方式,将他的代码运行到UI线程的。

初见

通过经典的二分查找,在众多第三方库中找到了MainSDK.init(context,···)这个函数,将其注释掉之后发现启动的trace中就没有com.hao.ad这个包的运行代码了。到这里问题就解决了,召集产品确认是否把这个SDK关掉就万事大吉了。

深入

作为码农的我怎么能放弃这次学习的机会呢,必然要到源码里一探究竟的:

// NoeSdk_1_5.0.0.jar!/com/boh/ejskhc/MainSDK.class
class MainSDK extends Thread(){
    // ···
    (new MainSDK()).start();
    // ···
}

可见,完美符合预期,的确是在一个线程中跑的,那么怎么post到UI线程的呢,在他的包里面继续寻找:

// NoeSdk_1_5.0.0.jar!/com/boh/ejskhc/h.class
Runnable var5 = new Runnable() {
                    public final void run() {
                        try {
                            h.a;
                            int var1x = (new f(i.b(var2.a))).a(var2, var1);
                            com.tao.admin.loglib.b.a(com.tao.admin.loglib.a.a().d() ? ": ".concat(String.valueOf(var1x)) : "");
                        } catch (Exception var2x) {
                        }
                    }
                };
                b.submit(var5);

再一次完美的对应上预期了,注意到这里有一段拼接字符串的操作,难不成是拼接com.hao.ad?继续探究下代码,就从var1x出发:

// NoeSdk_1_5.0.0.jar!/com/boh/ejskhc/f.class
static String b(int var0) {
        return "m" + var0 + ".jar";
    }
f(String var1) throws NullPointerException {
        var1 = MainSDK.a().getFilesDir().getAbsolutePath() + "/" + var1;
        this.a = new File(var1);
    }

又一次对上了,通过拼接了一个绝对路径/m数字.jar字符串打开了一个jar包,那么就应该出现DexClassLoader来记载这个包,继续寻找:

// NoeSdk_1_5.0.0.jar!/com/boh/ejskhc/f.class
  File var3 = MainSDK.a().getDir("dex", 0);
            Class var6;
            Object var7 = (var6 = (new DexClassLoader(this.a.toString(), var3.getAbsolutePath(), (String)null, ClassLoader.getSystemClassLoader().getParent())).loadClass(var1.d + "." + var1.e)).newInstance();
            Class[] var4;
            (var4 = new Class[2])[0] = Context.class;
            var4[1] = Map.class;
            return (Integer)var6.getMethod("load", var4).invoke(var7, MainSDK.a(), var2);

完美!基本确认就是这个问题了,还差最后一步,找到这个绝对路径/m数字.jar,给本次侦探盖棺定论!

反击

导出所有位于我们/data/data/包名/目录下的文件,寻找m数字.jar这个文件:

导出包名下所有文件

经过查找,找到了两个名称符合的文件m1.jar&&m7.jar
对这两个文件进行反编译,查看里面的dex文件:
m7.har中包含com.hao.ad

完美!

结案

抓贼要抓脏,一步步分析下来确认了就是这个第三方合作的SDK偷偷运行线程动态添加dex文件,并且把代码post到UI线程,不仅拖慢了我们APP的启动,还不定时的报一个崩溃!

总结

本次探案过程用到了这些相关工具好相关知识:

  1. profiler,启动过程分析
  2. DexClassLoader,动态dex加载
  3. 反射
  4. 二分查找
  5. adb相关
  6. apktool
最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 212,657评论 6 492
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 90,662评论 3 385
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 158,143评论 0 348
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 56,732评论 1 284
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 65,837评论 6 386
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 50,036评论 1 291
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 39,126评论 3 410
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 37,868评论 0 268
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 44,315评论 1 303
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 36,641评论 2 327
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 38,773评论 1 341
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 34,470评论 4 333
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 40,126评论 3 317
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 30,859评论 0 21
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 32,095评论 1 267
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 46,584评论 2 362
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 43,676评论 2 351