1

我的任务是将 IA32 代码转换为 Y86。原始程序是用 C 编写的,旨在获取一个整数数组,其中偶数定位值调用三个函数之一,奇数定位值在该函数内进行操作。这些函数包括数字的否定、数字的平方以及从 1 到提供的数字的总和。

大多数指令都可以轻松地从 IA32 转换为 Y86,但是有许多指令让我非常难受。

0000001e <negation>:
  1e:   55                      push   %ebp
  1f:   89 e5                   mov    %esp,%ebp
  21:   8b 45 08                mov    0x8(%ebp),%eax
  24:   f7 d8                   neg    %eax
  26:   5d                      pop    %ebp
  27:   c3                      ret    

neg 指令不是 Y86 中的有效指令。这就是我在 Y86 中所拥有的:

# int Negation(int x)
Negation:
    pushl %ebp
    pushl %esi
    rrmovl %esp,%ebp
    mrmovl 0x8(%ebp),%eax
    irmovl %esi,$0
    subl %eax, %esi
    rrmovl %esi, %eax
    popl %esi
    popl %ebp
    ret

这是解决这个问题的正确方法吗?

另一个指令是我的平方函数中的 imul 指令:

00000028 <square>:
  28:   55                      push   %ebp
  29:   89 e5                   mov    %esp,%ebp
  2b:   8b 45 08                mov    0x8(%ebp),%eax
  2e:   0f af c0                imul   %eax,%eax
  31:   5d                      pop    %ebp
  32:   c3                      ret 

有谁知道在这种情况下如何转换“imul”指令?

谢谢您的帮助!任何有关 IA32/Y86 转换的提示也将不胜感激。

4

3 回答 3

1

对于实现imul,您可能希望查看使用 shift 并添加例程来实现mul例程:

然后imul只需使用以下步骤:

  • 找出结果应该有什么符号
  • 将操作数转换为绝对值(使用您的否定例程)
  • mul用正值调用你的例程
  • 必要时将结果转换为负数
于 2012-12-01T00:52:19.740 回答
0

1) is mrmovl 0x4(%esp),%eax allowed?

  ixorl %eax, 0xffffffff  
  iaddl %eax, 1  

should be slightly more efficient (also ebp can be used as GPR -- no need to push esi)

2) for multiplication there are indeed shift and add-options,
but also a LUT based approach, exploiting the fact that 4*a*b = (a+b)^2 - (a-b)^2. for each 8x8 bit or NxN bit multiplication.

For a=h<<8+l, B=H<<8|L, aB = Ll + (hL+Hl)<<8 + hH<<16;
could be handled using 3 different tables:
s1[n] = n^2 >>2; s2[n]=n^2 << 6; s3[n]=n^2 << 14;

于 2012-12-01T15:46:29.197 回答
0

对于否定,您反转了 irmovl 指令的操作数。

以下代码有效:

 #
 # Negate a number in %ebx by subtracting it from 0
 #
 Start: 
  irmovl $999, %eax    // Some random value to prove non-destructiveness
  irmovl Stack, %esp   // Set the stack
  pushl %eax           // Preserve 

 Go:
  irmovl $300, %ebx
  xorl %eax, %eax
  subl %ebx,%eax
  rrmovl %eax, %ebx

 Finish:
  popl %eax             // Restore 
  halt

 .pos 0x0100
 Stack: 
于 2015-11-18T02:22:13.100 回答