Android项目APP逆向

破解某app主题皮肤

2019-06-07  本文已影响118人  好奇害死猫咪阿

前言

今天在使用一款视频app时,弹出一个对话框提示主题皮肤已经到期,想重新选一个主题时发现不是免费的。想到近来无事可做,不如就分析一下,权当练手学习了。

工具

思路分析

  1. 我们先来看一下主题选择界面


    主题界面

    对于主题皮肤这种功能,功能肯定是要放到本地的,然后每次打开app时校验一下失效时间。
    因为点击右侧的按钮之后才会有下一步的逻辑,所以就先把突破点放在这。

  2. 下一步就是直接拖入jadx反编译。大厂的app基本上不会做加固处理,除开效率不说,加固的app也是有一定几率崩溃的,所以直接反编译就行。之后在 string.xml 直接搜索文本

    字符串搜索结果
    接着全局搜索theme_action_subscribe_fmt
    字符串引用结果
    需要注意的是,jadx在反编译时会直接把smali中16进制的资源值转化为 R.string.xxx的形式,方便阅读。所以这里直接搜索16进制资源值是搜不到的。

这里的结果比较好,两个结果都源自同一个类,所以直接跟踪进去。


bl.eok$b类部分代码

这里的逻辑实际上还是比较清楚的。就是根据BiliSkin的不同状态确定具体的显示内容。实际上这个类还实现了View.OnClickListener 接口,也说明我们的思路是正确的

onClick函数部分代码

在实际使用过程中,主题列表的前两项,即少女粉夜间模式是免费的。结合这两处代码分析,比较可疑的是BiliSkinmIsFreemIsBought 两个域。


  1. 下一步就是编写Xposed模块,确认一下我们的思路。Xposed模块的编写这里就不多说了,毕竟网上资料很多。这里直接附上代码
public class Main  implements IXposedHookLoadPackage {

    @Override
    public void handleLoadPackage(XC_LoadPackage.LoadPackageParam loadPackageParam) throws Throwable {
        if (! "tv.danmaku.bili".equals(loadPackageParam.packageName)) {
            XposedBridge.log("ignore this package: " + loadPackageParam.packageName);
            return;
        }

        XposedBridge.log("start------------------->");

        XposedHelpers.findAndHookMethod("bl.eok$b", loadPackageParam.classLoader,
                "b", Object.class, new HookBiliSkinInfoMethod());
    }

    private static class HookBiliSkinInfoMethod extends XC_MethodHook {

        private static Class<?> sBiliSkinClass = null;
        private static Field sIsBiliSkinFree = null;

        @Override
        protected void beforeHookedMethod(MethodHookParam param) throws Throwable {
            XposedBridge.log("start with param: " + param.args[0]);

            if (sBiliSkinClass == null) {
                sBiliSkinClass = XposedHelpers.findClass(
                        "tv.danmaku.bili.ui.theme.api.BiliSkin",
                        param.thisObject.getClass().getClassLoader());
            }

            if (sIsBiliSkinFree == null) {
                sIsBiliSkinFree = XposedHelpers.findField(sBiliSkinClass, "mIsFree");
            }

            if (! (sBiliSkinClass.isInstance( param.args[0]))) {
                XposedBridge.log("This param is not the instance of BiliSkin, ignore");
                return;
            }

            sIsBiliSkinFree.set(param.args[0], true);
        }

        @Override
        protected void afterHookedMethod(MethodHookParam param) throws Throwable {
            XposedBridge.log("done");
        }
    }
}


  1. 重启后的效果如下图所示


    Xposed hook后主题界面

    可以看到,现在所有主题已经都可以用了。


  1. 然而关闭app,再打开时问题出现了
    主题过期对话框
    在点击确定按钮之后,app恢复成默认主题。所以下一步我们就想办法除去这个对话框。

  1. 同样的思路,在string.xml中搜索文本
    字符串搜索结果
    然后全局搜索,找到调用处
    字符串搜索结果

代码跟踪进去,很清楚的逻辑,就是创建了个Dialog监听点击事件

MainActivity部分代码

接下来就是hook掉这个方法了


XposedHelpers.findAndHookMethod("tv.danmaku.bili", loadPackageParam.classLoader,
                "d", new HookSkinExpiredMethod());

    private static class HookSkinExpiredMethod extends XC_MethodHook {

        @Override
        protected void beforeHookedMethod(MethodHookParam param) throws Throwable {
            param.setResult(null);
        }

        @Override
        protected void afterHookedMethod(MethodHookParam param) throws Throwable {

        }
    }

总结

说明

上一篇 下一篇

猜你喜欢

热点阅读