assembly - 二元炸弹第三阶段卡住了

标签 assembly x86 gdb reverse-engineering

老实说,我对此感到非常困惑,因为我的炸弹第三阶段看起来不像我的任何同学或我的教授给我的例子。任何帮助将不胜感激。我有一份最近使用的终端的副本,我将 我已经尝试了 5 个小时的大部分时间,我已经足够了解 %d %d 是所请求的布局,并且它要求 2 个数字,我相信其中一个是负数。由于这里的比较语句和jg

   0x08048fbb <+39>:    cmp    $0x1,%eax
   0x08048fbe <+42>:    jg     0x8048fc5 <phase_3+49>

此外,它还要求对相同值进行另一次比较,我认为这是这里的第一个比较

   0x08048fc5 <+49>:    cmpl   $0x7,-0xc(%ebp)
   0x08048fc9 <+53>:    ja     0x8049032 <phase_3+158>

让我失望的是所有的加法和减法,而且一般来说,所有的加法和减法都挤在底部。

如果我只是将我看到的数字相加,我在哪里可以找到在endor中实际与这些语句一起使用的值。此时我什至不知道它是否在盯着我的脸。全部对比如下

   0x08048fbb <+39>:    cmp    $0x1,%eax

0x08048fbe <+42>:jg 0x8048fc5

 0x08048fc5 <+49>:    cmpl   $0x7,-0xc(%ebp)
   0x08048fc9 <+53>:    ja     0x8049032 <phase_3+158>

   0x0804903c <+168>:   cmpl   $0x5,-0xc(%ebp)
   0x08049040 <+172>:   jg     0x8049047 <phase_3+179>

但目前一切都很困惑,我需要用新的眼光来看待这个问题。如果有任何帮助,我们将不胜感激。

That's number 2.  Keep going!
0 1

Breakpoint 1, 0x08048f9a in phase_3 ()
(gdb) disas
Dump of assembler code for function phase_3:
   0x08048f94 <+0>:     push   %ebp
   0x08048f95 <+1>:     mov    %esp,%ebp
   0x08048f97 <+3>:     sub    $0x28,%esp
