首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >炸弹实验室phase_4

炸弹实验室phase_4
EN

Stack Overflow用户
提问于 2014-10-11 13:54:55
回答 1查看 6.2K关注 0票数 2
代码语言:javascript
复制
Dump of assembler code for function func4
    <+0>: mov %rbx,-0x18(%rsp)
    <+5>: mov %rbp, -0x10(%rsp)
    <+10>: mov %r12,-0x8(%rsp)
    <+15>: sub $0x18,%rsp
    <+19>: mov %edi,%ebx
    <+21>: mov %esi,%ebp
    <+23>: test %edi, %edi
    <+25>: jg 0x400fb2<func4+34>
    <+27>: mov $0x0,%ebp
    <+32>: jmp 0x400fd2<func4+66>
    <+34> cmp $0x1, %edi
    <+37>: je 0x400fd2<func4+66>
    <+39>: lea -0x1(%rbx),%edi
    <+42>: callq 0x400f90 <func4>
    <+47>: mov %eax,%r12d
    <+50>: lea -0x2(%rbx),%edi
    <+53>: mov %ebp,%esi
    <+55>: callq 0x400f90 <func4>
    <+60>: lea (%r12,%rax,1),%eax
    <+64>: add %eax,ebp
    <+66>: mov %ebp, %eax
    <+68>: mov (%rsp),%rbx
    <+72>: mov 0x8(%rsp), %rbp
    <+77>: mov 0x10(%rsp),%r12
    <+82>: add $0x18,%rsp
    <+86>: retq

这是func4的反汇编代码。我不确定我是否正确地理解了这个函数。

这里我没有编写phase_4的反汇编代码,但是它需要"%d %d“的输入,第一个整数应该在1<=x<4范围内,所以应该是1,2,或者3。注册%edi最初的值是7。调用func4之后,代码会比较0x10(%rsp)和%eax的值,因此我应该知道func4调用后的%eax值。

我想,func4的分解代码意味着

代码语言:javascript
复制
put the stack
ebx = edi
ebp = esi
if edi is not zero
    if edi is one: then eax=ebp.
                   rearrange the stack
                   return.
    else: edi = -0x1(rbx)
          func4
          r12d = eax
          edi = -0x2(rbx)
          esi = ebp
          func4
          eax = rax+r12+ebp
          rearrange the stack and return.
else
    ebp=0
    eax=ebp
    return

但以我的理解我解决不了这个问题。例如,如果%rsp的原始地址为0x7fffffffd5a8,则该地址将更小,直到edi的值变为0。我发现0x7fffffd56f的值是0--第一个func4调用结束--但是在0x7fffffffd56e的值之后--所以第二个func4调用结束--所有寄存器都变成0,包括eax。

所以我认为第二个数的答案是零,但是(1,0),(2,0),(3,0)总是爆炸炸弹。

你猜我哪里错了,帮我?

EN

回答 1

Stack Overflow用户

回答已采纳

发布于 2014-10-11 16:16:18

ediesifunc4的两个参数。这是根据标准的调用约定,但也可以从这样的事实推断,这些寄存器是使用没有初始化,因此它们的值必须来自外部。因此,原型是int func4(int a, int b)

+23检查是否a > 0,如果是,则跳转。因此,我们可以很容易地跟踪如果条件为false会发生什么:

代码语言:javascript
复制
if (a <= 0) return 0;

+34正在检查是否a == 1,如果是,则返回ebp的当前值,但这是从esi (第二个参数b )初始化的。

代码语言:javascript
复制
if (a == 1) return b;

否则,行+39.+55递归调用func4。行+60将两个调用的结果一起添加,而行+64则添加b。所以我们有:

代码语言:javascript
复制
return func4(a - 1, b) + func4(a - 2, b) + b;

由此,您可以计算任何输入的返回值。

当然,如果允许使用调试器,只需让代码运行并查看eax的值;)

票数 2
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/26315403

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档