首页
论坛
课程
招聘
推荐专栏
课程评论
小想法
制作自己的插件so:
https://www.kanxue.com/include  "ida.h"

typedef  _DWORD  (*funGetObsoleteDexCache)(void  *);

//  art::ArtMethod::GetObsoleteDexCache作为a2让frida传入,比自己实现更方便
extern  "C"  int  MyGetDexFile(void  *a1,  void  *a2)  {
        int  result;

        if  ((*((_DWORD  *)  a1  +  1)  &  0x40000)  !=  0)  {
                funGetObsoleteDexCache  fDexCache  =  (funGetObsoleteDexCache)  a2;
                result  =  *(_DWORD  *)  ((_DWORD)  fDexCache(a1)  +  16);
        }  else  {
                result  =  *(_DWORD  *)  (*(_DWORD  *)  (*(_DWORD  *)  a1  +  16)  +  16);
        }
        return  result;
}

frida调用:
function  main()  {
        Java.perform(function  ()  {
                var  module_libext  =  null;
                if  (Process.arch  ===  "arm64")  {
                        module_libext  =  Module.load("/data/local/tmp/libnative-lib64.so");
                }  else  if  (Process.arch  ===  "arm")  {
                        module_libext  =  Module.load("/data/local/tmp/libnative-lib.so");
                }

                //获得GetObsoleteDexCache函数地址
                var  addrGetObsoleteDexCache;
                var  symbols  =  Module.enumerateSymbolsSync("libart.so");
                for  (var  i  =  0;  i  <  symbols.length;  i++)  {
                        var  symbol  =  symbols[i];
                        if  (symbol.name.indexOf("ArtMethod")  >=  0  &&  symbol.name.indexOf("GetObsoleteDexCache")  >=  0)  {
                                addrGetObsoleteDexCache  =  symbol.address;
                                break;
                        }
                }

                var  MyGetDexFile  =  module_libext.getExportByName("MyGetDexFile");
                var  funcMyGetDexFile  =  new  NativeFunction(MyGetDexFile,  "pointer",  ["pointer",  'pointer']);

                var  jnienv  =  Java.vm.getEnv();
                var  myclass  =  Java.use("com.sup.android.base.MainActivity").class;
                var  method  =  myclass.getDeclaredMethods();
                method  =  method[0];  //任意函数art_method都可GetDexFile()
                var  ArtMethodptr  =  jnienv.fromReflectedMethod(ptr(method.$h));
                var  DexFileptr  =  funcMyGetDexFile(ptr(ArtMethodptr),  ptr(addrGetObsoleteDexCache));
                dump(DexFileptr);
        })
}

function  dump(Dexfile)  {
        var  begin  =  ptr(Dexfile).add(Process.pointerSize).readPointer();
        var  size  =  ptr(Dexfile).add(2  *  Process.pointerSize).readU32();

        console.log(hexdump(begin))
        console.log(size);
        var  file  =  new  File("/sdcard/getDexFile.dex",  "w");
        file.write(begin.readByteArray(size));
        file.flush();
        file.close();
}
chocolate_961272
@Roger  哥哥好,求更新进阶教程呀哥哥。
小想法
用frida通过mCookie拿到DexFile:
function  useJni()  {
        Java.perform(function  ()  {
                Java.choose("dalvik.system.DexFile",  {
                        onMatch:  function  (object)  {
                                try  {
                                        var  myenv  =  Java.vm.getEnv();
                                        var  size  =  myenv.getArrayLength(mcookie.$h);
                                        var  longarrry  =  myenv.getLongArrayElements(mcookie.$h);

                                        for  (let  n  =  1;  n  <  size;  n++)  {  //0不是dex,从1开始才是dex
                                                var  mydexfile  =  ptr(longarrry).add(8  *  n).readPointer();  //这里为什么不是(Process.pointerSize*n)?因为mylong是long[],其pointerSize是8,而不是Process.pointerSize
                                                var  begin  =  ptr(mydexfile).add(Process.pointerSize).readPointer();
                                                var  size  =  ptr(mydexfile).add(Process.pointerSize  *  2).readU32();
                                                dump(begin,  size);
                                        }
                                }  catch  (e)  {
                                        console.log(e)
                                }
                        }
                });
        });
}

function  UseFridaApi()  {
        Java.perform(function  ()  {
                Java.choose("dalvik.system.DexFile",  {
                        onMatch:  function  (object)  {
                                try  {
                                        var  mcookie  =  object.mCookie.value;
                                        var  mylong  =  Java.array('long',  mcookie);
                                        console.log("DexFile地址数组:"+  JSON.stringify(mylong));

                                        for  (var  n  in  mylong)  {
                                                if  (n  >  0)  {      //0不是dex,从1开始才是dex
                                                        var  dexfileptr  =  ptr(mylong[n])
                                                        var  mydexfile  =  ptr(dexfileptr).add(8  *  n).readPointer();  //这里为什么不是(Process.pointerSize*n)?因为mylong是long[],其pointerSize是8,而不是Process.pointerSize
                                                        var  begin  =  ptr(mydexfile).add(Process.pointerSize).readPointer();
                                                        var  size  =  ptr(mydexfile).add(Process.pointerSize  *  2).readU32();
                                                        dump(begin,  size);
                                                }
                                        }
                                }  catch  (e)  {
                                        console.log(e)
                                }
                        }
                });
        });
}

function  dump(begin,  size)  {
        var  path  =  "/sdcard/"  +  size  +  ".dex";
        var  file  =  new  File(path,  "w");
        file.write(ptr(begin).readByteArray(size));
        file.flush();
        file.close();
        console.log("dump  success  "  +  size  +  ".dex")
}

frida主动调用Native案例:
function  main()  {
        var  dlopen  =  Module.findExportByName(null,  "android_dlopen_ext");

        Interceptor.attach(dlopen,  {
                onEnter:  function  (arg)  {
                        var  name  =  ptr(arg[0]).readCString();
                        if  (name.indexOf("libnative-lib.so")  >=  0)  {
                                console.log(name)
                                this.name  =  name;
                        }
                },
                onLeave:  function  (ret)  {
                        if  (this.name  !=  undefined)  {
                                //int  myfunc2(int  a)
                                var  func2  =  Module.findExportByName("libnative-lib.so",  "myfunc2");
                                func2  =  new  NativeFunction(func2,  'int',  ['int']);
                                console.log(func2(1));

                                //const  char*  myfunc3(const  char*  a)
                                var  func3  =  Module.findExportByName("libnative-lib.so",  "myfunc3");
                                func3  =  new  NativeFunction(func3,  'pointer',  ['pointer']);
                                var  mystr  =  Memory.alloc(100).writeUtf8String("func3  xxxxxxx");
                                console.log(func3(mystr).readCString());

                                //jbyte*  myfunc4(jbyte*  a)
                                var  func4  =  Module.findExportByName("libnative-lib.so",  "myfunc4");
                                func4  =  new  NativeFunction(func4,  'pointer',  ['pointer']);
                                var  b  =  [0x81,  0x99,  0xff,  0x7d];
                                mystr  =  Memory.alloc(100).writeByteArray(b);
                                console.log(hexdump(func4(mystr)));

                                //替换函数  const  char*  func5() 
                                var  func5  =  Module.findExportByName("libnative-lib.so",  "func5");
                                func5  =  new  NativeFunction(func5,  'pointer',  []);
                                Interceptor.replace(func5,  new  NativeCallback(function  ()  {
                                        var  str  =  Memory.alloc(10).writeUtf8String("hhhhhh");
                                        return  str;
                                },  'pointer',  []));
                        }
                }
        });
}
合作伙伴