能力值:
( LV2,RANK:10 )
|
-
-
2 楼
我觉得可以在XXXXX中先保存返回地址,然后返回地址出栈,还原指令,jmp 返回地址
|
能力值:
( LV2,RANK:10 )
|
-
-
3 楼
在hook的最后恢复原来的指令
PUSH EBP
MOV EBP,ESP
PUSH ECX
PUSH ESI
PUSH EDI
接着jmp到MOV ECX,ESI 指令的地址
|
能力值:
( LV2,RANK:10 )
|
-
-
4 楼
call的原理,是调用过程之前,会自动把下一条指令的地址,压入堆栈,不用担心跳回的问题
|
能力值:
( LV2,RANK:10 )
|
-
-
5 楼
来学习一下!
|
能力值:
( LV3,RANK:20 )
|
-
-
6 楼
真是一群假书呆子,书上说的都没领会,,,,,,哥直接上c++代码看哥的hook用几句汇编。:e9也能照抄
void MyWriteline(PCHAR Add,int Value)
{
DWORD dwPro = 0;
if (Add!=0)
{
VirtualProtect(Add,4,PAGE_READWRITE,&dwPro);
*(int *)Add =(int)Value;
VirtualProtect(Add,4,dwPro,&dwPro);
}
}
void myE8CovertInlineHook(DWORD inlineAdd,DWORD myFuctionADD,DWORD & OldAddContainer)
{
if (inlineAdd != 0 && myFuctionADD != 0 )
{
OldAddContainer=inlineAdd+*(PDWORD)(inlineAdd+1)+5;
MyWriteline((PCHAR)(inlineAdd+1),(int)(myFuctionADD-5-inlineAdd));
}
}
void myE8CovertInlineUnHook(DWORD inlineAdd,DWORD & OldAddContainer)
{
DWORD dwPro = 0;
if(inlineAdd!= 0 && OldAddContainer != 0)
{
MyWriteline((PCHAR)(inlineAdd+1),(int)(OldAddContainer-5-inlineAdd));
}
}
例子:
myE8CovertInlineHook(要hook的地址,(DWORD)自己的函数地址,用来保存原始地址的全局变量);
// __declspec(naked)void 我的函数()
// {
//
// ……
// ……
// ……
// ……
// __asm{
// jmp 原始地址
//
// }
// }
|
能力值:
(RANK:10 )
|
-
-
7 楼
返回时要还原现场,这就是原则。所以,HOOK的时候不要用
E8,不要用call xxxx,而要用jmp far xxxx,因为call的时候
把eip压入堆栈了,你返回的时候要恢复堆栈,这个很麻烦,
而用jmp,堆栈没有变, 你返回的时候,hook掉几行,就先
执行几行,再跳转回去就可以了,比如你的这个例子,
返回之前,先执行
先检查:
注意,这时,所有的寄存器应该都是原值,你用了几个,
就要恢复几个
再执行
PUSH EBP
MOV EBP,ESP
PUSH ECX
PUSH ESI
PUSH EDI
再跳转到hook的下一条语句:
MOV ECX,ESI,这样就可以了。
如果你用call,堆栈中有一个返回地址,但你又要操作
PUSH EBP...等等,这就不好操作,所以不如用jmp
|
能力值:
( LV3,RANK:20 )
|
-
-
8 楼
我的方法只要保证naked 堆栈是平衡的,被hook的地方用的是e8call就可以通杀,而且都是c代码写的别人一看就明白, 你这种方法一堆汇编,到时维护的时候一堆汇编混在一起, 你自己都分不清哪个是哪个了
|
能力值:
( LV2,RANK:10 )
|
-
-
9 楼
学习下学习学习
|
能力值:
( LV2,RANK:10 )
|
-
-
10 楼
OldAddContainer=inlineAdd+*(PDWORD)(inlineAdd+1)+5;
这句话的意思能讲的明白些么? 64位与32位的程序这些值都适应么?
|
能力值:
( LV2,RANK:10 )
|
-
-
11 楼
call 完了自己会回来
|
|
|