Move a square with the keyboard
The receiver registers polled once a frame for w, a, s and d, a direction kept in registers, and a square that keeps going until you steer it somewhere else.
A square you steer. The w, a, s and d keys set which way it is going and it keeps going that
way on its own, coming back in at the opposite edge when it leaves the grid. Click the Screen panel
first: the screen only gets the keyboard when it has the focus, and a ring around it says so while
it does.
A bouncing ball drew a picture that changed on its own. This one asks the keyboard, once per frame, whether anything has been typed, and the answer changes what every frame after it will look like.
You need to know: the "A bouncing ball" Example and the "The bitmap display and the keyboard
registers" lecture. What is new here is the two receiver registers at 0xffff0000, one whose bit 0
says a character is waiting and one that hands it over.
lw t4, 0(s6) reads the receiver control register and andi t4, t4, 1 keeps its Ready bit,
which is 1 when a character is waiting. lw t5, 4(s6) reads the receiver data register, whose
low byte is that character, and reading it takes the character out of the queue and makes room for
the next one. Neither of those is memory: sw and lw are how you talk to a device on this machine,
and the address is what says which one.
Polling once a frame is enough, because what is not read stays in the queue. Ready means "the queue is not empty", so a key pressed between two polls is still waiting at the next one and nothing is lost.
The four key codes are loaded into s8 to s11 before the loop and never touched again. MIPS writes
bne $t5, 'a', not_a and lets its assembler put the 97 into $at for you, one hidden instruction per
key per frame; RISC-V has no such register, so a branch against a character is a li you write, and
the place for it is outside the loop.
The M68K asks a different question. Its task 19 takes four key codes and answers with which of them
are held down at this instant, so a program there can tell that a key is still being held and that
another was let go. The receiver here has no such notion: it hands over characters that were typed,
one at a time, with no key code, no key up and no way to ask what is down now. That is why this
program is written around a direction that persists, and why it takes w, a, s and d and not
the arrow keys, which send nothing a receiver can carry.
The keys do not move the square, they write s4 and s5, and the code under them moves it. That
separation is what makes the square keep going after you let go of the key, and it is how anything
that moves in a game is written: the input decides the velocity, the frame applies it.
Setting the other step to 0 next to each direction is what keeps the movement to four directions.
Take the four li s5, 0 and li s4, 0 lines out and pressing d and then w leaves both steps set,
and the square goes diagonally.
One frame is about 154 instructions, so the runFor of 100000 is around six hundred and fifty of
them. A testcase cannot type into the receiver, so the keys are yours to try by hand.
Try changing li s2, 0 under ble s2, s7, x_low to li s2, LAST. The square stops against the right
edge instead of coming back in at the left, which is the same two instructions doing clamping instead
of wrapping.