美文网首页
每日优鲜mfsig分析及unidbg实现

每日优鲜mfsig分析及unidbg实现

作者: ever_hu | 来源:发表于2021-12-25 17:15 被阅读0次

每日优鲜mfsig分析及unidbg实现

环境

app:9.7.0

由于这个版本实在太古老了,打开就提示更新,而且似乎有时会使用mfsig,有时又没有,所以如果抓不到有mfsig的包可以尝试清除数据再打开app。

Java层

image-20211225164251518 image-20211225164231950

即使是这么古老的app,它也是加壳了,可以使用BlackDex脱壳,然后搜索mfsig。然后没有搜索到结果。

改用frida_hook_libarthook_art.js,注释掉其他模块,只保留NewStringUTF,把输出重定向到文件。

frida -U -f cn.missfresh.application -l hook_art.js --no-pause > miss.log

尝试搜索mfsnm

image

可以看到是在libsign.so中生成的,调用的函数似乎是静态注册的,Java层对应的函数是cn.missfresh.wsg.SecurityLib.nativeSign,jadx打开查看

image-20211225002036055

尝试hook这个函数

function hook_sign() {
    var String = Java.use("java.lang.String");
    var Util = Java.use("cn.missfresh.wsg.SecurityLib");
    Util.nativeSign.implementation = function(ctx, j, bArr) {
        console.log("j:", j);
        console.log("bArr:", String.$new(bArr));
        var ret = this.nativeSign(ctx, j, bArr);
        console.log("ret:", ret);
        return ret;
    }
}

function searchClassLoader(className) {
    Java.enumerateClassLoaders({
        onMatch: function (loader) {
            try {
                if (loader.findClass(className)) {
                    Java.classFactory.loader = loader;
                    console.log("find", loader);
                }
            } catch (error) {
            }
        }, 
        onComplete: function () {
            console.log("finish search");
        }
    })
}


function main(){
    Java.perform(function() {
        searchClassLoader("cn.missfresh.wsg.SecurityLib");
        hook_sign();
    })
}

setTimeout(main, 5000);
image-20211225163003537

可以看到输入是时间戳和请求参数。

unidbg实现

package com.missfresh;

import com.github.unidbg.AndroidEmulator;
import com.github.unidbg.Module;
import com.github.unidbg.linux.android.AndroidEmulatorBuilder;
import com.github.unidbg.linux.android.AndroidResolver;
import com.github.unidbg.linux.android.dvm.*;
import com.github.unidbg.linux.android.dvm.array.ByteArray;
import com.github.unidbg.memory.Memory;
import com.github.unidbg.virtualmodule.android.AndroidModule;

import java.io.File;
import java.nio.charset.StandardCharsets;
import java.util.ArrayList;
import java.util.List;

public class MissFresh  extends AbstractJni {
    private final AndroidEmulator emulator;
    private final VM vm;
    private final Module module;

    public static String pkgName = "cn.missfresh.application";
    public static String apkPath = "unidbg-android/src/test/java/com/missfresh/meiriyouxian9.7.0.apk";
    public static String soPath = "unidbg-android/src/test/java/com/missfresh/libsign.so";

    public MissFresh() {
        emulator = AndroidEmulatorBuilder.for32Bit().setProcessName(pkgName).build();
        final Memory memory = emulator.getMemory();
        memory.setLibraryResolver(new AndroidResolver(23));
        vm = emulator.createDalvikVM(new File(apkPath));
        new AndroidModule(emulator, vm).register(memory);
        vm.setVerbose(true);
        DalvikModule dm = vm.loadLibrary(new File(soPath), true);
        vm.setJni(this);

        dm.callJNI_OnLoad(emulator);
        module = dm.getModule();
    }

