MIPS指令练习

Exercise in MIPS instructions

我是 MIPS 的新手,我们在 class 中做了一个练习,我们必须编写一系列 MIPS 指令,如果该位将值“-1”写入 s6 寄存器寄存器 s0 的第七个位置(从右起)为“1”(否则寄存器 s6 保持不变)。假设 s0 的前 16 位全为 0。

供参考(可能有误):

伪代码:

if(s0[10]==1)
  s6 <- -1:

MIPS 指令:

andi $t1, $s0, 0x0040
beq $t1, [=11=], END_IF
addi $s6, [=11=], -1

我真的不明白我们为什么要考虑 s0[9] 以及我们是如何获得 MIPS 指令的。有人可以详细解释它是如何工作的吗?我被告知我们必须制作一个 "mask" 以查看寄存器中是否有位,但目前还不是很清楚。

编辑: if(s0[9]==1) -> if(s0[10]==1)

MIPS 转化为更多人类指令:

$t1 = $s0 bitand 0x00400   # note that 0x00400 is the 10th bit set, so anding s0 against that will give a number that is either 0, or 0x00400 if the 10th bit was set)
if $t1 == 0 -> goto endif
else  $s6 = -1

所以如果第10位没有设置,就去endif,否则设置s6

要了解为什么生成 MIPS 指令来实现您的伪代码,您必须首先了解按位运算的基础知识。在这种情况下,您正在处理 Bitwise AND 操作。按位与是检查某些位是否已设置的好方法。这种检查通常涉及使用所谓的位掩码。位掩码利用布尔逻辑的身份 属性。换句话说,任何与 1 相与的位都保留其值,而与 0 相与的任何位结果为零。考虑以下几个例子:

      01000
(AND) 11000
      -----
      01000


      01010
(AND) 11111
      -----
      01010


      01010
(AND) 00000
      -----
      00000

注意位掩码 11111 如何保留第一个操作数的原始值,而位掩码 00000 总是导致 00000.

现在将此应用于您的问题。如果你想检查是否设置了一个特定的位,比如从最右边的位置开始的第 11 位,那么你可以通过用第 11 位创建一个位掩码来实现 设置为 1,其余设置为零。例如,从十六进制到二进制我们有:

0x400 = 0000010000000000

注意十六进制值0x400中从最右边开始的第 11 位是如何设置为 1 的。请记住,这仅当我们从 1 开始计数时才会发生。

把它们放在一起。要检查 $s0[10] == 1(第 11 位)我们知道我们可以使用十六进制值 0x400 和按位与。如果设置了第 11 位,则 $s0 AND 0x400 的结果应为非零值。否则结果为零。现在让我们了解一下MIPS代码。

andi $t1, $s0, 0x00400  ; perform the AND and store the result in $t1
beq $t1, [=12=], END_IF     ; if $t1 is zero, then the 11th bit must not have been set. BRANCH past the following instruction!
addi $s6, [=12=], -1        ; Ah! We didn't take the branch so the 11th bit was set, so assign -1 to $s6
END_IF:

希望这能澄清您所看到的。

注意 - 这是您最初的要求:“编写一个 MIPS 指令序列,如果该位将值“-1”写入 s6 寄存器寄存器s0的第七位(右起)为“1”(否则寄存器s6不变)

我们可以使用与上面相同的逻辑,但我们需要一个不同的位掩码。检查右起第 7 位的位掩码看起来像 0x40 = 01000000这里根据写法要注意。右起第 7 位表示我们不是从零开始计数。 因此,如果我们编辑位掩码,我们实际上可以使用与以前完全相同的算法。

andi $t1, $s0, 0x40     ; perform the AND and store the result in $t1
beq $t1, [=13=], END_IF     ; if $t1 is zero, then the 7th bit must not have been set. BRANCH past the following instruction!
addi $s6, [=13=], -1        ; Ah! We didn't take the branch so the 7th bit was set, so assign -1 to $s6
END_IF: