精华内容
参与话题
问答
  • frida

    2020-12-09 17:33:05
    文章目录1.基本理解2.基本流程2.1 hook java方法汇总2.1.1 hook 重载函数使用overload2.1.2 hook构造函数用$init2.1.3 hook 内部类用$2.1.4 hook 生成对象使用$new2.1.5 hook 静态变量(属性)用...frida是一个优秀...

    1.基本理解

    frida是一个优秀的跨系统、跨平台的开源注入框架,既能hook java层,也能hook native层,而且安装简单便捷。不过局限性是手机要root权限。
    动态注入与hook都会修改目标程序的运行行为,但它们最大的区别在于:使用hook框架对程序hook后,会修改原方法或函数的指针,让其转去执行hook的方法,而动态注入则通过进程读写技术将一段代码或程序写到目标程序的内存空间,然后修改目标程序的指令指针,让加载代码得以执行。

    2.基本流程

    frida安装网上有安装教程
    本文主要叙述python+js式hook;

    import frida
    import sys
    
    # hook逻辑脚本;有时候会单独写个js脚本,然后文件读取(最好别有汉字);
    jscode=open('file.js').read()
    
    #连接usb设备
    redv = frida.get_usb_device()    
    # 注入进程,attach传入进程名称(字符串)或者进程号(整数)
    session = frida.attach("进程名称")
    script = session.create_script(jscode)
    
    
    # 接收脚本信息的回调函数
    # message是一个对象,type属性为send则表示send函数发送的信息,其内容在payload里
    # 下面这个on_message函数可以做固定用法,一般无需改动,当然也可直接打印message看看里边的内容
    def on_message(message, data):
        if message['type'] == 'send':
            print("[*]{0}".format(message['payload']))
        elif :
            print(message)
    # 应该是设置message事件的回调函数
    script.on('message', on_message)
    # 加载hook脚本
    script.load()
    #卸载脚本,如果只想运行一次就修改参数可能需要卸载脚本
    #定义一个全局变量判断是否得到自己想要的结果;global定义
    #script.unload()
    # 保持主线程不结束(也可以使用time.sleep循环)
    sys.stdin.read()
    
    
    

    上面的脚本一般不需要变动,真正需要改动的在file.js里面;

    #因为hookjava方法;外层要进行封装;
    Java.perform(function(){
    	#里面写包名.类名
        var tblives= Java.use('com.taobao.taolive.room.ui.chat.ChatController');
    	#写方法名;function里面输入参数也可以不写用arguments传入
    	#方法体里面才是真正需要改动的东西;每当程序执行这个方法,就会被frida勾住,执行下面的程序块
    	#
        tblives.setupChatTopMessage.implementation=function(a,b) {
            #js里面打印,python获取不到
            console.log(" start hook");
            console.log(" a:",a);
            console.log(" b:",b);
            #send方法也是输出,但是会经过回调函数到python脚本里面,可以对结果进行调用
            send(a)
            
    		#下面相当于还是执行的原方法的逻辑,没做改动
            var abc = this.setupChatTopMessage(a,b);
            return abc;
    
            }
            
        })
    ;
    

    2.1 hook java方法汇总

    2.1.1 hook 重载函数使用overload

    var   tblives= Java.use('com.taobao.taolive.room.ui.chat.ChatTopMessage');  
    #这个是构造函数的重载
    tblives.$init.overload("int","java.lang.String","java.lang.String","com.taobao.taolive.sdk.adapter.message.TLiveMsg").implementation=function(a,b,c,d) {}
    

    2.1.2 hook构造函数用$init

    代码见上

    2.1.3 hook 内部类用$

    #类里面又定义了一个类
    var inInnerClass = Java.use('ese.xposedtest.MainActivity$inInnerClass');
    

    2.1.4 hook 生成对象使用$new

    const JavaString = Java.use('java.lang.String');
    var exampleString1 = JavaString.$new('Hello World, this is an example string in Java.');
    console.log('[+] exampleString1: ' + exampleString1);
    
    

    2.1.5 hook 静态变量(属性)用反射的方法

    在这里插入代码片
    

    3. 进阶教学

    主要是对frida的应用

    3.1 打印动态加载的插件

    Java.perform(function(){
    		#加载jar/apk/dex
            var dexclassLoader = Java.use("dalvik.system.DexClassLoader");
            dexclassLoader.$init.implementation = function(dexPath,optimizedDirectory,librarySearchPath,parent) {
                #dex路径
                console.log("dexPath:" + dexPath);
                #输出优化后的dex文件
                console.log("optimizedDirectory:" + optimizedDirectory);
                #动态库路径
                console.log("librarySearchPath:" + librarySearchPath);
                #制定父类加载器
                console.log("parent:" + parent);
    
                this.$init(dexPath, optimizedDirectory, librarySearchPath, parent);
            }
            console.log("down!");
    
    });
    

    3.2打印native方法在so的位置偏移

    
    var ishook_libart = false;
    
    function hook_libart() {
        if (ishook_libart === true) {
            return;
        }
        var symbols = Module.enumerateSymbolsSync("libart.so");
        var addrGetStringUTFChars = null;
        var addrNewStringUTF = null;
        var addrFindClass = null;
        var addrGetMethodID = null;
        var addrGetStaticMethodID = null;
        var addrGetFieldID = null;
        var addrGetStaticFieldID = null;
        var addrRegisterNatives = null;
        var addrAllocObject = null;
        var addrCallObjectMethod = null;
        var addrGetObjectClass = null;
        var addrReleaseStringUTFChars = null;
        for (var i = 0; i < symbols.length; i++) {
            var symbol = symbols[i];
            if (symbol.name == "_ZN3art3JNI17GetStringUTFCharsEP7_JNIEnvP8_jstringPh") {
                addrGetStringUTFChars = symbol.address;
                console.log("GetStringUTFChars is at ", symbol.address, symbol.name);
            } else if (symbol.name == "_ZN3art3JNI12NewStringUTFEP7_JNIEnvPKc") {
                addrNewStringUTF = symbol.address;
                console.log("NewStringUTF is at ", symbol.address, symbol.name);
            } else if (symbol.name == "_ZN3art3JNI9FindClassEP7_JNIEnvPKc") {
                addrFindClass = symbol.address;
                console.log("FindClass is at ", symbol.address, symbol.name);
            } else if (symbol.name == "_ZN3art3JNI11GetMethodIDEP7_JNIEnvP7_jclassPKcS6_") {
                addrGetMethodID = symbol.address;
                console.log("GetMethodID is at ", symbol.address, symbol.name);
            } else if (symbol.name == "_ZN3art3JNI17GetStaticMethodIDEP7_JNIEnvP7_jclassPKcS6_") {
                addrGetStaticMethodID = symbol.address;
                console.log("GetStaticMethodID is at ", symbol.address, symbol.name);
            } else if (symbol.name == "_ZN3art3JNI10GetFieldIDEP7_JNIEnvP7_jclassPKcS6_") {
                addrGetFieldID = symbol.address;
                console.log("GetFieldID is at ", symbol.address, symbol.name);
            } else if (symbol.name == "_ZN3art3JNI16GetStaticFieldIDEP7_JNIEnvP7_jclassPKcS6_") {
                addrGetStaticFieldID = symbol.address;
                console.log("GetStaticFieldID is at ", symbol.address, symbol.name);
            } else if (symbol.name == "_ZN3art3JNI15RegisterNativesEP7_JNIEnvP7_jclassPK15JNINativeMethodi") {
                addrRegisterNatives = symbol.address;
                console.log("RegisterNatives is at ", symbol.address, symbol.name);
            } else if (symbol.name.indexOf("_ZN3art3JNI11AllocObjectEP7_JNIEnvP7_jclass") >= 0) {
                addrAllocObject = symbol.address;
                console.log("AllocObject is at ", symbol.address, symbol.name);
            }  else if (symbol.name.indexOf("_ZN3art3JNI16CallObjectMethodEP7_JNIEnvP8_jobjectP10_jmethodIDz") >= 0) {
                addrCallObjectMethod = symbol.address;
                console.log("CallObjectMethod is at ", symbol.address, symbol.name);
            } else if (symbol.name.indexOf("_ZN3art3JNI14GetObjectClassEP7_JNIEnvP8_jobject") >= 0) {
                addrGetObjectClass = symbol.address;
                console.log("GetObjectClass is at ", symbol.address, symbol.name);
            } else if (symbol.name.indexOf("_ZN3art3JNI21ReleaseStringUTFCharsEP7_JNIEnvP8_jstringPKc") >= 0) {
                addrReleaseStringUTFChars = symbol.address;
                console.log("ReleaseStringUTFChars is at ", symbol.address, symbol.name);
            }
        }
    
        if (addrRegisterNatives != null) {
            Interceptor.attach(addrRegisterNatives, {
                onEnter: function (args) {
                    console.log("[RegisterNatives] method_count:", args[3]);
                    var env = args[0];
                    var java_class = args[1];
                    
                    var funcAllocObject = new NativeFunction(addrAllocObject, "pointer", ["pointer", "pointer"]);
                    var funcGetMethodID = new NativeFunction(addrGetMethodID, "pointer", ["pointer", "pointer", "pointer", "pointer"]);
                    var funcCallObjectMethod = new NativeFunction(addrCallObjectMethod, "pointer", ["pointer", "pointer", "pointer"]);
                    var funcGetObjectClass = new NativeFunction(addrGetObjectClass, "pointer", ["pointer", "pointer"]);
                    var funcGetStringUTFChars = new NativeFunction(addrGetStringUTFChars, "pointer", ["pointer", "pointer", "pointer"]);
                    var funcReleaseStringUTFChars = new NativeFunction(addrReleaseStringUTFChars, "void", ["pointer", "pointer", "pointer"]);
    
                    var clz_obj = funcAllocObject(env, java_class);
                    var mid_getClass = funcGetMethodID(env, java_class, Memory.allocUtf8String("getClass"), Memory.allocUtf8String("()Ljava/lang/Class;"));
                    var clz_obj2 = funcCallObjectMethod(env, clz_obj, mid_getClass);
                    var cls = funcGetObjectClass(env, clz_obj2);
                    var mid_getName = funcGetMethodID(env, cls, Memory.allocUtf8String("getName"), Memory.allocUtf8String("()Ljava/lang/String;"));
                    var name_jstring = funcCallObjectMethod(env, clz_obj2, mid_getName);
                    var name_pchar = funcGetStringUTFChars(env, name_jstring, ptr(0));
                    var class_name = ptr(name_pchar).readCString();
                    funcReleaseStringUTFChars(env, name_jstring, name_pchar);
    
                    //console.log(class_name);
    
                    var methods_ptr = ptr(args[2]);
    
                    var method_count = parseInt(args[3]);
                    for (var i = 0; i < method_count; i++) {
                        var name_ptr = Memory.readPointer(methods_ptr.add(i * Process.pointerSize * 3));
                        var sig_ptr = Memory.readPointer(methods_ptr.add(i * Process.pointerSize * 3 + Process.pointerSize));
                        var fnPtr_ptr = Memory.readPointer(methods_ptr.add(i * Process.pointerSize * 3 + Process.pointerSize * 2));
    
                        var name = Memory.readCString(name_ptr);
                        var sig = Memory.readCString(sig_ptr);
                        var find_module = Process.findModuleByAddress(fnPtr_ptr);
                        console.log("[RegisterNatives] java_class:", class_name, "name:", name, "sig:", sig, "fnPtr:", fnPtr_ptr, "module_name:", find_module.name, "module_base:", find_module.base, "offset:", ptr(fnPtr_ptr).sub(find_module.base));
    
                    }
                },
                onLeave: function (retval) { }
            });
        }
    
        ishook_libart = true;
    }
    
    hook_libart();
    

    在这里插入图片描述

    3.3send 和console

    console.log()只是打印在控制台;
    send()方法会经过回调到脚本可以进行调用;
    但是有时候send()参数会返回结果很奇怪,解决办法如下

    send(arguments[1]);
    send(arguments[1].toString());
    [*]{'$handle': '0x203d2a', '$weakRef': 41}
    [*]{"nick":"难以释怀的浅时光","identify":{"APASS_USER":"0","fanLevel":"3","VIP_USER":"1"},"userid":"1016207621"}
    

    参考文献:
    hook基本流程
    hook方法

    native方法地址

    展开全文
  • Frida Dynamic instrumentation toolkit for developers, reverse-engineers, and security researchers. Learn more at frida.re. Two ways to install 1. Install from prebuilt binaries This is the ...
  • frida 视频教程

    2020-11-04 10:34:52
    frida 是一个全平台的hook神器,支持android ios macOS windows linux,这套教程就是给大家入门frida怎么使用。
  • Frida教程

    万次阅读 2018-04-24 11:01:12
    FRIDA 一 简介 Frida是一款基于python + javascript 的hook框架,适用于android/ios/linux/win/osx等平台。Frida的动态代码执行功能,主要是在它的核心引擎Gum中用C语言来实现的。 注入模式:大部分情况下,我们...

    FRIDA

    一 简介

    Frida是一款基于python + javascript 的hook框架,适用于android/ios/linux/win/osx等平台。Frida的动态代码执行功能,主要是在它的核心引擎Gum中用C语言来实现的。
    注入模式:大部分情况下,我们都是附加到一个已经运行到进程,或者是在程序启动到时候进行劫持,然后再在目标进程中运行我们的代码逻辑。这种方式是Frida最常用的使用方式。注入模式的大致实现思路是这样的,带有GumJS的Frida核心引擎被打包成一个动态连接库,然后把这个动态连接库注入到目标进程中,同时提供了一个双向通信通道,这样控制端就可以和注入的模块进行通信了,在不需要的时候,还可以在目标进程中把这个注入的模块给卸载掉。
    嵌入模式:针对没root过的设备Frida提供了一个动态连接库组件 frida-gadget, 可以把这个动态库集成到程序里面来使用Frida的动态执行功能。一旦集成了gadget,就可以和程序使用Frida进行交互。
    预加载模式:自动加载Js文件。

    这里写图片描述
    二 环境搭建-root设备

    1.下载FRIDA

    pip install frida		
    

    2.下载frida-server
    frida-server 是一个守护进程,通过TCP和Frida核心引擎通信,默认的监听端口是27042
    地址: https://github.com/frida/frida/releases
    注意:版本和类型对应,框架和设备对应
    3.连接设备并确认连接

    	adb devices											
    

    4.将frida-server压缩包解压并push到设备中

    adb push /Users/用户名/Desktop/frida-server-10.7.7-android-arm  data/local/tmp/frida-server						
    

    5.运行frida-server

    $adb shell
    $su
    $cd  /data/local/tmp
    $chmod  755  frida-server
    $./frida-server                          
    

    6.检查是否正常
    转发android TCP端口到本地

    adb forward tcp:27042 tcp:27043
    adb forward tcp:27043 tcp:27043
    Frida-ps -U       
    

    这里写图片描述
    -U 代表着 USB,并且让 Frida 检查 USB-Device真机,出现图上这样就是成功了。

    三 常用API
    1.JAVA
    (1)Java.perform(fn)
    frida的main,注意:所有的脚本必须放在这里面,示例:

    Java.perform(function () {                                                                                     
        var Activity = Java.use(“android.app.Activity”);//获得类包相当于js的new()                                                       
        Activity.onResume.implementation = function () {//改变onResume函数     	
             	send("onResume() got called! Let's call the original implementation”);                              
             this.onResume();											
        };														
    });							
    

    (2)Java.use(className)
    动态获取一个类的对象,为以后改变对象方法的实现,或者用$new()实例化对象, $dispose()销毁对象,示例:

    Java.perform(function () {										
        var Activity = Java.use("android.app.Activity");						
        var Exception = Java.use("java.lang.Exception");						
        Activity.onResume.implementation = function () {						
            throw Exception.$new(“Hello World!");							
        };														
    });														
    

    (3)Java.enumerateLoadedClasses(callbacks)
    列出当前已经加载的类,用回调函数处理
    回调函数onMatch:function(className){ }
    找到加载的每个类的时候被调用,参数就是类的名字,这个参数可以传给java.use()来获得一个js类包
    回调函数onComplete: function ()
    列出所有类之后被调用
    2.JavaScript
    (1)Interceptor.attach(target, callbacks)
    在target指定的位置进行函数调用拦截,target是一个NativePointer参数,用来指定你想要拦截的函数的地址。callbacks参数是一个对象:
    onEnter: function(args): 被拦截函数调用之前回调,其中原始函数的 参数使用args数组(NativePointer对象数组)来表示,可以在这里修改函数的调用参数。
    onLeave: function(retval): 被拦截函数调用之后回调,其中retval表示原始函数的返回值,retval是从NativePointer继承来的,是对原始返回值的一个封装,可以使用retval.replace(1337)调用来修改返回值的内容。注意:retval对象只在 onLeave函数作用域范围内有效,因此如果你要保存这个对象以备后续使用的话,一定要使用深拷贝来保存对象,比如:ptr(retval.toString())
    示例:

    Interceptor.attach(Module.findExportByName(“libc.so”,”read”),{				
    	onEnter:function(args){										
    		this.fileDescriptor = args[0].toInt32();						
    	},													
    	onLeave:function(retval){									
    		if(retval.toInt32( ) > 0){									
    			/* do something with this.fileDescriptor */				
    		}												
    	}													
    });										
    

    此外,this 对象还包含了一些额外的比较有用的属性:

    returnAddress: 返回NativePointer类型的 address 对象
    context: 包含 pc,sp,以及相关寄存器比如 eax, ebx等,可以在回调函数中直接修改
    errno: (UNIX)当前线程的错误值
    lastError: (Windows) 当前线程的错误值
    threadId: 操作系统线程Id
    depth: 函数调用层次深度
    

    (2)Interceptor.detachAll()
    取消之前所有的拦截调用
    (3)Interceptor.replace(target, replacement):
    函数实现代码替换,注意:这种情况主要用于想要完全替换掉一个原有函数的实现,replacement参数使用JavaScript形式的一个NativeCallback来实现,后续如果想要取消这个替换效果,可以使用 Interceptor.revert调用来实现

    四 工具
    (1)frida-ps
    用于枚举进程

    --version             show program's version number and exit					
    -h, --help            show this help message and exit						
    -D ID, --device=ID    connect to device with the given ID					
    -U, --usb             connect to USB device							
    -R, --remote          connect to remote frida-server						
    -H HOST, --host=HOST  connect to remote frida-server on HOST			
    -a, --applications    list only applications							
    -i, --installed       include all installed applications						
    

    (2)frida-trace
    动态跟踪

     --version             show program's version number and exit				
     -h, --help            show this help message and exit						
     -D ID, --device=ID    connect to device with the given ID					
     -U, --usb             connect to USB device							
     -R, --remote          connect to remote frida-server						
     -H HOST, --host=HOST  connect to remote frida-server on HOST			
     -f FILE, --file=FILE  spawn FILE									
     -n NAME, --attach-name=NAME                   attach to NAME				
     -p PID, --attach-pid=PID                         attach to PID					
     --debug               enable the Node.js compatible script debugger			
     --disable-jit         disable JIT									
     -I MODULE, --include-module=MODULE     include MODULE				
     -X MODULE, --exclude-module=MODULE   exclude MODULE				
     -i FUNCTION, --include=FUNCTION               include FUNCTION			
     -x FUNCTION, --exclude=FUNCTION             exclude FUNCTION			
     -a MODULE!OFFSET, --add=MODULE!OFFSET     add MODULE!OFFSET		
     -T, --include-imports                                          include program's imports		
     -t MODULE, --include-module-imports=MODULE       include MODULE 		imports													
     -m OBJC_METHOD, --include-objc-method=OBJC_METHOD     include 		OBJC_METHOD												
    

    示例:
    启动手机中的Chrome浏览器

    	frida-trace -i "open" -U com.android.chrome	
    

    可以看到终端中出现:

    open:Loaded handler at :”/用户名/__handlers__/libc.so/open.js”	
    

    frida-trace会生成一个javascript文件,然后Frida会将其注入到进程中,并跟踪特定的调用。生成的open.js脚本将钩住libc.so中的open函数并输出参数.
    open.js:

    /*														
     * Auto-generated by Frida. Please modify to match the signature of open.		
     * This stub is currently auto-generated from manpages when available.		
     *														
     * For full API reference, see: http://www.frida.re/docs/javascript-api/			
     */														
    
    {														
      /**														
       * Called synchronously when about to call open.						
       *														
       * @this {object} - Object allowing you to store state for use in onLeave.		
       * @param {function} log - Call this function with a string to be presented to 	the user.													
       * @param {array} args - Function arguments represented as an array of 		NativePointer objects.											
       * For example use Memory.readUtf8String(args[0]) if the first argument is a 	pointer to a C string encoded as UTF-8.								
       * It is also possible to modify arguments by assigning a NativePointer 		object to an element of this array.									
       * @param {object} state - Object allowing you to keep state across function calls.														
       * Only one JavaScript function will execute at a time, so do not worry 		about race-conditions.											
       * However, do not use this to store function arguments across onEnter/		onLeave, but instead											
       * use "this" which is an object for keeping state local to an invocation.		
       */														
      onEnter: function (log, args, state) {								
        log("open(" +												
          "path=\"" + Memory.readUtf8String(args[0]) + "\"" +					
          ", oflag=" + args[1] +										
        ")");													
      },														
    														
      /**														
       * Called synchronously when about to return from open.				
       *														
       * See onEnter for details.										
       *														
       * @this {object} - Object allowing you to access state stored in onEnter.		
       * @param {function} log - Call this function with a string to be presented to	 the user.													
       * @param {NativePointer} retval - Return value represented as a 			NativePointer object.											
       * @param {object} state - Object allowing you to keep state across function calls.														
       */														
      onLeave: function (log, retval, state) {								
      }														
    }													
    

    这里写图片描述
    可以实时修改open.js进行操作,终端输出如图。

    (3)Python绑定
    示例:
    从Python注入chrome.js脚本
    注意:从命令行加载脚本然后生成一个命令的进程时,Frida容易崩溃。所以先生成进程,再让Frida注入脚本

    #!/usr/bin/python             										
    import frida												
    # js														
    jscode= """													
    console.log("[*] Starting script");									
    Java.perform(function() {										
       var Activity = Java.use("android.app.Activity");						
        Activity.onResume.implementation = function () {						
            console.log("[*] onResume() got called!");							
            this.onResume();											
        };														
    });														
    """														
    # startup frida and attach to com.android.chrome process on a usb device		
    session = frida.get_usb_device().attach("com.android.chrome")				
    # create a script for frida of jsccode								
    script = process.create_script(jscode)								
    # and load the script											
    script.load()												
    

    五 使用
    (1)挂钩libc.so中的函数

    frida-trace -i "xxx" -U com.android.xxxxx	
    

    启动FRIDA和应用,在应用程序启动主进程之前注入FRIDA代码。—no-pause不会中断应用程序,并将生成的进程的任务留给FRIDA,这会打开一个shell,在里边使用Javascript API向Frida写命令

    frida -U -f com.android.xxxxx —no-pause	
    

    例如:重写onResume函数,如图,一旦调用onResume()就会得到如下结果。
    这里写图片描述
    这里写图片描述

    (2)Hook函数
    FRIDA可以动态改变Android应用的行为,比如可以绕过检测Android设备是否处于root状态的函数。对于在ART(Android Runtime,Android运行时)环境中运行的应用来说,可以使用Java.perform来hook函数。
    需要工具:
    dex2jar:将apk使用压缩工具打开提出classes.dex放入dex2jar文件夹中,为d2j_invoke.sh和d2j-dex2jar.sh增加执行权限 ,执行sh d2j-dex2jar.sh classes.dex得到classes-dex2jar.jar。
    JD-GUI:阅读classes-dex2jar.jar

    示例:
    JavaScript

    setImmediate(function() {         //包裹在setImmediate中以防超时				
    	Java.perform(function(){	 //所有脚本必须在这里面				
        		classObject = Java.use("com.android.MainActivity");			
      		classObject .targetFunction.implementation = function(v){			
            			send("argetFunction hooked");						
       		 }													});        												
    });									
    

    (3)Hook native函数
    使用Frida中的Interceptor函数,深入到设备的底层内存中,hook特定的库或者内存地址
    可能需要工具:
    Radare2(或者其他的反汇编工具):可以使用r2frida将Radare2连接到Frida,然后对进程的内存进行静态分析和反汇编处理。使用Radare2的数据包管理程序来安装r2frida,注意先安装Radare2。

    	r2pm install r2frida						
    

    访问进程以及让r2frida执行注入操作的语法如下所示:

    	r2 frida://DEVICE-ID/PROCESS	
    

    示例:
    JavaScript

    setImmediate(function() {										
        Java.perform(function() {										
    	var targetFunction = undefined;								
    	imports = Module.enumerateImportsSync("libfoo.so");//通过导入函数表	获取 targetFunction函数的地址									
    	for(i = 0; i < imports.length; i++) {								
    		if(imports[i].name == "targetFunction") {						
          			targetFunction = imports[i].address;					
            			break;										
        		}												
    	}													
    	Interceptor.attach(targetFunction, {							
        		onEnter: function (args) {								
          			//do something									
         		},												
    	});													
    	console.log("[*] Intercepting targetFunction”);						
        });														
    });														
    
    

    六 嵌入模式-unroot设备
    需要的工具:
    apktool下载地址:https://bitbucket.org/iBotPeaches/apktool/downloads/
    1.下载frida-Gadget
    2.解码app

          apktool d targetapp.apk -o targetappFolder
    

    3.将对应的frida-Gadget复制到targetappFolder/lib/或者targetappFolder/lib/armeabi下,注意版本对应。
    4.打开manifest.xml找到MainActivity,因为我们希望在执行任何其他代码之前注入frida-Gadget,所以将以下smali代码复制到MainActivity的onCreate()方法中

    const-string v0, "frida-gadget"	
    invoke-static {v0}, Ljava/lang/System;->loadLibrary(Ljava/lang/String;)V
    

    5.如果manifest.xml没有Internet permission需要进行添加

    <uses-permission android:name="android.permission.INTERNET" />
    

    6.将apk重新打包

    	apktool b -o repackaged.apk targetappFolder/
    

    7.签名
    创建keystore(如果没有的话)

    keytool -genkey -v -keystore custom.keystore -alias mykeyaliasname -	keyalg RSA -keysize 2048 -validity 10000				
    

    签名

    jarsigner -sigalg SHA256withRSA -digestalg SHA1 -keystore custom.keystore -storepass 你的密码 repackaged.apk mykeyaliasname
    

    验证

    jarsigner -verify repackaged.apk	
    

    zipalign(在sdk的build-tools里面,注意路径)

    zipalign 4 repackaged.apk final.apk
    

    8.安装apk

    adb install final.apk	
    

    七 frida-Gadget使用
    经过第六节重打包的apk在启动时会进入等待页面,这时使用frida-ps -U只显示Gadget一个进程,使用frida -U Gadget进行连接(依旧可以使用frida-trace等工具)。
    这里写图片描述
    我们可以通过%load 脚本.js进行操作(脚本依旧要包裹在Java.perform()中)。

    八 目前存在的一些检测FRIDA的方法
    (1)方法:frida-server通过 TCP 对外与 frida 通信, Java 遍历运行的进程列表能够检查到 frida-server 是否在运行
    措施:重命名 frida-server
    (2)方法:frida-server 默认的TCP 端口是 27047,检查端口是否开放
    措施:命令行指定参数改变frida-server的监听端口
    (3)方法:frida-server 使用 D-Bus 协议通信,为每个开放的端口发送 D-Bus 的认证消息,回复的端口是 frida-server
    措施:Frida 提供了不需要 frida-server 运行的模式
    (4)方法:利用frida 运行时映射到内存的库,直接逐一检查加载的库。在内存中扫描 frida 的库特征 “gadgets”。例如:字符串 “LIBFRIDA”,它在所有 frida-gadget 和 frida-agent 的版本中都有出现
    措施:打补丁,对修改的apk进行重建和签名(例如:apktool)

    展开全文
  • Frida 视频讲解

    2020-09-16 11:22:15
    frida作者在OSDC 2015的演讲视频,附带字幕及PPT,这是第一部分,讲解Frida的demo演示。
  • frida Hook

    2020-08-05 14:59:31
    Frida hook Android Java函数 Frida 环境搭建介绍 1、首先需要去github下载frida server文件,下载链接如下https://github.com/frida/frida/releases,根据Android手机不同的CPU架构选择合适的frida-server文件 2、...

    Frida hook Android Java函数

    Frida 环境搭建介绍
    1、首先需要去github下载frida server文件,下载链接如下https://github.com/frida/frida/releases,根据Android手机不同的CPU架构选择合适的frida-server文件
    2、通过adb push 命令将下载好的frida-server文件传到手机设备中,设置frida-server文件的执行权限
    3、电脑安装python pip
    4、使用pip安装frida (pip install frida)安装过程可能存在一个问题(先留个坑)

    使用frida对Android java 方法进行hook
    写了一个Android Demo程序,进行演示,Demo代码截图:
    ![在这里插入图片描述](https://img-blog.csdnimg.cn/20200805143021670.png?x-oss-process=image/watermark,type_ZmFuZ3poZW5naGVpdGk,shadow_10,text_aHR0cHM6Ly9ibG9nLmNzZG4ubmV0L2hlcHB5c2hvd19teXNlbGY=,size_16,color_FFFFFF,t_70

    在这对TestgetString进行hook,hook代码:
    import frida,sys
    check_hook_code = “”" send(“Running Script”);
    Java.perform(function(){
    var MainActivity = Java.use(“com.bluetooth.myapplication.MainActivity”);
    MainActivity.TestgetString.overload(“int”).implementation = function(v){
    send(“TestDStringValu:”+arguments[0]);
    send(this.TestgetString(v));
    }
    }); “”"

    def on_message(message, data):
    if message[‘type’] == ‘send’:
    print("[*] {0}".format(message[‘payload’]))
    else:
    print(message)

    process = frida.get_device_manager().enumerate_devices()[-1].attach(“com.bluetooth.myapplication”)
    script = process.create_script(check_hook_code)
    script.on(‘message’, on_message)
    script.load()
    sys.stdin.read()

    在这涉及到了java重载方法,函数重载就是相同函数名,但是函数的参数不同,hook重载函数事需要使用列举出函数的参数类型,上述代码hook的就是TestgetString(int a)方法,hook结果:
    在这里插入图片描述
    成功获取到TestgetString传递的参数以及返回值

    展开全文
  • frida搭建

    2020-05-21 16:23:39
    pip install frida-tools 查看是否正常 frida --version 服务端 https://github.com/frida/frida/releases 注意要和客户端版本一致 adb push frida-server-12.5.7-android-x86 /data/local/tmp/ adb shell cd /data/...

    安装客户端

    pip install frida-tools
    查看是否正常
    frida --version

    服务端

    https://github.com/frida/frida/releases
    注意要和客户端版本一致

    adb push frida-server-12.5.7-android-x86 /data/local/tmp/
    adb shell
    cd /data/local/tmp/
    chmod 777 frida-server-12.5.7-android-x86
    ./frida-server-12.5.7-android-x86

    端口转发

    adb forward tcp:27042 tcp:27042
    adb forward tcp:27043 tcp:27043

    验证

    frida-ps -R

    优点

    跨平台
    hook分析比xposed方便,支持native

    文档

    推荐 javascript
    https://frida.re/docs/javascript-api/

    常用命令

    frida-ps

    C:\WINDOWS\system32>frida-ps --help
    Usage: frida-ps [options]
    
    Options:
      --version             show program's version number and exit
      -h, --help            show this help message and exit
      -D ID, --device=ID    connect to device with the given ID
      -U, --usb             connect to USB device
      -R, --remote          connect to remote frida-server
      -H HOST, --host=HOST  connect to remote frida-server on HOST
      -O FILE, --options-file=FILE
                            text file containing additional command line options
      -a, --applications    list only applications
      -i, --installed       include all installed applications
      -j, --json            output results as JSON
    

    frida-trace

    C:\WINDOWS\system32>frida-trace --help
    Usage: frida-trace [options] target
    
    Options:
      --version             show program's version number and exit
      -h, --help            show this help message and exit
      -D ID, --device=ID    connect to device with the given ID
      -U, --usb             connect to USB device
      -R, --remote          connect to remote frida-server
      -H HOST, --host=HOST  connect to remote frida-server on HOST
      -f FILE, --file=FILE  spawn FILE
      -F, --attach-frontmost
                            attach to frontmost application
      -n NAME, --attach-name=NAME
                            attach to NAME
      -p PID, --attach-pid=PID
                            attach to PID
      --stdio=inherit|pipe  stdio behavior when spawning (defaults to “inherit”)
      --runtime=duk|v8      script runtime to use
      --debug               enable the Node.js compatible script debugger
      --squelch-crash       if enabled, will not dump crash report to console
      -O FILE, --options-file=FILE
                            text file containing additional command line options
      -I MODULE, --include-module=MODULE
                            include MODULE
      -X MODULE, --exclude-module=MODULE
                            exclude MODULE
      -i FUNCTION, --include=FUNCTION
                            include FUNCTION
      -x FUNCTION, --exclude=FUNCTION
                            exclude FUNCTION
      -a MODULE!OFFSET, --add=MODULE!OFFSET
                            add MODULE!OFFSET
      -T, --include-imports
                            include program's imports
      -t MODULE, --include-module-imports=MODULE
                            include MODULE imports
      -m OBJC_METHOD, --include-objc-method=OBJC_METHOD
                            include OBJC_METHOD
      -M OBJC_METHOD, --exclude-objc-method=OBJC_METHOD
                            exclude OBJC_METHOD
      -s DEBUG_SYMBOL, --include-debug-symbol=DEBUG_SYMBOL
                            include DEBUG_SYMBOL
      -q, --quiet           do not format output messages
      -d, --decorate        add module name to generated onEnter log statement
      -S PATH, --init-session=PATH
                            path to JavaScript file used to initialize the session
      -P PARAMETERS_JSON, --parameters=PARAMETERS_JSON
                            parameters as JSON, exposed as a global named
                            'parameters'
      -o OUTPUT, --output=OUTPUT
                            dump messages to file
    

    展开全文
  • frida, 克隆这里 repo 以生成 Frida 面向开发人员,反向工程师和安全研究人员的动态测试工具包。安装的两种方式- 1从预生成的二进制文件安装这是开始使用的推荐方法。 你所需要做的就是:pip install --user frida #...
  • frida 学习

    2019-08-21 10:05:00
    frida-server 地址 https://github.com/frida/frida/releases 安装 python3.7 pip3 install frida pip3 install frida-tools 安装成功后 import frida 看是否安装成功 frida-server的端口转发adb forward tcp:...
  • Package frida

    2021-01-01 01:17:09
    <div><p><em>From on November 10, 2016 13:...<p>http://frida.re</p> <p><em>Copied from original issue: termux/termux-packages#551</em></p>该提问来源于开源项目:termux/termux-root-packages</p></div>
  • FRIDA-DEXDump Features support fuzzy search broken header dex. fix struct data of dex-header. compatible with all android version(frida supported). support loading as objection plugin ~ pypi ...
  • frida笔记

    2020-02-29 20:52:26
    https://www.jianshu.com/p/646032f34d57 window上搭建frida环境 https://frida.re/docs/examples/android/ frida官方文档 https://herbwen.com/index.php/archives/48/ frida官网 demo一例 解ctf题 ...
  • Frida API使用(2)

    2020-08-09 23:25:27
    Frida
  • 安装frida

    2020-04-02 10:56:19
    在kali安装frida之前要先安装pip curl https://bootstrap.pypa.io/get-pip.py -o get-pip.py 这里要注意,需要显式指定使用python3,因为kali已经安装了python2.x和3.x版本 python3 get-pip.py 安装frida pip ...
  • Frida搭建

    千次阅读 2018-04-09 19:54:25
    1.下载Frida,终端输入其中一个: pip install frida npm install frida 2.frida –version查看版本下载对应的server 地址: https://github.com/frida/frida/releases 注意:版本和类型都要注意对应,arm的要...
  • Frida原理视频讲解

    2020-09-16 13:42:44
    Frida作者在2015年关于该工具原理的讲解视频。 Frida是个轻量级so级别的hook框架,它可以帮助逆向人员对指定的进程的so模块进行分析。
  • Frida官方手册 - 安装Frida

    千次阅读 2017-10-19 10:12:56
    安装Frida 从零开始安装使用Frida大概只需要几分钟的时间就可以搞定。如果你安装的过程中发现什么问题,可以告诉我们(请参考原文链接https://www.frida.re/docs/installation),看看我们是否有比较好的解决方案...
  • frida enum

    2019-06-03 11:59:38
    https://github.com/haidragon/frida-scripts 转载于:https://blog.51cto.com/haidragon/2404161
  • frida安装教程

    2020-06-02 09:30:34
    frida安装教程以及使用frida脱壳测试frida安装教程1. windows安装frida环境2.手机中安装frida服务端frida脱壳教程1. 文件头搜索dex2. 暴力搜内存dump 学习笔记 frida安装教程 1. windows安装frida环境 需要python...

空空如也

1 2 3 4 5 ... 20
收藏数 2,342
精华内容 936
关键字:

frida