首页
社区
课程
招聘
jmp [ecx*4 + 426515] 修改失败
发表于: 2010-3-8 20:51 5644

jmp [ecx*4 + 426515] 修改失败

2010-3-8 20:51
5644
RT。
修改 JMP 426515之类的5字节的是成功的,成功的跳转到我想要跳转的地方。

但是修改jmp [ecx*4 + 426515] 这个7字节的,不知道跳到哪里去了,OD显示无任何指令。
修改方法是 jmp xxxx
                nop
                nop
最后两个nop是平衡上面7个字节用的。
计算公式是:目标地址 - 当前地址 - 7;得到jmp 后面的地址:E9 yyyyy

为啥呢?
难道是上面的jmp地址动态生成的原因吗??
谢谢。

[培训]内核驱动高级班,冲击BAT一流互联网大厂工作,每周日13:00-18:00直播授课

收藏
免费 0
支持
分享
最新回复 (10)
雪    币: 134
活跃值: (10)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
2
计算错误,不应是减7了,应该是减5,后面的 nop 已是下一条指令了
2010-3-8 21:10
0
雪    币: 141
活跃值: (10)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
3
-5也一样。程序卡在那里 了。。。
原本是 :
00401005      FF248D 15654200   jmp     dword ptr [ecx*4+426515]
应该是7个字节吧。

现在替换成:
0040100E    - E9 F2FFFF02       jmp     03401005
只有5个字节了。所以才用nop填充,按照距离来算是7个字节的距离啊。。。
2010-3-8 21:28
0
雪    币: 134
活跃值: (10)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
4
[QUOTE=kakueiken;772452]-5也一样。程序卡在那里 了。。。
原本是 :
00401005      FF248D 15654200   jmp     dword ptr [ecx*4+426515]
应该是7个字节吧。

现在替换成:
0040100E    - E9 F2FFFF02       jmp     034...[/QUOTE]

原来是 00401005,怎么变成 0040100E 了。
不过这个跳转应该是没问题的,只是 03401005 这个目标地址正确吗?
2010-3-8 21:53
0
雪    币: 78
活跃值: (10)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
5
格式
描述
举例
类别
说明

jmp 16位寄存器
以16位寄存器的值改变IP
jmp ax
段内转移
 

jmp 段地址:偏移地址
以立即数改变段地址和偏移地址
jmp 0045H:0020H
段间转移
 

jmp short 标号
以标号地址后第一个字节的地址来改变IP,实际上这个功能可以作如下描述:
(IP)=(IP)+8bit位移
8bit位移指的是从jmp指令后第一个字节开始算起
jmp short sign
段内短转移
对IP的修改范围是-128->127,实际算法是编译器根据当前IP指针的指向来计算到底偏移多少个字节来指向下一条指令,下面这段代码就会出编译错误
jmp short s
dw 200 dup(2)
s: mov ax,4
因为跳转超过了范围

jmp near ptr 标号
以标号地址后第一个字的地址来改变IP,
实际上这个功能可以作如下描述:
(IP)=(IP)+16bit位移
16bit位移指的是从jmp指令后第一个字节开始算起
jmp near ptr sign
段内近转移
对IP的修改范围是-32768->32767

jmp far ptr标号
以标号的段地址和指令地址同时改变CS和IP
jmp far ptr sign
段间转移
 

jmp word ptr 内存地址
以内存地址单元处的字修改IP,内存单元可以以任何合法的方式给出
jmp word ptr ds:[si]
jmp word ptr ds:[0]
jmp word ptr [bx]
jmp word ptr [bp+si+idata]
段内转移
 

jmp dword ptr 内存地址
以内存地址单元处的双字来修改指令,高地址内容修改CS,低地址内容修改IP,内存地址可以以任何合法的方式给出
jmp dword ptr [bx]
段间转移
s1 segment
dw 0a0bh, 0c0dh
s1 ends

mov ax,s1
mov ds,ax
jmp dword ptr ds:[0]
2010-3-8 22:15
0
雪    币: 141
活跃值: (10)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
6
不好意思。上面是乱写的,本想说明一下大概。

现在做法如下:
先VirtualAlloc一块内存,假如首地址是:0x03000000
现在把程序的JMP指令修改:
原指令:
0040F4A9                 jmp     ds:off_426515[ecx*4] ; switch jump
修改后指令:
0x03000000 - 0x0040F4A9 - 7 = 0x2BF0B50

0040F4A9 E9 500BBF02  jmp 03000000
0040F4AE 90
0040F4AF 90

现在OD显示jmp 03000000地址的东西什么也没有。

