Assembly 装配测验-第6阶段

Assembly 装配测验-第6阶段,assembly,gdb,reverse-engineering,Assembly,Gdb,Reverse Engineering,我一直在解决关于汇编代码的小测验,但是Quiz6(第6阶段)对我来说真的很难弄清楚它在做什么。 我刚刚发现,第6阶段的输入是六个整数,每个整数都是相同的,并且小于等于6。 我在下面的代码行中写了一些其他细节 第六阶段说: Dump of assembler code for function phase_6: => 0x00005555555554fd <+0>: push %r14 0x00005555555554ff <+2>: push %r13

我一直在解决关于汇编代码的小测验,但是Quiz6(第6阶段)对我来说真的很难弄清楚它在做什么。 我刚刚发现,第6阶段的输入是六个整数,每个整数都是相同的,并且小于等于6。 我在下面的代码行中写了一些其他细节

第六阶段说:

Dump of assembler code for function phase_6:
=> 0x00005555555554fd <+0>: push   %r14
   0x00005555555554ff <+2>: push   %r13
   0x0000555555555501 <+4>: push   %r12
   0x0000555555555503 <+6>: push   %rbp
   0x0000555555555504 <+7>: push   %rbx
   0x0000555555555505 <+8>: sub    $0x60,%rsp
   0x0000555555555509 <+12>:    mov    %fs:0x28,%rax
   0x0000555555555512 <+21>:    mov    %rax,0x58(%rsp)
   0x0000555555555517 <+26>:    xor    %eax,%eax
   0x0000555555555519 <+28>:    mov    %rsp,%r13
   0x000055555555551c <+31>:    mov    %r13,%rsi
   0x000055555555551f <+34>:    callq  0x555555555aba <read_six_numbers>
   0x0000555555555524 <+39>:    mov    %r13,%r12
   0x0000555555555527 <+42>:    mov    $0x0,%r14d
   0x000055555555552d <+48>:    jmp    0x555555555554 <phase_6+87>
   0x000055555555552f <+50>:    callq  0x555555555a7e <explode_bomb>
   0x0000555555555534 <+55>:    jmp    0x555555555563 <phase_6+102>
   0x0000555555555536 <+57>:    add    $0x1,%ebx
   0x0000555555555539 <+60>:    cmp    $0x5,%ebx
   0x000055555555553c <+63>:    jg     0x555555555550 <phase_6+83>
   0x000055555555553e <+65>:    movslq %ebx,%rax
   0x0000555555555541 <+68>:    mov    (%rsp,%rax,4),%eax
   0x0000555555555544 <+71>:    cmp    %eax,0x0(%rbp)
   0x0000555555555547 <+74>:    jne    0x555555555536 <phase_6+57>
   0x0000555555555549 <+76>:    callq  0x555555555a7e <explode_bomb>
   // Upper cods seems to test the identicality and integers are under equal 6


   //And I have no idea what are below codelines do. From here...
   0x000055555555554e <+81>:    jmp    0x555555555536 <phase_6+57>
   0x0000555555555550 <+83>:    add    $0x4,%r13
   0x0000555555555554 <+87>:    mov    %r13,%rbp
   0x0000555555555557 <+90>:    mov    0x0(%r13),%eax
   0x000055555555555b <+94>:    sub    $0x1,%eax
   0x000055555555555e <+97>:    cmp    $0x5,%eax
   0x0000555555555561 <+100>:   ja     0x55555555552f <phase_6+50>
   0x0000555555555563 <+102>:   add    $0x1,%r14d
   0x0000555555555567 <+106>:   cmp    $0x6,%r14d
   0x000055555555556b <+110>:   je     0x555555555572 <phase_6+117>
   0x000055555555556d <+112>:   mov    %r14d,%ebx
   0x0000555555555570 <+115>:   jmp    0x55555555553e <phase_6+65>
   0x0000555555555572 <+117>:   lea    0x18(%r12),%rcx
   0x0000555555555577 <+122>:   mov    $0x7,%edx
   0x000055555555557c <+127>:   mov    %edx,%eax
   0x000055555555557e <+129>:   sub    (%r12),%eax
   0x0000555555555582 <+133>:   mov    %eax,(%r12)
   0x0000555555555586 <+137>:   add    $0x4,%r12
   0x000055555555558a <+141>:   cmp    %r12,%rcx
   0x000055555555558d <+144>:   jne    0x55555555557c <phase_6+127>
   0x000055555555558f <+146>:   mov    $0x0,%esi
   0x0000555555555594 <+151>:   jmp    0x5555555555b0 <phase_6+179>
   0x0000555555555596 <+153>:   mov    0x8(%rdx),%rdx
   0x000055555555559a <+157>:   add    $0x1,%eax
   0x000055555555559d <+160>:   cmp    %ecx,%eax
   0x000055555555559f <+162>:   jne    0x555555555596 <phase_6+153>
   0x00005555555555a1 <+164>:   mov    %rdx,0x20(%rsp,%rsi,8)
   0x00005555555555a6 <+169>:   add    $0x1,%rsi
   0x00005555555555aa <+173>:   cmp    $0x6,%rsi
   0x00005555555555ae <+177>:   je     0x5555555555c6 <phase_6+201>
   0x00005555555555b0 <+179>:   mov    (%rsp,%rsi,4),%ecx
   0x00005555555555b3 <+182>:   mov    $0x1,%eax
   0x00005555555555b8 <+187>:   lea    0x202c71(%rip),%rdx        # 0x555555758230 <node1>
   0x00005555555555bf <+194>:   cmp    $0x1,%ecx
   0x00005555555555c2 <+197>:   jg     0x555555555596 <phase_6+153>
   0x00005555555555c4 <+199>:   jmp    0x5555555555a1 <phase_6+164>
   0x00005555555555c6 <+201>:   mov    0x20(%rsp),%rbx
   0x00005555555555cb <+206>:   mov    0x28(%rsp),%rax
   0x00005555555555d0 <+211>:   mov    %rax,0x8(%rbx)
   0x00005555555555d4 <+215>:   mov    0x30(%rsp),%rdx
   0x00005555555555d9 <+220>:   mov    %rdx,0x8(%rax)
   0x00005555555555dd <+224>:   mov    0x38(%rsp),%rax
   0x00005555555555e2 <+229>:   mov    %rax,0x8(%rdx)
   0x00005555555555e6 <+233>:   mov    0x40(%rsp),%rdx
   0x00005555555555eb <+238>:   mov    %rdx,0x8(%rax)
   0x00005555555555ef <+242>:   mov    0x48(%rsp),%rax
   0x00005555555555f4 <+247>:   mov    %rax,0x8(%rdx)
   0x00005555555555f8 <+251>:   movq   $0x0,0x8(%rax)
   0x0000555555555600 <+259>:   mov    $0x5,%ebp
   0x0000555555555605 <+264>:   jmp    0x555555555610 <phase_6+275>
   // ...To Here


   //I think this block is compareing $rbx, *($rbx + 8), .... with ($rbx)
   //but gdb says can't read the memory *($rbx + 8), *(*($rbx + 8) + 8), ...things.
   //Only it reads $rbx
   0x0000555555555607 <+266>:   mov    0x8(%rbx),%rbx
   0x000055555555560b <+270>:   sub    $0x1,%ebp
   0x000055555555560e <+273>:   je     0x555555555621 <phase_6+292>
   0x0000555555555610 <+275>:   mov    0x8(%rbx),%rax
   0x0000555555555614 <+279>:   mov    (%rax),%eax
   0x0000555555555616 <+281>:   cmp    %eax,(%rbx)
   0x0000555555555618 <+283>:   jge    0x555555555607 <phase_6+266>
   0x000055555555561a <+285>:   callq  0x555555555a7e <explode_bomb>
   0x000055555555561f <+290>:   jmp    0x555555555607 <phase_6+266>



   0x0000555555555621 <+292>:   mov    0x58(%rsp),%rax
   0x0000555555555626 <+297>:   xor    %fs:0x28,%rax
   0x000055555555562f <+306>:   jne    0x55555555563e <phase_6+321>
   0x0000555555555631 <+308>:   add    $0x60,%rsp
   0x0000555555555635 <+312>:   pop    %rbx
   0x0000555555555636 <+313>:   pop    %rbp
   0x0000555555555637 <+314>:   pop    %r12
   0x0000555555555639 <+316>:   pop    %r13
   0x000055555555563b <+318>:   pop    %r14
   0x000055555555563d <+320>:   retq   
   0x000055555555563e <+321>:   callq  0x555555554e90 <__stack_chk_fail@plt>