    public void call_sign() {
        List<Object> list = new ArrayList<>(10);
        list.add(vm.getJNIEnv());
        list.add(0);
        list.add(vm.addLocalObject(vm.resolveClass("android/content/Context").newObject(null)));
        list.add(1640187039566L);
        list.add(vm.addLocalObject(new ByteArray(vm, "version9.7.0tdkeyJvcyI6ImFuZHJvaWQiLCJ2ZXJzaW9uIjoiMy4xLjkiLCJwYWNrYWdlcyI6ImNuLm1pc3NmcmVzaC5hcHBsaWNhdGlvbiomOS43LjAiLCJwcm9maWxlX3RpbWUiOjI4MywiaW50ZXJ2YWxfdGltZSI6MTQ5NjksInRva2VuX2lkIjoiajViSUs1SmV1bUxzZUVWMVptb3ZxNHNzT0J4OXBCUlJsNk9kbzRlQ01iemZWNWNlUmswSjZYK2lLWE4rVkdJQ3N5S1V0MFByS1lHSE5tMm5iSlZIOHc9PSJ9source_device_id359906070748939sessionandroid0.95648171296963921640187024465screen_width1440screen_height2560realVersionplatformandroidisShow0imeifbc64376480ee60e43e933dae0258d3fdevtka3JZZ1NRVzNZWW9ZMERIVDFvQmJ6MytoVkxsQWJuV1RnLzV2MnpXYVZGUTFqN09zUFIzeFd6WWo3dkNsb0J4MEY2Q1FGeTZhZXpQaA0KdFlZWXAzQkxicmxiTm5rejE0SEt5UE84UVpWOXdWRUxJem0rd0ZiV2QzVks4cFphMmphQWJFYmJrK3dFQXRCL1N6eEtXNmp3eHc9PQ==device_id359906070748939currentLng113.97177currentLat22.540642android_id581e0c22a2843d73android_channel_valuept-lingdu002access_tokenSM_Device_ID2021120821500831e6fbaf8244fa2c94916c1cfe02a8a701cd5c98e2bbb3dc".getBytes(StandardCharsets.UTF_8))));
        Number result = module.callFunction(emulator, 0x38bf4+1, list.toArray())[0];
        System.out.println("result:" + vm.getObject(result.intValue()).getValue().toString());
    }

    public static void main(String[] args) {
        MissFresh test = new MissFresh();
        test.call_sign();
    }
}
image-20211225164649870

没结果。。。不过我们在Java层看到除了nativeSign外还有个函数nativeInit,应该需要先调用它,它的输入可以通过hook查看。

public void call_init() {
    List<Object> list = new ArrayList<>(10);
    list.add(vm.getJNIEnv());
    list.add(0);
    list.add(vm.addLocalObject(vm.resolveClass("android/content/Context").newObject(null)));
    list.add(vm.addLocalObject(new StringObject(vm, "01000002")));
    Number result = module.callFunction(emulator, 0x38bb4+1, list.toArray())[0];
    System.out.println("init:"+result.intValue());
}
public static void main(String[] args) {
    MissFresh test = new MissFresh();
    test.call_init();
    test.call_sign();
}

重新运行

image-20211225164924693

报错了,补个环境

@Override
public DvmObject<?> callObjectMethodV(BaseVM vm, DvmObject<?> dvmObject, String signature, VaList vaList) {
    switch (signature) {
        case "android/content/Context->getAssets()Landroid/content/res/AssetManager;": {
            return vm.resolveClass("android/content/res/AssetManager").newObject(signature);
        }
    }
    return super.callObjectMethodV(vm, dvmObject, signature, vaList);
}

重新运行

image-20211225165026197

和抓包结果一致。

代码实现

package com.missfresh;

import com.github.unidbg.AndroidEmulator;
import com.github.unidbg.Module;
import com.github.unidbg.linux.android.AndroidEmulatorBuilder;
import com.github.unidbg.linux.android.AndroidResolver;
import com.github.unidbg.linux.android.dvm.*;
import com.github.unidbg.linux.android.dvm.array.ByteArray;
import com.github.unidbg.memory.Memory;
import com.github.unidbg.virtualmodule.android.AndroidModule;

import java.io.File;
import java.nio.charset.StandardCharsets;
import java.util.ArrayList;
import java.util.List;

public class MissFresh  extends AbstractJni {
    private final AndroidEmulator emulator;
    private final VM vm;
    private final Module module;

    public static String pkgName = "cn.missfresh.application";
    public static String apkPath = "unidbg-android/src/test/java/com/missfresh/meiriyouxian980.apk";
    public static String soPath = "unidbg-android/src/test/java/com/missfresh/libsign980.so";

