一、Hook技术
在计算机编程中,HOOK 是一种「劫持」程序原有执行流程,添加额外处理逻辑的技术。基本所有的软件程序都可以通过hook方式进行行为拦截,hook方式就是改变原始的执行流。
Linux平台常见的拦截:
- 修改函数指针
- 用户态动态库拦截
- 内核态系统调用拦截
- Ptrace
- Kernel Inline Hook
1.1 函数指针Hook
1.1.1 理解
C语言的一项强大的功能就是指针,指针代表一个地址,而函数指针就是指向一个函数地址的指针,通过函数指针来指向不同的函数地址控制执行流。
一般这类函数指针存在于软件运行的整个周期中,要实施这类hook首先就是找到关键的函数指针,之后就和普通的指针修改一样进行改变就OK。
函数指针的使用形式:
//函数定义
func() {
....
}
//函数指针
fun = func
//函数指针调用
fun()
通过修改函数指针进行hook:
origin_fun = fun; //保存原始函数指针
f = hook_func; //函数指针指向hook函数
hook_func() {
...
origin_fun(); //一般都会再次调用原始函数来完成实际功能
}
1.1.2 示例
#include <stdio.h>
//由于后面要在注册函数中进行挂钩操作,
//所以把这个函数指针定义成全局变量
int (*g_pFun)(int a, int b);
//单独看这个函数是完全不知道要对x, y做什么操作的,
//所以可猜测到main函数里的情况一定是先挂钩(知道自己做什么)
//再调用ExeFun函数
void ExeFun(){
int x = 1;
int y = 2;
int ret;
ret = g_pFun(x, y);//这里要和什么功能挂钩我们暂时不知道
printf("%d\n",ret);
}
//这里开始挂钩 括号内的int (*pFun)(int a, int b)
// 是一个函数指针形参(符合这个指针的函数都可以被作为参数传进来)
int RegFun(int (*pFun)(int a, int b)){
g_pFun = pFun;
return 0;
}
//函数功能
int max(int a, int b){
if(a > b)
return a;
return b;
}
int min(int a, int b){
if(a > b)
return b;
return a;
}
int main(int argc, char **argv){
RegFun(max);//这里是将具体操作挂钩子
ExeFun();//这里就是执行具体操作的地方
RegFun(min);
ExeFun();
return 0;
}
1.1.3 参考文章
http://t.csdnimg.cn/nZy4r
http://t.csdnimg.cn/A4r9U