以上03000000是变化的,因为每次分配多不一样。但是我经过好几次计算,确实是按照上面的公式。

但是同样修改附近的一个JMP 5字节的。就成功了。
2010-3-8 22:37
0
雪    币: 141
活跃值: (10)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
7
谢谢,你说的很详细。虽然有些一知半解。
因为是DLL注入后,想修改进程的一个函数内的一个JMP,跳入自己DLL内的一个函数。然后再跳回去。
2010-3-8 22:54
0
雪    币: 78
活跃值: (10)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
8
那就先保存后覆盖回去
2010-3-8 23:02
0
雪    币: 12948
活跃值: (3947)
能力值: ( LV15,RANK:1575 )
在线值:
发帖
回帖
粉丝
9
[QUOTE=kakueiken;772418]RT。
修改 JMP 426515之类的5字节的是成功的,成功的跳转到我想要跳转的地方。

但是修改jmp [ecx*4 + 426515] 这个7字节的,不知道跳到哪里去了,OD显示无任何指令。
修改方法是 jmp xxxx
                nop
               ...[/QUOTE]

如果你是在OD中修改(修改内存中的)应该可以的...不过也不能存盘...
如果你是直接修改文件这个地方应该是不可以的...因为7个字节的后4个字节应该正好是重定位的位置,也就是那7个字节的前三个是不变的,后4个字节会在载入到内存时由对应的重定位表中的项来修正,就会变了..
要改的话你还得找到并清了那个项...
2010-3-8 23:02
0
雪    币: 141
活跃值: (10)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
10
用这个方法 jmp dword ptr[12345];0x12345->03000000
好像可以的,我Log已经出来了。
就是 jmp 03000000这个不行,不知道为啥。在这里贴出为修改的汇编;
IDA,Copy的:
.text:0040F49B                 mov     edx, [ebp+var_114C]
.text:0040F4A1                 xor     ecx, ecx
.text:0040F4A3                 mov     cl, ds:byte_4266D5[edx]
.text:0040F4A9                 jmp     ds:off_426515[ecx*4] ; switch jump
.text:0040F4B0
.text:0040F4B0 loc_40F4B0:                             ; DATA XREF: .text:off_426515o
.text:0040F4B0                 mov     dword_1495880, 0 ; jumptable 0040F4A9 case 95
.text:0040F4BA                 push    2               ; Size
.text:0040F4BC                 mov     eax, dword_14955E0

以下是OD:

0040F49B    8B95 B4EEFFFF   mov     edx, dword ptr [ebp-114C]
0040F4A1    33C9            xor     ecx, ecx
0040F4A3    8A8A D5664200   mov     cl, byte ptr [edx+4266D5]
0040F4A9    FF248D 15654200 jmp     dword ptr [ecx*4+426515]         ; Sangokus.004127B1
0040F4B0    C705 80584901 0>mov     dword ptr [1495880], 0
0040F4BA    6A 02           push    2
0040F4BC    A1 E0554901     mov     eax, dword ptr [14955E0]
0040F4C1    05 5D1D6A00     add     eax, 006A1D5D

郁闷两天了。呵呵。

目标实现:
0040F4A9                 jmp    03000000
...
03000000:

pushad
call mydll.log
popad
jmp     dword ptr [ecx*4+426515];此处回跳到原先的想跳的地方。
2010-3-8 23:25
0
雪    币: 141
活跃值: (10)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
11
可能是我计算错了,但是怎么计算也没成功最后修改了别地方12字节。做法类似。
发现确实call dword ptr,jmp dword ptr更好些,不用计算。
另外自己也实验了一番,把程序内的一段汇编Copy到进程中(自己申请的内存中)。也可以执行。
只要dll以注入,整个程序就是你的了。一下是自己实验的内容:

int _start = 0;
int _end = 0;
char _msg[] = "teste\n";
char exe[1000] = {0};

void test(){
        __asm{
                call _l1
_l1:
                pop ecx
                mov _start,ecx
        };
        printf(_msg);
        __asm{
                call _l2
_l2:
                pop ecx
                mov _end,ecx
        };
}

void main(){
        DWORD old=0;
        BOOL v = VirtualProtect(exe,1024,PAGE_EXECUTE_READWRITE,&old);
        _start += 7;
        _end -= 5;
        memcpy(exe,(char *)_start,_end - _start);
        int jj = (int)&exe;
        __asm{
                pushad
                jmp dword ptr[jj]
                popad
        };
}

这样是不是很方便。?!
2010-3-12 23:23
0
游客
登录 | 注册 方可回帖
返回
//