二元炸弹第4阶段组装

时间:2016-11-09 15:36:06

标签: assembly gdb

我有一个非常相似的问题:Binary Bomb - Phase 4但它仍然不同,我不完全确定该怎么做。

这是我的phase_4代码:

public static function getTickets($conn){
     $sql = "select tickets.*,customers.* from tickets,customers where 
     (tickets.ticket_customer_id = customers.customer_id)  order by tickets.ticket_open_date desc ";
     $st = $conn->query($sql);

     $list = array();
     while($row=$st->fetch(PDO::FETCH_ASSOC)) {
         $list[] = New Tickets($row);
         $columnNames = array_keys($row);
     }

     //total rows of customer
     $totalRows = count($list);
     $columnCount = count($columnNames);

     //pass the values to page
    return (array("results"=>$list ,"totalRows"=>$totalRows,"columnCount"=>$columnCount));
}

这是func_4代码:

 08048d3e <phase_4>:
 8048d3e:       83 ec 2c                sub    $0x2c,%esp
 8048d41:       8d 44 24 18             lea    0x18(%esp),%eax
 8048d45:       89 44 24 0c             mov    %eax,0xc(%esp)
 8048d49:       8d 44 24 1c             lea    0x1c(%esp),%eax
 8048d4d:       89 44 24 08             mov    %eax,0x8(%esp)
 8048d51:       c7 44 24 04 75 a7 04    movl   $0x804a775,0x4(%esp)
 8048d58:       08
 8048d59:       8b 44 24 30             mov    0x30(%esp),%eax
 8048d5d:       89 04 24                mov    %eax,(%esp)
 8048d60:       e8 6b fb ff ff          call   80488d0 <__isoc99_sscanf@plt>
 8048d65:       83 f8 02                cmp    $0x2,%eax //making sure I have 2 inputs
 8048d68:       75 0e                   jne    8048d78 <phase_4+0x3a> //if not explodes bomb
 8048d6a:       8b 44 24 18             mov    0x18(%esp),%eax
 8048d6e:       83 f8 01                cmp    $0x1,%eax //has to be greater than 1
 8048d71:       7e 05                   jle    8048d78 <phase_4+0x3a> //otherwise jumps to bomb
 8048d73:       83 f8 04                cmp    $0x4,%eax
 8048d76:       7e 05                   jle    8048d7d <phase_4+0x3f> //has to be less than 4 or jumps to bomb
 8048d78:       e8 af 05 00 00          call   804932c <explode_bomb>
 8048d7d:       8b 44 24 18             mov    0x18(%esp),%eax
 8048d81:       89 44 24 04             mov    %eax,0x4(%esp)
 8048d85:       c7 04 24 09 00 00 00    movl   $0x9,(%esp)
 8048d8c:       e8 50 ff ff ff          call   8048ce1 <func4> //calls function 4
 8048d91:       3b 44 24 1c             cmp    0x1c(%esp),%eax
 8048d95:       74 05                   je     8048d9c <phase_4+0x5e> //compares two values and explodes bomb if not equal
 8048d97:       e8 90 05 00 00          call   804932c <explode_bomb>
 8048d9c:       83 c4 2c                add    $0x2c,%esp
 8048d9f:       90                      nop
 8048da0:       c3                      ret

我已经检查过以确保输入必须是两位小数,我还可以看到最后两个数字相互比较(8048d97,0x1c(%esp)和%eax)。在phase_4的开头,我认为代码也表明第一个数字必须在1到4之间,而在第4阶段结束时,数字已被修改,它必须等于第二个数字。如果我错了,请纠正我。

我只是不确定func_4正在做什么,以及如何确定输入应该是什么。我认为它可能是二进制搜索,但不确定如何检查它与第一个输入的对应关系。任何帮助将不胜感激!

1 个答案:

答案 0 :(得分:0)

  

func_4正在做什么,以及如何确定输入应该是什么。

 8048d81:       89 44 24 04             mov    %eax,0x4(%esp)
     ; input value loaded to [esp+4] -> [esp+0x24] inside func4
 8048d85:       c7 04 24 09 00 00 00    movl   $0x9,(%esp)
     ; 9 stored to [esp+0] -> [esp+0x20] inside func4
 8048d8c:       e8 50 ff ff ff          call   8048ce1 <func4>
     ; something calculated
     ; then the result is compared with other input value, they should be equal

