HOOK原理

C 静态: 系统的C函数存在着动态的部分!!,本来C语言是静态的所以fishHook是无法Hook的,但是由于系统的C函数存在着动态的部分,所以fishHook可以Hook了,但是也只能Hook系统的C函数
编译时确定:函数地址
OC 动态
运行时确定:函数地址
fishHook 只能做C函数的(只能Hook C函数)
PIC技术
fishhook原理探索PIC技术

一、HOOK

HOOK,中文译为“挂钩”或“钩子”。在iOS逆向中是指改变程序运行流程的一种技术。通过hook可以让别人的程序执行自己所写的代码。在逆向中经常使用这种技术。所以在学习过程中,我们重点要了解其原理,这样能够对恶意代码进行有效的防护。

iOS中HOOK技术的几种方式
  • 1、Method Swizzle
    利用OC的Runtime特性,动态改变SEL(方法编号)和IMP(方法实现)的对应关系,达到OC方法调用流程改变的目的。主要用于OC方法。
  • 2、fishhook
    它是Facebook提供的一个动态修改链接mach-O文件的工具。利用MachO文件加载原理,通过修改懒加载和非懒加载两个表的指针达到C函数HOOK的目的。
  • 3、Cydia Substrate
    Cydia Substrate 原名为 Mobile Substrate ,它的主要作用是针对OC方法、C函数以及函数地址进行HOOK操作。当然它并不是仅仅针对iOS而设计的,安卓一样可以用。官方地址:http://www.cydiasubstrate.com/
Method Swizzle
Cydia Substrate
  • MobileHooker
    顾名思义用于HOOK。它定义一系列的宏和函数,底层调用objc的runtime和fishhook来替换系统或者目标应用的函数.其中有两个函数:
    MSHookMessageEx 主要作用于Objective-C方法: void MSHookMessageEx(Class class, SEL selector, IMP replacement, IMP result)
    MSHookFunction 主要作用于C和C++函数: void MSHookFunction(voidfunction,void* replacement,void** p_original) , Logos语法的%hook 就是对此函数做了一层封装

  • MobileLoader
       MobileLoader用于加载第三方dylib在运行的应用程序中。启动时MobileLoader会根据规则把指定目录的第三方的动态库加载进去,第三方的动态库也就是我们写的破解程序.

  • safe mode
       破解程序本质是dylib,寄生在别人进程里。 系统进程一旦出错,可能导致整个进程崩溃,崩溃后就会造成iOS瘫痪。所以CydiaSubstrate引入了安全模式,在安全模 式下所有基于CydiaSubstratede 的三方dylib都会被禁用,便于查错与修复。

二、fishHook

它是Facebook提供的一个动态修改链接mach-O文件的工具。利用MachO文件加载原理,通过修改懒加载和非懒加载两个表的指针达到C函数HOOK的目的。

  • 获取代码 git clone https://github.com/facebook/fishhook.git

  • 关键函数

三、fishHOOK原理

fishHOOK可以HOOK我们的C函数,但是我们知道函数是静态的,也就是说在编译的时候,编译器就知道了它的实现地址,这也是为什么C函数只写函数声明调用时会报错。那么为什么fishhook还能够改变C函数的调用呢?难道函数也有动态的特性存在?我们一起来探究它的原理…

  • fishhook利用string Table、Symbols、indirect symbols、懒加载表之间的对应关系。用字符参数最终找到懒加载表的指针,通过重绑定修改指针的值。达到HOOK的目的
How it works

dyld binds lazy and non-lazy symbols by updating pointers in particular sections of the __DATA segment of a Mach-O binary. fishhook re-binds these symbols by determining the locations to update for each of the symbol names passed to rebind_symbols and then writing out the corresponding replacements.

For a given image, the __DATA segment may contain two sections that are relevant for dynamic symbol bindings: __nl_symbol_ptr and __la_symbol_ptr. __nl_symbol_ptr is an array of pointers to non-lazily bound data (these are bound at the time a library is loaded) and __la_symbol_ptr is an array of pointers to imported functions that is generally filled by a routine called dyld_stub_binder during the first call to that symbol (it's also possible to tell dyld to bind these at launch). In order to find the name of the symbol that corresponds to a particular location in one of these sections, we have to jump through several layers of indirection. For the two relevant sections, the section headers (struct sections from ) provide an offset (in the reserved1 field) into what is known as the indirect symbol table. The indirect symbol table, which is located in the __LINKEDIT segment of the binary, is just an array of indexes into the symbol table (also in __LINKEDIT) whose order is identical to that of the pointers in the non-lazy and lazy symbol sections. So, given struct section nl_symbol_ptr, the corresponding index in the symbol table of the first address in that section is indirect_symbol_table[nl_symbol_ptr->reserved1]. The symbol table itself is an array of struct nlists (see ), and each nlist contains an index into the string table in __LINKEDIT which where the actual symbol names are stored. So, for each pointer __nl_symbol_ptr and __la_symbol_ptr, we are able to find the corresponding symbol and then the corresponding string to compare against the requested symbol names, and if there is a match, we replace the pointer in the section with the replacement.

The process of looking up the name of a given entry in the lazy or non-lazy pointer tables looks like this:

四、通过符号找字符串

根据fishhook的原理,查看MachO文件。

你可能感兴趣的:(HOOK原理)