Academic Integrity: tutoring, explanations, and feedback — we don’t complete graded work or submit on a student’s behalf.

Write MIPS that asks for the user to specify the dimensions of the first matrix,

ID: 3574127 • Letter: W

Question

Write MIPS that asks for the user to specify the dimensions of the first matrix, it then dynamically allocates it and reads double precision numbers to fill it. It then asks for the second matrix dimensions, dynamically allocate and read the double precisions to fill it. It prints out each of the two matrices appropriately labeled. It then determines if they can be added. If so, it dynamically allocates a result matrix, adds the two given matrices putting the answer in the appropriate cells of the result matrix. If the two matrices cannot be added you will print a message that these two matrices cannot be added. You should store the base addresses and dimensions of all two/three dynamically declared arrays in separate static variables i.e. mat1, mat2, result, row1, row2, row3, col1, col2, col3

Subprograms to write:

read_col_matrix: will prompt for height and width of matrix to be allocated. It then validates that both height and width values are greater than zero. If invalid height and width has been entered it will then print an error message and ask for valid dimensions again. It will then call create_col_matrix to allocate the matrix. This subprogram will then prompt user for double precision values and stores them into the matrix allocated by create_col_matrix. This subprogram will store them in column major order. Values will be entered row by row. For example, if the matrix is 2 x 3 and the user enters sequence “11 12 13 21 22 23”, the first row of the matrix will be [11 12 13] and the second row will be [21 22 23].This subprogram has three arguments OUT, the base address of the allocated array, its height and its width.

$sp+0 Holds array base address (OUT)

$sp+4 Holds array base height (OUT)

$sp+8 Holds array base width (OUT)

create_col_matrix: this subprogram This subprogram allocates a dynamic array of double precision numbers given the height and width passed IN and returns base address of array via stack.

$sp+0 Holds array base address (OUT)

$sp+4 Holds array base height (IN)

$sp+8 Holds array base width (IN)

print_col_matrix: this subprogram will receive as arguments IN the base address of matrix, matrix height and width. Then the subprogram will then print the matrix in rectangular format. For example, a 4 x 3 matrix will be printed as 4 rows and 3 columns.

$sp+0 Holds array base address (IN)

$sp+4 Holds array base height (IN)

$sp+8 Holds array base width (IN)

add_col_matrix: This subprogram gets as argument IN base address of first matrix, this matrix height and width and base address of second matrix, its matrix height and width. Then subprogram will validate that dimensions of matrices are equal; if dimensions are not equal then the subprogram will print an error message matrix and return 0 for the result matrix base address, height and width and print out an error message. If dimensions are equal, then subprogram allocates a new matrix with the same dimensions as the given matrices using create_col_matrix. It will then add the first matrix to the second matrix element-by-element and stores the result double precision number into newly allocated matrix. Finally, subprogram returns base address, height and width of resulting matrix.

$sp+0   Holds matrix A array base address (IN)

$sp+4   Holds matrix A base height (IN)

$sp+8   Holds matrix A base width (IN)

$sp+12 Holds matrix B array base address (IN)

$sp+16 Holds matrix B base height (IN)

$sp+20 Holds matrix B base width (IN)

$sp+24 Holds matrix base address of result (OUT)

$sp+28 Holds matrix height of result (OUT)

$sp+32 Holds matrix width of result (OUT)

Explanation / Answer

Solution:

.data
str1:.asciiz "Enter length of array"
arr: .space 40 #10 element integer array
.text
la $a0,str1 #Load and print string asking for string
li $v0,4
syscall
main:
li $v0,8 #take in input
la $a0, buffer #load byte space into address
li $a1, 20 # allot the byte space for string
move $t0,$a0 #save string to t0
li $v1, 9 # Load system instruction to allocate dynamic memory
li $t1, 8 # 8 bytes per element
mult $t0, $t1 # Calculates how big the allocated memory has to be in bytes.
mflo $a0 # Loads this value into $a0
syscall # Allocates memory and returns address into $v0
la $s0, arr # load address of arr into $s0
sw $v1, ($s0) # Save allocated memory address into the space reserved in .text
jal : read_double_array
jal : print_double_array
jal : get_sum_avg
jal : print_less_than
mainEnd:

read_double_array
li $v0, 10
syscall # Halt
  
.text
str2: .asciiz "Enter element"     
read_double_array:

.data
prompt: .asciiz "Input Row "
colon: .asciiz ": "
Output: .asciiz " Output Row "
space: .asciiz " "
newline: .asciiz " "
array: .space 33
char: .space 2

.text

main:

li $t9, 1 # counter for prompt
la $s1, array #set base address of array to s1

# main loop at beginning of the program that prompts for Input row 4 times, each time continuing to take input until a newline character is found
prompt_loop:
beq $t9, 5, finished_input # ends this when we are about to start the 5th iteration
la $a0, prompt #load prompt message into $a0
li $v0, 4 # printstring
syscall
la $a0, ($t9) #load prompt message into $a0 for syscall
li $v0, 1 # printstring
syscall
la $a0, colon # load colon into $a0
li $v0, 4 # printstring
syscall

# read loop deels with newline and spaces by giving control flow away to other places, adapted from Stack Overflow answer about processing strings
# to integers

read_loop: #start of read loop

jal getc #jump to getc subroutine

#storing char into array
lb $t0, char #load the char from char buffer into t0, stripping space

sb $t0, 0($s1) #store the char into the nth elem of array

#checking for end of line
lb $t1, newline #load newline char into t1
beq $t0, $t1, prompt_counter_increase #end of string? jump to finished_looping

#checking for space
lb $t1, space #load newline char into t1
beq $t0, $t1, read_loop # keeps going as though nothing has happened if we run across a space
addi $s1, $s1, 1 # increments base address of array j loop #jump to start of read loop

# get character subroutine found on Stack Overflow and slightly modified
getc: #read char from keyboard buffer and return ascii value
li $v0, 8 # read string
la $a0, char #load address of char
li $a1, 2 # length of string is 1byte char and 1byte for space, defined above already
syscall # store the char byte from input buffer into char
jr $ra #jump-register to calling function, which is back to read_loop

# increments counter after successfully encountering a newline char
prompt_counter_increase:
addi $t9, $t9, 1 # increment counter
j prompt_loop # jumps back to prompt_loop because we need next line

# resets the counter so elements can be spit back out the same order and also loads the array again, pretty much just reset everything
finished_input:
addi $t9, $t9, -4 # resets the counter because the way we have it set up we increment it again to echo everything in the right order
la $s1, array # loads the array back into $s1

# this pretty much does what prompt_loop did but in reverse
output_loop:

beq $t9, 5, end_program # same concept, we have reset $t9 earlier in finished_input
la $a0, Output #load output prompt to $a0
li $v0, 4 # print string
syscall
la $a0, ($t9) # load prompt message into $a0 for syscall
li $v0, 1 # print int
la $a0, colon #load prompt message into $a0
li $v0, 4 # print string
syscall
li $t3, 1 # this counter is used

# turns ascii to int, this method takes our array and reformats it into how it looked when it was input, ie we add spaces
string_to_integer:
beq $t3, 5, output_counter_increase
addi $t3,$t3,1 # increment counter
lb $a0,($s1) # load byte of the first char
lb $t1, newline #load newline char into t1
beq $a0, $t1, end_program #end of string? jump to finished_looping

addi $a0, $a0,-48 # turns ascii to int
li $v0, 1 # print int
syscall
la $a0, space # load prompt message into $a0 for syscall
li $v0, 4 #load syscall to print string
syscall
addi $s1, $s1, 1 #increments base address of array

j string_to_integer # loops back itself

#increments output counter
output_counter_increase:

addi $t9, $t9, 1 #increment
j output_loop # back to the loop again

#ends the program
end_program:

li $v0, 10 #exits
syscall

read_double_array_end:
jr $ra # jump back to the main
.text
print_double_array:


print_double_array_end:
jr $ra # jump back to the main
  
.text
get_sum_avg:


get_sum_avg_end:

  
jr $ra # jump back to the main
.text
print_less_than:

  
print_less_than_end:
jr $ra # jump back to the main

Hire Me For All Your Tutoring Needs
Integrity-first tutoring: clear explanations, guidance, and feedback.
Drop an Email at
drjack9650@gmail.com
Chat Now And Get Quote