我不确定,哪个输入是哪个(你知道sscanf和你的ABI的格式字符串,所以你可以更好地说明,存储在[esp + 0x18]中并且测试为2的值,在计算中使用了3或4,只是比较了存储在[esp + 0x1c]中的那个。我猜想计算的输入是秒(对于sscanf在+ 0x0c,另一个在+ 0x08)?所以密码是& #34; <func4(9,2-4)> <2-4>&#34;

由于func4是干净的asm递归代码,你可以为所有三个可能的输入运行它,看看它产生了什么结果(在调试器中,踩过指令,所以你设法捕获一些参数导致无限循环或一些其他的肮脏,加上你会知道它是如何工作的。)

然后找出哪个输入。

  

不确定func_4正在做什么

嘿,这就是装配工作的方式。您很少查看指令流,并快速浏览它们中的算法。更常见的是,你需要通过指令彻底模拟头部指令中的CPU状态,注意每个细节(比如通过指令改变标志,看起来只用于设置值,然后稍后指示保留标志用于条件通过保持计算值的某些时间线,通常可以猜测实现的算法。

或者如果不是算法,那么至少要知道计算出什么值。

我再次检查了代码,看起来像Fibonnaci主题的变体,如func4(0,x) = 0func4(1,x) = xfunc4(y, x) = (只是快速猜测,太懒了)验证我做对了) x + func4(y-1, x) + func4(y-2, x)

编辑:我现在确定公式不正确,至少缺少一个常量(但可能更糟糕)。

所以我想知道,你是否懒得费心去模拟CPU并获得正确的结果,或者你对某些特定指令有问题,它究竟做了什么(即你懒得阅读指令参考指南)?所以它归结为&#34;你是懒惰还是懒惰?&#34;因为我绝对都是,所以这是我对你的问题的回答。 :)

如果您不了解某些指示的某些特定细节,请询问。

编辑评论:

  

&#34; //必须小于4或跳到炸弹&#34;

不,它是jle,&#34;跳过的签名少于/等于&#34;,所以正确的评论是&#34;必须少于等于4&#34;这对值[TYPE_MIN,4]有效。

对于&#34;少于4&#34;你需要使用jl =&#34;跳过签名更少&#34;。

对于&#34;少于4&#34;那里没有签名jb =&#34;跳到&#34;以下,它涵盖了值[0,3]。 jbe涵盖[0,4]值。

如果要检查Jcc description,您将看到这些条件跳转仅基于标志寄存器中的少数标志,仅此而已(jcxz/jecxz除外,它比较cx寄存器并且不会#39; t触摸旗帜。)

此外,您可能会注意到有几个别名,因此您可以在代码中写入符合您目的的代码。例如jzje是相同的指令,第一个别名代表&#34;当零(标志)&#34;时跳转,另一个是#34;等于&#34; 。因此,通读它并习惯这些缩写,它将使拆卸的阅读更容易一些。

  

//调用函数4

这无用的评论,从指令本身来看是显而易见的。你会添加例如参数(9,input_2),这对读者来说会更有益。

下一个&#34;比较&#34;评论具有类似无用的性质。两个数字是什么?如果你已经对它们进行了追踪,那么你应该把这个结果写成注释,这样就像&#34;比较func4的结果和input_1&#34;。

我将尝试向您展示func4:

的示例
 8048ce1 <func4>:
  ; allocates 0x1c bytes on stack for local variables
  ; (so return address is at [esp+0x1c] now, was at [esp])
 8048ce1:       83 ec 1c                sub    $0x1c,%esp
  ; stores current ebx, esi and edi in [esp+0x10 / 0x14 / 0x18]
 8048ce4:       89 5c 24 10             mov    %ebx,0x10(%esp)
 8048ce8:       89 74 24 14             mov    %esi,0x14(%esp)
 8048cec:       89 7c 24 18             mov    %edi,0x18(%esp)
  ; esi = [esp+0x20] = first argument of func4(arg1, arg2)
 8048cf0:       8b 74 24 20             mov    0x20(%esp),%esi
  ; ebx = [esp+0x24] = second argument of func4(arg1, arg2)
 8048cf4:       8b 5c 24 24             mov    0x24(%esp),%ebx
  ; when esi(arg1) <= 0, jump to ExitWith0
 8048cf8:       85 f6                   test   %esi,%esi
 8048cfa:       7e 2b                   jle    8048d27 ExitWith0
  ; when esi(arg1) == 1, jump to ExitWithValueFromEbx
 8048cfc:       83 fe 01                cmp    $0x1,%esi
 8048cff:       74 2b                   je     8048d2c ExitWithValueFromEbx
  ; store arg2 in [esp+4]
 8048d01:       89 5c 24 04             mov    %ebx,0x4(%esp)
  ; store (arg1-1) in [esp] (preparing args for recursive call)
 8048d05:       8d 46 ff                lea    -0x1(%esi),%eax
 8048d08:       89 04 24                mov    %eax,(%esp)
  ; recursion: eax = func4(arg1-1, arg2) ; ebx/esi/edi preserved
 8048d0b:       e8 d1 ff ff ff          call   8048ce1 <func4>
  ; edi = eax (result) + ebx*1 (arg2)
 8048d10:       8d 3c 18                lea    (%eax,%ebx,1),%edi
  ; [esp+4] is set to arg2 again
  ; (it's still there, but this asm looks like debug level of C, not very efficient)
 8048d13:       89 5c 24 04             mov    %ebx,0x4(%esp)
  ; esi -= 2 (no more original arg1 in esi), and set [esp+0]
 8048d17:       83 ee 02                sub    $0x2,%esi
 8048d1a:       89 34 24                mov    %esi,(%esp)
  ; second recursive call: func4(arg1-2, arg2)
 8048d1d:       e8 bf ff ff ff          call   8048ce1 <func4>
  ; ebx = edi + eax*1 ; edi was arg2 + f4(arg1-1, arg2)
 8048d22:       8d 1c 07                lea    (%edi,%eax,1),%ebx
  ; so ebx = arg2 + f4(arg1-1, arg2) + f4(arg1-2, arg2), return that value
 8048d25:       eb 05                   jmp    8048d2c ExitWithValueFromEbx
ExitWith0:
 8048d27:       bb 00 00 00 00          mov    $0x0,%ebx
ExitWithValueFromEbx:
 8048d2c:       89 d8                   mov    %ebx,%eax
  ; restore values of ebx/esi/edi (return value is in eax)
 8048d2e:       8b 5c 24 10             mov    0x10(%esp),%ebx
 8048d32:       8b 74 24 14             mov    0x14(%esp),%esi
 8048d36:       8b 7c 24 18             mov    0x18(%esp),%edi
  ; restore esp value, so [esp] is return address, and return
 8048d3a:       83 c4 1c                add    $0x1c,%esp
 8048d3d:       c3                      ret

所以我在答案中确实猜到了,那些,1)在lea中迷惑了我,我不熟悉AT&amp; T语法,所以在一个较弱的时刻我认为&#39; s + 1到结果,但它是* 1到索引寄存器(我习惯于英特尔语法,它看起来像lea ebx,[edi+eax])。

但正如您所看到的,一旦您开始记下笔记,并专注于单一指令,我确实设法在这次正确解读。

目前,确保理解每条指令对您来说非常重要,我指的是每一个细节,例如lea如何工作以及为什么它不读取内存值,即使参数是(...),什么是所有可能的寻址模式(如果你想做f(a,b)= 1 + b + f(a-1,b)+ f,它会是什么样子( a-2,b)?尝试找到一个,只需要修改一个lea(这两个中的任何一个))。

我不确定你有什么文献,因为我使用了英特尔语法的一切(我认为AT&amp; T语法对C编译器有好处,但对人类来说并不是那么多......但总体而言#39 ;不是那么糟糕,如果你已经知道另一个,那么大多是烦人的,如果你只知道AT&amp; T,那可能就行了。)

在最坏的情况下问一下,虽然有关说明目的的问题是&#34;省力&#34;,因为所有x86手册都是免费提供的,但是如果你不确定某些措辞的真正意义,并且运行这样的指令很少调试器中的时间没有帮助,你必须要问。只需添加您的想法以及令您困惑的词语。