Lpyax 发表于 2020-2-7 16:15:44

Call和十六进制的转换的一些问题

各位大佬好,我想问一下

Lpyax 发表于 2020-2-7 16:18:37

(怎么直接发出去了)
E8 F9FFFFFF       call ws2_32.764B6CFF               
E8 00000001   call 774B6D0B
E8 00000000   call ws2_32.764B6D10
这个 E8 后面的十六进制是怎么通过call后面的地址算出来的

人造人 发表于 2020-2-7 19:23:07

请先自己通过这个程序理解,然后把你不懂的地方指出来


start:
L1:        nop
        call        L1
        nop
L2:        call        L2
        nop
        call        L3
L3:        nop


> nasm -o main.bin main.asm

> ndisasm -b 32 main.bin
0000000090                nop
00000001E8FAFFFFFF      call 0x0
0000000690                nop
00000007E8FBFFFFFF      call 0x7
0000000C90                nop
0000000DE800000000      call 0x12
0000001290                nop

>

Lpyax 发表于 2020-2-7 21:44:03

人造人 发表于 2020-2-7 19:23
请先自己通过这个程序理解,然后把你不懂的地方指出来

万分感谢您在百忙之中抽空回答我的问题,只是。。。
我没学汇编啊{:10_285:}
虽说我也知道不会却直接往汇编区发帖有问题。。

按照我的理解的话,看起来是
(在除了call全是nop的前提下)
call下一行则为E8 00000000,
call本行则是   E8 FBFFFFFF,
call上一行则是E8 FAFFFFFF。
我再用OD试了一下,
call上两行则是E8 F9FFFFFF
call上三行则是E8 F8FFFFFF
然后总是F后面这个数字在不断消减,随后减少的是第一个字母。。。。
然后到了第四位。。。。emmm,,,抱歉,我看不出其中的规律

人造人 发表于 2020-2-7 21:51:29

Lpyax 发表于 2020-2-7 21:44
万分感谢您在百忙之中抽空回答我的问题,只是。。。
我没学汇编啊
虽说我也知道不会却直接往 ...

e8后面的4个字节表示从call指令的下一条指令开始的偏移
第3个call的是call指令的下一条指令,使用偏移就是0

call指令一共5个字节,所以call当前的这条call指令的偏移就是 0 - 5 = -5,fffffffb就是-5

Lpyax 发表于 2020-2-7 22:00:07

人造人 发表于 2020-2-7 21:51
e8后面的4个字节表示从call指令的下一条指令开始的偏移
第3个call的是call指令的下一条指令,使用偏移就 ...

喔!而nop占一个字节,所以call上一行的nop就是偏移-6,也就是FFFFFFFA。
可是,FFFFFFFA和FFFFFFFB又是怎么变成FAFFFFFF和FBFFFFFF的呢

我百度看到的是取反码然后按位+1,不过这样不也就是得了个6(十六进制)而已么。。不是很明白。。
上述引用资料:https://zhidao.baidu.com/question/579612385.html

Lpyax 发表于 2020-2-7 22:06:39

人造人 发表于 2020-2-7 21:51
e8后面的4个字节表示从call指令的下一条指令开始的偏移
第3个call的是call指令的下一条指令,使用偏移就 ...

(刚刚回复了一次不过好像要审核,应该是加了个网址)
按照您所说的我又去试了一下,发现对于call上一条,偏移是-6,也就是FFFFFFFA
但是我又有一个问题,FFFFFFFA和FFFFFFFB又是怎么转换成FAFFFFFF和FBFFFFFF的呢
抱歉给您添麻烦了

人造人 发表于 2020-2-7 22:20:46

FAFFFFFF是在内存中的表示形式,看的时候,从右往左看,两个字母为1组
fa ff ff ff

也就是0xfffffffa

换一个
1254BC71

12 54 bc 71
0x71bc5412

人造人 发表于 2020-2-7 22:22:56

Lpyax 发表于 2020-2-7 22:06
(刚刚回复了一次不过好像要审核,应该是加了个网址)
按照您所说的我又去试了一下,发现对于call上一条 ...

"发现对于call上一条,偏移是-6"
这取决于上一条指令的长度,不是偏移永远都是-6

Lpyax 发表于 2020-2-7 22:25:32

人造人 发表于 2020-2-7 22:22
"发现对于call上一条,偏移是-6"
这取决于上一条指令的长度,不是偏移永远都是-6

嗯 以指令的开头算起对吧 FF(两个字母)为一个字节
非常感谢您的回答,占用您的时间了!

人造人 发表于 2020-2-7 22:41:04

401067:       85 c0                   testl%eax,%eax
401069:       74 57                   je   0x4010c2
40106b:       b9 02 00 00 00          movl   $0x2,%ecx


401070:       e8 db 66 04 00          callq0x447750