End of assembler dump.
功能阶段_6的汇编程序代码转储:
=>0x000055554FD:推送%r14
0x000055554FF:推送%r13
0x00005555501:推送%r12
0x00005555503:推送%rbp
0x00005555504:推送%rbx
0x00005555505:低于$0x60,%rsp
0x00005555509:mov%fs:0x28,%rax
0x00005512:mov%rax,0x58(%rsp)
0x00005517:xor%eax,%eax
0x00005519:mov%rsp,%r13
0x0000551C:mov%r13,%rsi
0x00005551F:callq 0x55555ABA
0x00005524:mov%r13,%r12
0x00005527:mov$0x0,%r14d
0x0000552D:jmp 0x5554
0x0000552F:callq 0x555A7E
0x00005534:jmp 0x5563
0x00005536:添加$0x1,%ebx
0x00005539:cmp$0x5,%ebx
0x00005553C:jg 0x555550
0x0000553E:movslq%ebx,%rax
0x00005541:mov(%rsp,%rax,4),%eax
0x00005544:cmp%eax,0x0(%rbp)
0x00005547:jne 0x555536
0x000055549:callq 0x55555A7E
//上面的代码似乎测试了同一性,整数小于等于6
//我不知道下面的代码行是做什么的。从这里。。。
0x0000554E:jmp 0x5536
0x00005550:添加$0x4,%r13
0x000055554:mov%r13,%rbp
0x000055557:mov 0x0(%r13),%eax
0x00005555B:sub$0x1,%eax
0x00005555E:cmp$0x5,%eax
0x00005561:ja 0x552F
0x00005563:添加$0x1,%r14d
0x00005567:cmp$0x6,%r14d
0x0000556B:je 0x5572
0x0000556D:mov%r14d,%ebx
0x00005570:jmp 0x553E
0x00005572:lea 0x18(%r12),%rcx
0x00005577:mov$0x7,%edx
0x0000557C:mov%edx,%eax
0x0000557E:sub(%r12),%eax
0x00005582:mov%eax,(%r12)
0x00005586:添加$0x4,%r12
0x0000558A:cmp%r12,%rcx
0x0000558D:jne 0x557C
0x0000558F:mov$0x0,%esi
0x00005594:jmp 0x55B0
0x00005596:mov 0x8(%rdx),%rdx
0x0000559A:添加$0x1,%eax
0x0000559D:cmp%ecx,%eax
0x00005559F:jne 0x555596
0x0000555A1:mov%rdx,0x20(%rsp,%rsi,8)
0x0000555A6:添加$0x1,%rsi
0x0000555AA:cmp$0x6,%rsi
0x0000555AE:je 0x55C6
0x000055B0:mov(%rsp,%rsi,4),%ecx
0x0000555B3:mov$0x1,%eax
0x0000555B8:lea 0x202c71(%rip),%rdx#0x55758230
0x0000555BF:cmp$0x1,%ecx
0x0000555C2:jg 0x555596
0x0000555C4:jmp 0x5555A1
0x0000555C6:mov 0x20(%rsp),%rbx
0x0000555CB:mov 0x28(%rsp),%rax
0x000055D0:mov%rax,0x8(%rbx)
0x0000555D4:mov 0x30(%rsp),%rdx
0x0000555D9:mov%rdx,0x8(%rax)
0x0000555DD:mov 0x38(%rsp),%rax
0x0000555e2:mov%rax,0x8(%rdx)
0x0000555E6:mov 0x40(%rsp),%rdx
0x0000555EB:mov%rdx,0x8(%rax)
0x0000555EF:mov 0x48(%rsp),%rax
0x0000555F4:mov%rax,0x8(%rdx)
0x0000555F8:movq$0x0,0x8(%rax)
0x00005555600:mov$0x5,%ebp
0x00005555605:jmp 0x555610
//…到这里
//我认为这个区块是比较$rbx,*($rbx+8)。。。。含($rbx)
//但是gdb说不能读取内存*($rbx+8),*(*($rbx+8)+8),…东西。
//只有上面写着$rbx
0x00005555607:mov 0x8(%rbx),%rbx
0x0000555560B:子$0x1,%ebp
0x0000555560E:je 0x555621
0x00005555610:mov 0x8(%rbx),%rax
0x00005555614:mov(%rax),%eax
0x00005555616:cmp%eax,(%rbx)
0x00005555618:jge 0x555607
0x0000555561A:callq 0x555A7E
0x0000555561F:jmp 0x555607
0x00005555621:mov 0x58(%rsp),%rax
0x00005555626:xor%fs:0x28,%rax
0x0000555562F:jne 0x55563E
0x00005555631:添加$0x60,%rsp
0x00005555635:弹出%rbx
0x00005555636:弹出%rbp
0x00005555637:弹出%r12
0x00005555639:弹出%r13
0x0000555563B:弹出%r14
0x0000555563D:retq
0x0000555563E:callq 0x554E90
汇编程序转储结束。
我还尝试了
直到*0x00005555618
ni
来识别流程,但是。。。不知道规则是什么…