    public MissFresh() {
        emulator = AndroidEmulatorBuilder.for32Bit().setProcessName(pkgName).build();
        final Memory memory = emulator.getMemory();
        memory.setLibraryResolver(new AndroidResolver(23));
        vm = emulator.createDalvikVM(new File(apkPath));
        new AndroidModule(emulator, vm).register(memory);
        vm.setVerbose(true);
        DalvikModule dm = vm.loadLibrary(new File(soPath), true);
        vm.setJni(this);

        dm.callJNI_OnLoad(emulator);
        module = dm.getModule();
    }

    @Override
    public DvmObject<?> callObjectMethodV(BaseVM vm, DvmObject<?> dvmObject, String signature, VaList vaList) {
        switch (signature) {
            case "android/content/Context->getAssets()Landroid/content/res/AssetManager;": {
                return vm.resolveClass("android/content/res/AssetManager").newObject(signature);
            }
        }
        return super.callObjectMethodV(vm, dvmObject, signature, vaList);
    }

    public void call_init() {
        List<Object> list = new ArrayList<>(10);
        list.add(vm.getJNIEnv());
        list.add(0);
        list.add(vm.addLocalObject(vm.resolveClass("android/content/Context").newObject(null)));
        list.add(vm.addLocalObject(new StringObject(vm, "01000002")));
        Number result = module.callFunction(emulator, 0x38bb4+1, list.toArray())[0];
        System.out.println("init:"+result.intValue());
    }

    public void call_sign() {
        List<Object> list = new ArrayList<>(10);
        list.add(vm.getJNIEnv());
        list.add(0);
        list.add(vm.addLocalObject(vm.resolveClass("android/content/Context").newObject(null)));
        list.add(1640187039566L);
        list.add(vm.addLocalObject(new ByteArray(vm, "version9.7.0tdkeyJvcyI6ImFuZHJvaWQiLCJ2ZXJzaW9uIjoiMy4xLjkiLCJwYWNrYWdlcyI6ImNuLm1pc3NmcmVzaC5hcHBsaWNhdGlvbiomOS43LjAiLCJwcm9maWxlX3RpbWUiOjI4MywiaW50ZXJ2YWxfdGltZSI6MTQ5NjksInRva2VuX2lkIjoiajViSUs1SmV1bUxzZUVWMVptb3ZxNHNzT0J4OXBCUlJsNk9kbzRlQ01iemZWNWNlUmswSjZYK2lLWE4rVkdJQ3N5S1V0MFByS1lHSE5tMm5iSlZIOHc9PSJ9source_device_id359906070748939sessionandroid0.95648171296963921640187024465screen_width1440screen_height2560realVersionplatformandroidisShow0imeifbc64376480ee60e43e933dae0258d3fdevtka3JZZ1NRVzNZWW9ZMERIVDFvQmJ6MytoVkxsQWJuV1RnLzV2MnpXYVZGUTFqN09zUFIzeFd6WWo3dkNsb0J4MEY2Q1FGeTZhZXpQaA0KdFlZWXAzQkxicmxiTm5rejE0SEt5UE84UVpWOXdWRUxJem0rd0ZiV2QzVks4cFphMmphQWJFYmJrK3dFQXRCL1N6eEtXNmp3eHc9PQ==device_id359906070748939currentLng113.97177currentLat22.540642android_id581e0c22a2843d73android_channel_valuept-lingdu002access_tokenSM_Device_ID2021120821500831e6fbaf8244fa2c94916c1cfe02a8a701cd5c98e2bbb3dc".getBytes(StandardCharsets.UTF_8))));
        Number result = module.callFunction(emulator, 0x38bf4+1, list.toArray())[0];
        System.out.println("result:" + vm.getObject(result.intValue()).getValue().toString());
    }

    public static void main(String[] args) {
        MissFresh test = new MissFresh();
        test.call_init();
        test.call_sign();
    }
}

代码仅供把玩。

相关文章

网友评论

      本文标题:每日优鲜mfsig分析及unidbg实现

      本文链接:https://www.haomeiwen.com/subject/mkgdqrtx.html