All pastes #269126 Raw Edit

Untitled

public text v1 · immutable
·published 2006-12-06 08:37 UTC
rendered paste body
# Shawn Olson
# Class: C SC 252
# Instructor: Patrick Homer
#
# **prog7.s**
#
# Purpose: Create a recursive subroutine reverseWords that takes in a string and prints the words
# in the string in reverse order

.data
 
mainNumStrings:
        .word 4
mainStrings:
        .word mainStr1
        .word mainStr3
        .word mainStr4
        .word mainStr5
 
mainStr1:   .asciiz "One here With some CapitALS"
mainStr3:   .asciiz "AND ONE THAT IS ALL CAPS"
mainStr4:   .asciiz "and one that is all lower"
mainStr5:   .asciiz ";298stuff297that9872surrounds9782words!!@#$here(*&"
 
mainNewline:
            .asciiz "\n"
 
.text
main:
        # Function prologue -- even main has one
        subu  $sp, $sp, 24       # allocate stack space -- default of 24 here
        sw    $fp, 0($sp)        # save caller's frame pointer
        sw    $ra, 4($sp)        # save return address
        addiu $fp, $sp, 24       # setup main's frame pointer
 
# for (i = 0; i < mainNumStrings; i++ )
#    load address of string into $a0
#    call reverseWords
 
        # $s0 = i
        addi  $s0, $zero, 0
        # $s1 = mainNumStrings
        la    $t0, mainNumStrings
        lw    $s1, 0($t0)
        # $s2 = address of mainStrings
        la    $s2, mainStrings
        
MainLoopBegin:
        slt   $t0, $s0, $s1      # $t0 = $s0 < $s1
        beq   $t0, $zero, MainLoopEnd
        
        # print the string
        lw    $a0, 0($s2)        # $a0 = addr of a string
        li    $v0, 4
        syscall
        la    $a0, mainNewline
        li    $v0, 4
        syscall
        
        # call reverseWords to get the words printed in reverse order
        lw    $a0, 0($s2)
        jal   reverseWords
        la    $a0, mainNewline
        la    $v0, 4
        syscall
        addi  $s0, $s0, 1        # i++
        addi  $s2, $s2, 4        # $s2 += 4, to get addr of next string
        j     MainLoopBegin
 
MainLoopEnd:
 
MainDone:
        # Epilogue for main -- restore stack & frame pointers and return
        lw    $ra, 4($sp)        # get return address from stack
        lw    $fp, 0($sp)        # restore the caller's frame pointer
        addiu $sp, $sp, 24       # restore the caller's stack pointer
        jr    $ra                # return to caller
 
isLetter:
        # Function prologue
        subu  $sp, $sp, 24       # allocate stack space -- default of 24 here
        sw    $fp, 0($sp)        # save caller's frame pointer
        sw    $ra, 4($sp)        # save return address
        sw    $a0, 8($sp)        # preserve $a0
        addiu $fp, $sp, 24       # setup isLetter's frame pointer
 
        addi  $t0, $zero, 0x41   # $t2 = 'A'
        addi  $t1, $zero, 0x5a   # $t3 = 'Z'
        addi  $t2, $zero, 0x61   # $t2 = 'a'
        addi  $t3, $zero, 0x7a   # $t3 = 'z'
 
        addi  $v0, $zero, 0      # $v0 = 0 -- assume char is not a letter
 
        # check upper-case first
        # is the character < 'A'
        slt   $t4, $a0, $t0      # $t4 = $a0 < $t0, $t4 = char < 'A'
        bne   $t4, $zero, isLetterDone
        # is the character > 'Z'
        slt   $t4, $t1, $a0      # $t4 = $t1 < $a0, $t4 = 'Z' < char
        bne   $t4, $zero, isLetterCheckLower
        addi  $v0, $zero, 1      # return 1, since char is upper-case
        j     isLetterDone
 
isLetterCheckLower:
        # check lower-case
        # is the character < 'a'
        slt   $t4, $a0, $t2      # $t4 = $a0 < $t2, $t4 = char < 'a'
        bne   $t4, $zero, isLetterDone
        # is the character > 'z'
        slt   $t4, $t3, $a0      # $t4 = $t3 < $a0, $t4 = 'z' < char
        bne   $t4, $zero, isLetterDone
        addi  $v0, $zero, 1      # return 1, since char is lower-case
 
isLetterDone:
        # Epilogue for isLetter -- restore stack & frame pointers and return
        lw    $a0, 8($sp)        # restore $a0
        lw    $ra, 4($sp)        # get return address from stack
        lw    $fp, 0($sp)        # restore the caller's frame pointer
        addiu $sp, $sp, 24       # restore the caller's stack pointer
        jr    $ra                # return to caller

# Your code goes below this line
.data
ReverseWordsNewLine:        .asciiz  "\n"

.text
reverseWords:

        # prologue
        subu  $sp, $sp, 24       # allocate stack space -- default of 24 here
        sw    $fp, 0($sp)        # save caller's frame pointer
        sw    $ra, 4($sp)        # save return address
        sw    $a0, 8($sp)        # preserve $a0
        addiu $fp, $sp, 24       # setup reverseWords' frame pointer
        subu  $sp, $sp, 40       # allocate space for storing a word

        # $t5 = $sp's location (stores the word)
	add   $t5, $zero, $sp

        # $t6 = read through $a0 as reverseWords checks through the line

	# store $a0 into $t7
	add   $t7, $zero, $a0

	# load the first byte into $t6
	lb    $t6, 0($t7)

	# 1: check the first character in the line until a letter is found
	# 2: once a letter is found, keep adding letters to $t5 until a non-letter is found
	# 3: keep word on stack and call reverseWords again
	# 4: base case: when character == \0, print out the word in $t5

ReverseWordsLoopBegin:

	# if not \0, then check if $t6 is not a letter
	add   $a0, $t6, $zero

	subu  $sp, $sp, 16
	sw    $t5, 8($sp)
	sw    $t6, 4($sp)
	sw    $t7, 0($sp)

	jal   isLetter

	lw    $t7, 0($sp)
	lw    $t6, 4($sp)
	lw    $t5, 8($sp)
	addu  $sp, $sp, 16

	# if it is not a letter, branch to the end of the loop
	beq   $v0, $zero, ReverseWordsEndOfString

	# must be a letter, preserve onto stack allocation and set $t4 to 1
	add   $t4, $zero, 1
	sb    $t6, 0($t5)
	add   $t5, $t5, 1

ReverseWordsLoopBottom:
	# get the next character ready
	add  $t7, $t7, 1
	lb   $t6, 0($t7)

ReverseWordsLoopAgain:
	j ReverseWordsLoopBegin

ReverseWordsEndOfString:

	sb $zero, 0($t5)

	# if $t6 = 0, skip the recursive call
	beq  $t6, $zero, ReverseWordsPrintWord
	add  $a0, $t7, $zero
	jal reverseWords
	
ReverseWordsPrintWord:
	# print out what's on the stack
	add   $a0, $sp, $zero
	li    $v0, 4
	syscall

	la    $a0, ReverseWordsNewLine
	li    $v0, 4
	syscall

	# Epilogue for reverseWords -- restore stack & frame pointers and return
	addu  $sp, $sp, 40       # get back to original $sp starting point
        lw    $a0, 8($sp)        # restore $a0
        lw    $ra, 4($sp)        # get return address from stack
        lw    $fp, 0($sp)        # restore the caller's frame pointer
        addiu $sp, $sp, 24       # restore the caller's stack pointer
        jr    $ra                # return to caller