| CompOrg Fall 2001 |
|   Assignment   |   Stuff you need to know   |   What and How to submit   |   Grading   |   Notes and Hints |
Write a MIPS assembly language program (that will run under SPIM) that displays the contents of a sequence of memory locations. When the program starts, the user should be prompted for a starting address (through the SPIM console window). The 32 bit address and the contents of the 32 bit word at the selected address should be dispayed on one line. All addresses and values are to be specified/displayed as 8 Hex digits. The user should then be able to view the next word in memory by pressing the Enter key, or quit the program by pressing 'q'. The program should continue to allow the user to sequence through memory in the same manner.
Below are some screenshots of what is expected. Initially the program prompts the user for a starting address:

The user now enters a 32 bit address in hex (8 hex digits).

Now the program should display the starting address as an 8 hex digit number, followed by a colon and a space, and then the contents of the memory location (also as an 8 digit hex number).

Now the program should read a character from the user, and if the character is 'q' the program should stop. If anything other than 'q' is entered, the program should display the next word in memory. Each time a new word is displayed (with it's address), the program should read a character, stopping only when the user enters a 'q'. Here is what the result should look like:

NOTE: whatever character the user types will appear at the end of each line - in the above example the user pressed Enter on all the lines except the last one, and the 'q' on the last line is what stopped the program.
When reading or printing HEX digits, you only need to support capitals, so you can expect FE03D210, but you don't need to handle fe03d210.
SPIM will not like it if your program tries to access some
addresses, for example if the user types an address that is not word
aligned (the address is not a multiple of 4) and you attempt to do a
lw from such an address - SPIM will complain. SPIM also
will complain if the address is not part of the address space that
SPIM emulates, for example the address 00000000 seems to give SPIM
trouble. We will test your program with only word-aligned addresses
that are valid (something displayed in the DATA or TEXT window of
SPIM). You should assume that whatever address you are given by the
user is valid - no error checking is necessary.
When reading the starting address you can expect a valid address
entered as exactly 8 hex digits. All values displayed by your program
must be 8 hex digits (the value 0 should be displayed as
00000000).
The MIPS instruction set, including the pseudoinstructions supported by SPIM. Appendix A of the text includes a reference.
The syscall I/O support provided by SPIM - this is also
documented in Appendix A (and in the SPIM documentation).
How to convert a 32 bit value (the contents of a register) to
a string of ASCII encoded HEX digits. For example, you will need to be
able to convert the binary value 0001 0010 0010 1101 0011 0111 0000 1111
to the string "122D370F" so you can print it.
How to convert a ASCII encoded string composed of 8 hex digits to a binary value that you can put in a register.
How to write MIPS subroutines! Without any subroutines this program would require thousands of instructions (your program would be thousands of lines long). Subroutines are required!
You should submit your program (the source code for your program),
along with a file named README that contains a brief
(one line) description of each subroutine you write.
Email your submission to comporg-submit@cs.rpi.edu with the subject line "HW4".
Assembly language is very hard to read! Make sure you provide lots of comments to help us. It's a good idea to summarize each subroutine with some comments that indicate what the arguments are and what/where the return value is. For example, here is a sample:
# ------------------------- # subroutine hex_to_binary # converts a single ASCII hex digit to 4 bits # input: the ASCII hex digit is passed in the LS byte of $a0 # output: the result is returned as the 4 LS bits of $v0 # hex_to_binary: ...code goes here...
Grades will be determine by:
Note that you are required to use subroutines, and that your grade depends on how well you do this. There should not be large chunks of code that are duplicated in your program - if you find yourself doing this you should wrap the code in a subroutine and call it from many places (instead of duplicating the code many times...)
In HW#1 you could ask printf to format numbers in hex for you. There is no similar function in SPIM - you need to write this. Much of the code required involves this conversion of ASCII hex digits to and from binary values. Here is how I divided this part of my program in to subroutines - you don't need to mimic my subroutines, but in case you are lost this may be a good starting point:
nibble_to_hex: converts a 4 bit binary value to
an ASCII hex digit. For example, converts 1010 to
'A'.
byte_to_hex: converts an 8 bit binary value to
2 ASCII hex digits. (uses nibble_to_hex)
word_to_hex: converts a 32 bit binary value to
a string of 8 ASCII hex digits. (uses byte_to_hex)
hex_to_nibble: converts a single ASCII hex digit
to a 4 bit binary value.
hex_to_byte: converts 2 ASCII hex digits to
n 8 bit binary value. (uses hex_to_nibble)
hex_to_word: converts an string of 8 ASCII hex digits to
a 32 bit binary value. (uses hex_to_byte)
None of these subroutines is very large.
NOTE: A nibble is a 4 bit quantity (half of a byte)
To read a single character you can use the syscall to read a
string, and set the string length to 2 (you need to include room for
the terminating null). The syscall will return as soon as
a single key is pressed.
You can use character literals as constants, for example, you can do this:
add $t0,$t0,'0'
The above would add the ASCII code for the character '0' to the
contents of register $t0. So you don't need to know the
ASCII code for '0', you can just use '0'.