od随便打开一个记事本,汇编几条jmp指令,可以看到如下

地址      HEX        反汇编

010073B4   - E9 7B9E8787    JMP 88881234

010073B9   - E9 769E8787    JMP 88881234

010073BE   - E9 719E8787    JMP 88881234

010073C3   - E9 6C9E8787    JMP 88881234

010073C8   - E9 679E8787    JMP 88881234

010073CD   - E9 629E8787    JMP 88881234

010073D2   - E9 5D9E8787    JMP 88881234

010073D7   - E9 589E8787    JMP 88881234

010073DC   - E9 539E8787    JMP 88881234

010073E1   - E9 4E9E8787    JMP 88881234

010073E6   - E9 499E8787    JMP 88881234

可以看到同样的汇编指令,在不同的地址上的机器码不一样。

有啥关系呢?看第一条:88881234-010073b4=87879e80

这个值跟E9后面的那个值差了5(E9后面那个值要反过来看,因为X86是大端模式)


同样这个规律也使用与后面几条。


为什么呢?

下面摘录一个网上的


直接的jmp分3种 

Short Jump(短跳转)机器码 EB rel8 

只能跳转到256字节的范围内 

Near Jump(近跳转)机器码 E9 rel16/32 

可跳至同一个段的范围内的地址 

Far Jump(远跳转)机器码EA ptr 16:16/32 

可跳至任意地址,使用48位/32位全指针 

要注意的是,短跳转和近跳转指令中包含的操作数都是相对于(E)IP的偏移,而远跳转指令中包含的是目标的绝对地址,所以短/近跳转会出现跳至同一目标的指令机器码不同,不仅会不同,而且应该不同。而远跳转中包含的是绝对地址,因此转移到同一地址的指令机器码相同 

下面的指令是这样计算偏移的. 

004A2FCE   ^ E9 072BFEFF  jmp   00485ADA 

         ======== 

485ADA-4A2FCE=  FFFE2B0C  这里只是指向当前指令的IP处,实际计算跳转地址要去 

掉当前指令的长度,当前的跳转指令需要5个字节,FFFE2B0C-5=FFFE2B07


我们一般就用E9了,所以计算公式就是 要跳转的地址-指令所在的位置-5=机器码

当然 如果我们要在内存中写的话,肯定是写机器码的。也就是也E9 机器码。



结合上面的博文,可以在被HOOK的地址出写入JMP指令跳回到原来的地方,

被HOOK的地址-原来地址-5 = 机器码(这个就是要写入到 被HOOK地址的地方)

为什么不直接修改SSDT表,因为很多程序都会循环去看又没有被改回来,又会被修改回去。