1

I'm new to MIPS, and we've done an exercise in class where we have to write a sequence of MIPS instructions that writes the value "-1" to the s6 register if the bit in the seventh position (from the right) of the register s0 is "1" (otherwise the register s6 remains unchanged). It is assumed that the first 16 bits of s0 are all zeros.

For reference (subject to errors):

Pseudocode:

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

MIPS Instructions:

andi $t1, $s0, 0x0040
beq $t1, $0, END_IF
addi $s6, $0, -1

I don't really understand why we are considering s0[9] and how we got the MIPS Instructions. Can someone explain in detail how it works? I've been told that we have to make a "mask" in order to see if there's a bit in the register, but it's not very clear for now.

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

Kevin
  • 427
  • 4
  • 12
  • 1
    Wasn't that first instruction `andi`? – harold Sep 24 '19 at 17:45
  • Yes, it's a typo. Thank you, edited. – Kevin Sep 24 '19 at 17:46
  • 1
    `0x00400` isn't the appropriate bitmask check for the 9th bit. `0x00400` = `0000010000000000`, so clearly here `0x400` sets the 10th bit (if you start counting from 0). Is this code you were provided or something that you came up with, because based on your requirements the MIPS instructions are incorrect as shown. If you can clarify this, I can clarify how it all works. – h0r53 Sep 24 '19 at 17:56
  • 1
    Side note, `0x00200` = `0000001000000000` would be the appropriate check for the 9th bit (again, if you start counting from 0, which is common). – h0r53 Sep 24 '19 at 17:57
  • @CaitLANJenner, you're right, the pseudo-code should be `s0[10]` – Kevin Sep 24 '19 at 18:01
  • Your requirement is still confusing. You say, "if the bit in the seventh position (from the right) of the register s0..." That would mean the pseudo-code should be `s0[6]`. Can you please clarify? – h0r53 Sep 24 '19 at 18:03
  • @CaitLANJenner Thank you for assisting me. I'm not really sure about the pseudo-code part and the MIPS instructions because I think my TA edited the problem at a later time. Can you show me how you'd do that without considering the pseudo-code and the MIPS code I've written? And explaining in detail how it works? Very much appreciated. – Kevin Sep 24 '19 at 18:11

2 Answers2

1

MIPS into more human instructions:

$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

So if the 10th bit is not set, go to endif, otherwise set s6

lostbard
  • 5,065
  • 1
  • 15
  • 17
  • 1
    `0x00400` would not be the 9th bit though. Something is wrong with the originally provided MIPS instructions. – h0r53 Sep 24 '19 at 17:53
1

To understand why the MIPS instructions are produced to implement your pseudo-code you must first understand the basics of bitwise operations. In this case, you are dealing with a Bitwise AND operation. A Bitwise AND is a great way to check to see if certain bits are set or not. Such a check often involves using what is known as a bit mask. Bit masks take advantage of the identity property of boolean logic. In other words, any bit AND'd with a 1 retains its value, while any bit AND'd with a 0 results in zero. Consider the few following examples:

      01000
(AND) 11000
      -----
      01000


      01010
(AND) 11111
      -----
      01010


      01010
(AND) 00000
      -----
      00000

Notice how the bitmask 11111 retains the original value of the first operand, and the bitmask 00000 always results in 00000.

Now applying this to your problem. If you want to check if a particular bit is set, say the 11th bit from the rightmost position, then you can do so by creating a bitmask with the 11th bit set to 1 and the rest set to zero. For example, from hex to binary we have:

0x400 = 0000010000000000

Notice how the 11th bit from the rightmost position is set to 1 in the hexadecimal value 0x400. Remember, this is only if we start counting from 1.

Putting it all together. To check if $s0[10] == 1 (the 11th bit) we know we can use the hex value 0x400 and a bitwise AND. If the 11th bit is set, the result of $s0 AND 0x400 should result in a non-zero value. Otherwise the result is zero. Now let's understand the MIPS code.

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

Hopefully this clarifies what you are seeing.

NOTE - This was your original request: "write a sequence of MIPS instructions that writes the value "-1" to the s6 register if the bit in the seventh position (from the right) of the register s0 is "1" (otherwise the register s6 remains unchanged)"

We can use the same logic as above, but we need a different bitmask. The bitmask for checking the 7th bit from the right would look like 0x40 = 01000000. Here we have to be careful based on the wording. The 7th bit from the right means we are not counting from zero. So we can actually use the exact same algorithm as before if we edit the bitmask.

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