=> 0x08048f9a <+6>:     lea    -0x10(%ebp),%eax
   0x08048f9d <+9>:     mov    %eax,0xc(%esp)
   0x08048fa1 <+13>:    lea    -0xc(%ebp),%eax
   0x08048fa4 <+16>:    mov    %eax,0x8(%esp)
   0x08048fa8 <+20>:    movl   $0x804a58c,0x4(%esp)
   0x08048fb0 <+28>:    mov    0x8(%ebp),%eax
   0x08048fb3 <+31>:    mov    %eax,(%esp)
   0x08048fb6 <+34>:    call   0x8048894 <__isoc99_sscanf@plt>
   0x08048fbb <+39>:    cmp    $0x1,%eax
   0x08048fbe <+42>:    jg     0x8048fc5 <phase_3+49>
   0x08048fc0 <+44>:    call   0x8049321 <explode_bomb>
   0x08048fc5 <+49>:    cmpl   $0x7,-0xc(%ebp)
   0x08048fc9 <+53>:    ja     0x8049032 <phase_3+158>
   0x08048fcb <+55>:    mov    -0xc(%ebp),%eax
   0x08048fce <+58>:    xchg   %ax,%ax
   0x08048fd0 <+60>:    jmp    *0x804a4c0(,%eax,4)
   0x08048fd7 <+67>:    mov    $0x0,%eax
   0x08048fdc <+72>:    lea    0x0(%esi,%eiz,1),%esi
   0x08048fe0 <+76>:    jmp    0x804902d <phase_3+153>
   0x08048fe2 <+78>:    mov    $0x0,%eax
   0x08048fe7 <+83>:    jmp    0x804902a <phase_3+150>
   0x08048fe9 <+85>:    mov    $0x0,%eax
   0x08048fee <+90>:    xchg   %ax,%ax
   0x08048ff0 <+92>:    jmp    0x8049027 <phase_3+147>
   0x08048ff2 <+94>:    mov    $0x0,%eax
   0x08048ff7 <+99>:    jmp    0x8049024 <phase_3+144>
   0x08048ff9 <+101>:   mov    $0x0,%eax
   0x08048ffe <+106>:   xchg   %ax,%ax
   0x08049000 <+108>:   jmp    0x8049021 <phase_3+141>
   0x08049002 <+110>:   mov    $0x0,%eax
   0x08049007 <+115>:   jmp    0x804901c <phase_3+136>
   0x08049009 <+117>:   mov    $0x30d,%eax
   0x0804900e <+122>:   xchg   %ax,%ax
   0x08049010 <+124>:   jmp    0x8049017 <phase_3+131>
   0x08049012 <+126>:   mov    $0x0,%eax
   0x08049017 <+131>:   sub    $0x264,%eax
   0x0804901c <+136>:   add    $0x3b8,%eax
   0x08049021 <+141>:   sub    $0x49,%eax
   0x08049024 <+144>:   add    $0x49,%eax
   0x08049027 <+147>:   sub    $0x49,%eax
   0x0804902a <+150>:   add    $0x49,%eax
   0x0804902d <+153>:   sub    $0x49,%eax
   0x08049030 <+156>:   jmp    0x804903c <phase_3+168>
   0x08049032 <+158>:   call   0x8049321 <explode_bomb>
   0x08049037 <+163>:   mov    $0x0,%eax
   0x0804903c <+168>:   cmpl   $0x5,-0xc(%ebp)
   0x08049040 <+172>:   jg     0x8049047 <phase_3+179>
   0x08049042 <+174>:   cmp    -0x10(%ebp),%eax
   0x08049045 <+177>:   je     0x804904c <phase_3+184>
   0x08049047 <+179>:   call   0x8049321 <explode_bomb>
   0x0804904c <+184>:   leave
   0x0804904d <+185>:   lea    0x0(%esi),%esi
   0x08049050 <+188>:   ret
End of assembler dump.
(gdb)

最佳答案

您提到的第一个比较( +39 处的比较)正在比较 %eax它保存 sscanf 的返回值。因此,它只是测试可以转换多少参数。此代码需要 2 ,因此该代码正在执行 if (sscanf() > 1) goto ok; explode_bomb();

+49处的比较正在检查第一个数字,它是 if ((unsigned)x > 7) explode_bomb();我希望这是显而易见的。

下一步,地址:+60 ,这段代码中有一条最重要的指令:jmp *0x804a4c0(,%eax,4) 。这是通过跳转表进行跳转。它将带您到不同的位置,具体取决于 %eax 中的值。 ,此时它保存着您的第一个输入。我们知道输入在0之间和7所以该表中有 8 个条目。您应该能够使用 x/8a 0x804a4c0 检查它们。可以合理猜测,它们是以下代码块中的各个地址,并且流程在 +163 处重新加入。 。编译器通常使用此模式来实现 switch声明。

线路+168进一步将第一个数字限制在 0 之间和5 ,和线 +174将第二个数字与 %eax 的当前值进行比较并在不匹配时引爆炸弹。这告诉我们有效输入形成 6 对。我们可以选择任意第一个数字,按照跳转表查看 %eax 中将放置什么值。并将其输入为第二个数字。

关于assembly - 二元炸弹第三阶段卡住了,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/28914722/

相关文章:

linux - 在程序集 ci20 段错误中提示用户输入

performance - 了解 Intel CPU 上的 4K 混叠

assembly - `movl (%eax), %eax`中的括号是什么意思?

linux - 根据 gdb 信息源找不到源文件

ubuntu - Google crashpad 上的一个交叉编译平台应用程序。 Ubuntu 中无法读取 dmp 文件

assembly - "shift operates on bits individually"是什么意思?

assembly - 进入长模式

assembly - 在 8086 汇编(16 位模式)中读取堆栈

linux - 如何通过查看堆栈值生成回溯?

c++ - 来自 libc.so.6 C++ 的 bad_alloc