401075:       48 c7 c1 ff ff ff ff    movq   $0xffffffffffffffff,%rcx
40107c:       e8 af 4e 04 00          callq0x445f30
401081:       48 8b 15 58 20 12 00    movq   0x122058(%rip),%rdx      # 0x5230e0
401088:       48 89 02                movq   %rax,(%rdx)
40108b:       48 8b 15 3e 20 12 00    movq   0x12203e(%rip),%rdx      # 0x5230d0
401092:       48 89 02                movq   %rax,(%rdx)
401095:       48 8b 05 a4 20 12 00    movq   0x1220a4(%rip),%rax      # 0x523140
40109c:       8b 10                   movl   (%rax),%edx
40109e:       48 8b 05 db 1f 12 00    movq   0x121fdb(%rip),%rax      # 0x523080
4010a5:       48 8b 00                movq   (%rax),%rax
4010a8:       89 10                   movl   %edx,(%rax)
4010aa:       e8 71 4a 04 00          callq0x445b20
4010af:       48 8b 05 3a 1f 12 00    movq   0x121f3a(%rip),%rax      # 0x522ff0
4010b6:       83 38 01                cmpl   $0x1,(%rax)
4010b9:       74 65                   je   0x401120
4010bb:       31 c0                   xorl   %eax,%eax
4010bd:       48 83 c4 28             addq   $0x28,%rsp
4010c1:       c3                      retq
...
447748:       ff 25 be 4d 0f 00       jmpq   *0xf4dbe(%rip)      # 0x53c50c
44774e:       90                      nop
44774f:       90                      nop


447750:       ff 25 ae 4d 0f 00       jmpq   *0xf4dae(%rip)      # 0x53c504


447756:       90                      nop
447757:       90                      nop
447758:       ff 25 96 4d 0f 00       jmpq   *0xf4d96(%rip)      # 0x53c4f4
44775e:       90                      nop
44775f:       90                      nop


这个偏移的计算方法是,目标地址 - 当前指令的下一条指令的地址
401070:       e8 db 66 04 00          callq0x447750
447750:       ff 25 ae 4d 0f 00       jmpq   *0xf4dae(%rip)      # 0x53c504

也就是 447750 - 401075 = 000466db

db 66 04 00 就是 000466db

对于向前转移也一样
445f0c:       90                      nop
445f0d:       90                      nop
445f0e:       90                      nop
445f0f:       90                      nop


445f10:       db e3                   fninit


445f12:       c3                      retq
445f13:       90                      nop
445f14:       90                      nop
445f15:       90                      nop
445f16:       90                      nop
445f17:       90                      nop
...
446840:       ba 01 00 00 00          movl   $0x1,%edx
446845:       b9 0b 00 00 00          movl   $0xb,%ecx
44684a:       e8 41 0d 00 00          callq0x447590
44684f:       b8 ff ff ff ff          movl   $0xffffffff,%eax
446854:       e9 c4 fe ff ff          jmpq   0x44671d
446859:       ba 01 00 00 00          movl   $0x1,%edx
44685e:       b9 08 00 00 00          movl   $0x8,%ecx
446863:       e8 28 0d 00 00          callq0x447590


446868:       e8 a3 f6 ff ff          callq0x445f10


44686d:       e9 38 ff ff ff          jmpq   0x4467aa
446872:       90                      nop
446873:       90                      nop
446874:       90                      nop
446875:       90                      nop


445f10 - 44686d = fffff6a3
e8 a3 f6 ff ff

Lpyax 发表于 2020-2-7 22:47:03

人造人 发表于 2020-2-7 22:41
这个偏移的计算方法是,目标地址 - 当前指令的下一条指令的地址
401070:       e8 db 66 04 00    ...

喔!明白了,学习到了(虽说这些代码看不懂...为啥mov后面加个l,call和jmp后面加个q。。。{:10_266:}是缩写么 jmp far这种?)

人造人 发表于 2020-2-7 22:47:07

要得到 -6 在内存中的存储格式

先得到 6 的二进制形式

00000000000000000000000000000110
取反
11111111111111111111111111111001
然后再加 1
11111111111111111111111111111010

这就是 -6
换回十六进制就是
FFFFFFFA

人造人 发表于 2020-2-7 22:48:42

Lpyax 发表于 2020-2-7 22:47
喔!明白了,学习到了(虽说这些代码看不懂...为啥mov后面加个l,call和jmp后面加个q。。。是 ...

这是gnu语法的汇编语言
明白了这个地址的计算方法就行了

Lpyax 发表于 2020-2-7 22:52:28

人造人 发表于 2020-2-7 22:47
要得到 -6 在内存中的存储格式

先得到 6 的二进制形式


嗯?-6在内存中不是以FAFFFFFF表示的么

Lpyax 发表于 2020-2-7 22:53:04

人造人 发表于 2020-2-7 22:48
这是gnu语法的汇编语言
明白了这个地址的计算方法就行了

嗯,谢谢大佬

Lpyax 发表于 2020-2-7 22:53:40

Lpyax 发表于 2020-2-7 22:52
嗯?-6在内存中不是以FAFFFFFF表示的么

虽然说在计算器里面的确FFFFFFFA=-6

人造人 发表于 2020-2-7 22:56:07

Lpyax 发表于 2020-2-7 22:52
嗯?-6在内存中不是以FAFFFFFF表示的么

那就两个一组,再倒过来

FFFFFFFA

ff ff ff fa

fa ff ff ff

Lpyax 发表于 2020-2-7 23:00:35

人造人 发表于 2020-2-7 22:56
那就两个一组,再倒过来

FFFFFFFA


嗯,而且我发现似乎jmp这些也是一样的情况(幸好我暂时不需要改写jmp)

人造人 发表于 2020-2-7 23:01:30

Lpyax 发表于 2020-2-7 23:00
嗯,而且我发现似乎jmp这些也是一样的情况(幸好我暂时不需要改写jmp)

嗯,jmp也一样
页: [1] 2
查看完整版本: Call和十六进制的转换的一些问题