ios逆向工程-内部钩子(Method Swizzling)
Method Swizzling(方法调配)
怎么说呢,先了解什么是钩子为什么用钩子,学过C++的朋友应该清楚,hook就是用来获得(截断/改变)底层调用的方法。这样我们可以自由的修改或者读取一些想要的东西。(个人理解)
下面是百度百科的解释:钩子(Hook),是Windows消息处理机制的一个平台,应用程序可以在上面设置子程以监视指定窗口的某种消息,而且所监视的窗口可以是其他进程所创建的。当消息到达后,在目标窗口处理函数之前处理它。钩子机制允许应用程序截获处理window消息或特定事件
那ios中我们就用Method Swizzling来实现,为什么说是内部钩子呢,因为需要在工程里实现,我改天会分享外部的。
----------------------------------------------凌乱的分割线------------------------------------------
先了解一下SEL和IMP的概念,
SEL可以理解为函数名的意思,我们常用的@selector()就是通过字符串获得SEL
IMP可以理解成函数指针的意思,是能正确读取到函数的内容
一般是这样的:盗个图
我们要做的就是把链接线解开,然后连到我们自定义的函数IMP上,如果有需要的话,我们再连回原来的IMP上
就是这样的:
如果在执行完IMPn后还想继续调用IMPc的话,只需要在IMPn中调用selectorN就行了。
---------------------------------------------凌乱的分割线----------------------------------------
具体怎么做呢:
1
|
Method origMethod = class_getInstanceMethod( class , origSelector); //获取SEL的Method |
Method是一个结构体,我们想要的IMP就在里面,看看结构
1
2
3
4
5
|
struct objc_method { SEL method_name OBJC2_UNAVAILABLE; char *method_types OBJC2_UNAVAILABLE; IMP method_imp OBJC2_UNAVAILABLE; } |
1
|
IMP origIMP = method_getImplementation(origMethod); //获取Method中的IMP |
ok,IMP获取到了,连接SEL到别的IMP呢
1
2
|
BOOL class_addMethod(Class cls, SEL name, IMP imp, const char *types); //先增加新方法名SEL+原来的IMP IMP method_setImplementation(Method m, IMP imp); //然后将原来的method(SEL)重新分配新的IMP |
1
|
void method_exchangeImplementations(Method m1, Method m2) //或者可以使用method的交换方法 |
---------------------------------------------凌乱的分割线-------------------------------------
实战,假设我们想知道app跳转都传送了什么值(如应用调用QQ分享什么的),那么我们可以勾取UIApplication的OpenUrl方法
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
|
#import "KHookObjectWrapper.h" #import "UIKit/UIKit.h" #import <objc/objc.h> #import <objc/runtime.h> @implementation KHookObjectWrapper + ( void )setup { //openURL Method m = class_getInstanceMethod([UIApplication class ], @selector(openURL:)); class_addMethod([UIApplication class ], @selector(hook_openURL:), method_getImplementation(m), method_getTypeEncoding(m)); method_setImplementation(m, class_getMethodImplementation([self class ], @selector(hook_openURL:))); } - ( BOOL )hook_openURL:(NSURL *)url { NSLog(@ "hook_openURL:%@" , [url absoluteString]); return [self hook_openURL:url]; } |
使用method的交换方法实现:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
|
#import "KHookObjectWrapper.h" #import "UIKit/UIKit.h" #import <objc/objc.h> #import <objc/runtime.h> @implementation KHookObjectWrapper + ( void )setup { //openURL Method m = class_getInstanceMethod([UIApplication class ], @selector(openURL:)); Method m2 = class_getInstanceMethod([self class ], @selector(hook_openURL:)); class_addMethod([UIApplication class ], @selector(hook_openURL:), method_getImplementation(m), method_getTypeEncoding(m)); //为什么要有这句的,因为UIApplication没有hook_openURL方法会奔溃,大家觉得可以讲self的hook_openURL改名成openURL,大家可以试试,也是不行的 method_exchangeImplementations(m, m2); } - ( BOOL )hook_openURL:(NSURL *)url { NSLog(@ "hook_openURL:%@" , [url absoluteString]); return [self hook_openURL:url]; } @end |
--------------------------------------------------------------------
另外再加一点,假如你只是想重写类的某些方法,分类也是不错的选择,分类一旦加入工程,不需要包含头文件有会生效,所以请慎重使用
1
2
3
4
5
6
7
8
|
@implementation UIApplication (test) - ( BOOL )openURL:(NSURL*)url { NSLog(@ "!!!!!%@" , [url absoluteString]); return YES; } @end |
当然你没办法重新在掉回原来的IMP了!
ios逆向工程-内部钩子(Method Swizzling)的更多相关文章
- iOS中AOP与Method Swizzling 项目中的应用
引子:项目中需要对按钮点击事件进行统计分析,现在项目中就是在按钮的响应代码中添加点击事件,非常繁琐.所以使用了AOP(面向切面编程),将统计的业务逻辑统一抽离出来. 项目中添加的开源库:https:/ ...
- ios逆向工程
原 ios逆向工程-内部钩子(Method Swizzling) Method+Swizzling ios hook Method Swizzling(方法调配) 怎么说呢,先了解什么是钩子为什么 ...
- 【原】iOS动态性(三) Method Swizzling以及AOP编程:在运行时进行代码注入
概述 今天我们主要讨论iOS runtime中的一种黑色技术,称为Method Swizzling.字面上理解Method Swizzling可能比较晦涩难懂,毕竟不是中文,不过你可以理解为“移花接木 ...
- iOS运行时与method swizzling
C语言是静态语言,它的工作方式是通过函数调用,这样在编译时我们就已经确定程序如何运行的.而Objective-C是动态语言,它并非通过调用类的方 法来执行功能,而是给对象发送消息,对象在接收到消息之后 ...
- IOS 开发之 Method Swizzling + Category
ios 分类中如果增加的方法与被扩展的类方法名重复,则原方法就没法被调用….看以下例子 例如: @interface ClassA : NSObject - (NSString *) myMethod ...
- iOS 使用Method Swizzling隐藏Status Bar
在iOS 6中,隐藏Status Bar很的简单. // iOS 6及曾经,隐藏状态栏 [[UIApplication sharedApplication] setStatusBarHidden:YE ...
- iOS执行时与method swizzling
C语言是静态语言,它的工作方式是通过函数调用,这样在编译时我们就已经确定程序怎样执行的.而Objective-C是动态语言,它并不是通过调用类的方法来执行功能,而是给对象发送消息,对象在接收到消息之后 ...
- IOS 开发之 Method Swizzling
ios 分类中如果增加的方法与被扩展的类方法名重复,则原方法就没法被调用….看以下例子 例如: @interface ClassA : NSObject - (NSString *) myMethod ...
- ios method swizzling
阅读器 iOS开发iOS 本文由TracyYih[博客]翻译自NSHipster的文章Method Swizzling. 在上周associated objects一文中,我们开始探索Ob ...
随机推荐
- 【转】Python 字符串大小写转换
转载自:python 中字符串大小写转换 一.pyhton字符串的大小写转换, 常用的有以下几种方法: 1.对字符串中所有字符(仅对字母有效)的大小写转换,有两个方法: print 'just to ...
- C# 自动触发鼠标、键盘事件
要在C#程序中触发鼠标.键盘事件必须要调用windows函数. 一.鼠标事件的触发 1.引用windows函数mouse_event /// <summary> /// 鼠标事件 /// ...
- 关于推荐库位 java前端与SQL语句后面的结合
----------------------------------------------------------------------------------- select a1.id,a1. ...
- TensorFlow备忘录——conv2d函数
卷积函数 TensorFlow学习备忘录 tf.nn.conv2d(input, filter, strides, padding, use_cudnn_on_gpu=None, data_forma ...
- 读懂 ECMAScript 规格
概述 规格文件是计算机语言的官方标准,详细描述语法规则和实现方法. 一般来说,没有必要阅读规格,除非你要写编译器.因为规格写得非常抽象和精炼,又缺乏实例,不容易理解,而且对于解决实际的应用问题,帮助不 ...
- LNMP环境配置SSL证书 lnmp ssl add
.4新增的添加SSL功能 lnmp ssl add 如果需要添加输入 y ,不添加输入 n 回车. 选择了添加SSL会提示 有两个选项,1 选项为使用自己准备好的SSL证书和key. > &g ...
- ACM ICPC Central Europe Regional Contest 2013 Jagiellonian University Kraków
ACM ICPC Central Europe Regional Contest 2013 Jagiellonian University Kraków Problem A: Rubik’s Rect ...
- 织梦dedecms获取当前内容页栏目id号的方法
一,可在内容模板中直接这样写{dede:field.typeid/} 可显示本栏目的id 二,也可这样写 {dede:type}[field:ID /]{/dede:type} . 三, 如果是在{ ...
- TestNG入门--安装和基本介绍
TestNG介绍 TestNG是Java中的一个测试框架, 类似于JUnit 和NUnit, 功能都差不多, 只是功能更加强大,使用也更方便 Java中已经有一个JUnit的测试框架了. Tes ...
- Ubuntu 14.04配置虚拟主机
虚拟主机常用于在一个单独的IP地址上提供多个域名的网站服务.如果有人想在单个VPS的单个IP地址运行多个网站,这是非常有用的.在这个教程中,让我告诉你如何设置在Ubuntu 14.04 LTS的Apa ...