我找到了

此阶段具有大小为16字节的链表节点。(注意
mov0x8(%rbx),%rbx
指针跟踪
p=p->next
qword从相对于节点开始的+8偏移量加载

我们可以忽略指针的高位dword,因为它们都是相同的(x86是小端),只需使用默认大小的32位元素,使用GDB
检查
/3x
格式查看每个节点的前3个dword即可

Breakpoint 1, 0x00005555555554fd in phase_6 ()
(gdb) until *0x0000555555555618
0x0000555555555618 in phase_6 ()
(gdb) x/3x $rdx-16
0x555555758230 <node1>: 0x00000189  0x00000001  0x00000000
(gdb) x/3x $rdx
0x555555758240 <node2>: 0x00000113  0x00000002  0x55758230
(gdb) x/3x $rdx+16
0x555555758250 <node3>: 0x0000007f  0x00000003  0x55758240
(gdb) x/3x $rdx+32
0x555555758260 <node4>: 0x000000ff  0x00000004  0x55758250
(gdb) x/3x $rdx+48
0x555555758270 <node5>: 0x000001fd  0x00000005  0x55758260
(gdb) x/3x $rbx
0x555555758110 <node6>: 0x000003b3  0x00000006  0x55758270
如果
节点7-a
的值大于
节点7-b
,程序会说OK。如果不是NO

每个节点的

0x555555758230 <node1>: 0x00000189
0x555555758240 <node2>: 0x00000113
0x555555758250 <node3>: 0x0000007f
0x555555758260 <node4>: 0x000000ff
0x555555758270 <node5>: 0x000001fd
0x555555758110 <node6>: 0x000003b3
0x55758230:
0x555555758230 <node1>: 0x00000189
0x555555758240 <node2>: 0x00000113
0x555555758250 <node3>: 0x0000007f
0x555555758260 <node4>: 0x000000ff
0x555555758270 <node5>: 0x000001fd
0x555555758110 <node6>: 0x000003b3