All pastes #416235 Raw Edit

Stuff

public text v1 · immutable
#416235 ·published 2007-03-30 04:21 UTC
rendered paste body
# Shawn Olson
# C SC 252
# Instructor: Patrick Homer
#
# **prog4.s**
#
# Purpose: Create a subroutine convert that takes in an ascii string and takes any
# prepending spaces or tabs out of the phrase, and replaces any capital letters with
# lower case letters. This subroutine also outputs the number of characters read in
# and gives them to the main method.

.data
 
mainNumPhrases:
        .word  3
 
mainPhrases:
        .word  mainPhrase1
        .word  mainPhrase2
        .word  mainPhrase3
 
mainPhrase1:
        .asciiz "A man, a plan, a canal, Panama!"
mainPhrase2:
        .asciiz "   CSc252 -- Computer Organization  "
mainPhrase3:
        .asciiz "            Three Tabs To StarT This Line    "
 
mainOriginalStr:
        .asciiz "The original string:\n"
mainTotalStr:
        .asciiz "Total character count: "
 
mainNewline:
        .asciiz "\n"
 
.text
main:
         # Function prologue -- even main has one
         subu  $sp, $sp, 24       # allocate stack space
         sw    $fp, 0($sp)        # save frame pointer of caller
         sw    $ra, 4($sp)        # save return address
         addiu $fp, $sp, 24       # setup frame pointer of main
 
         la    $t0, mainNumPhrases
         lw    $s0, 0($t0)        # $s0 = mainNumPhrases
 
         # skip everything if there are no phrases
         beq   $s0, $zero, mainDone
 
         # for i = 0 to mainNumPhrases - 1
         #   print phrase
         #   call convert
         addi  $s1, $zero, 0      # $s1 = i
         la    $s2, mainPhrases   # $s2 = mainPhrases[i]
         lw    $s3, 0($s2)        # $s3 = address of current phrase
         addi  $s4, $zero, 0      # $s4 = character count = 0
 
mainLoopBegin:
         # if i < mainNumPhrases
         slt   $t3, $s1, $s0      # $t3 = i < mainNumPhrases
         beq   $t3, $zero, mainLoopEnd
 
         # print the current phrase
         la    $a0, mainOriginalStr
         li    $v0, 4
         syscall
         addi  $a0, $s3, 0        # $a0 = address of current phrase
         li    $v0, 4
         syscall
         la    $a0, mainNewline
         la    $v0, 4
         syscall
        
         # Startup Sequence:
         addi  $a0, $s3, 0        # $a0 = address of current phrase
         jal   convert
         # Clean up: get count of characters
         add   $s4, $s4, $v0      # $s4 += count
        
         # print blank line
         la    $a0, mainNewline
         li    $v0, 4
         syscall
        
         addi  $s1, $s1, 1        # i++
         addi  $s2, $s2, 4        # $s2 = address of next phrase
         lw    $s3, 0($s2)        # $s3 = next phrase
         j     mainLoopBegin
        
mainLoopEnd:
         # print the total character count
         la    $a0, mainTotalStr
         li    $v0, 4
         syscall
         addi  $a0, $s4, 0
         li    $v0, 1
         syscall
         la    $a0, mainNewline
         li    $v0, 4
         syscall
 
mainDone:# Epilogue for main -- restore stack & frame pointers
         lw    $ra, 4($sp)        # get return address from stack
         lw    $fp, 0($sp)        # restore frame pointer of caller
         addiu $sp, $sp, 24       # restore stack pointer of caller
         jr    $ra                # return to caller
 
.data
printLineNewline:
         .asciiz "\n"
printLineModifiedStr:
         .asciiz "The modified string:\n"
.text
printLine:
         # Function prologue
         subu  $sp, $sp, 24      # allocate stack space
         sw    $fp, 0($sp)       # save frame pointer of caller
         sw    $ra, 4($sp)       # save return address
         sw    $a0, 8($sp)       # save the address of the string
         addiu $fp, $sp, 24      # setup frame pointer for printLine
 
         la    $a0, printLineModifiedStr
         li    $v0, 4
         syscall
         lw    $a0, 8($sp)
         li    $v0, 4
         syscall
         la    $a0, printLineNewline
         li    $v0, 4
         syscall
 
printLineDone:
         # Epilogue for printLine -- restore stack & frame pointers
         lw    $a0, 8($sp)        # restore the address of string
         lw    $ra, 4($sp)        # get return address from stack
         lw    $fp, 0($sp)        # restore frame pointer of caller
         addiu $sp, $sp, 24       # restore stack pointer of caller
         jr    $ra                # return to caller
 
# Your code goes below this line
.data
TestText:	.asciiz	"stuff"
.text
convert:

	subu	$sp, $sp, 24
	sw	$fp, 0($sp)
	sw	$ra, 4($sp)
	addiu	$fp, $sp, 24

ConvertCheckWhiteSpaceStart:

	lb	$t7, 0($a0)
	beq	$t7, 9, ConvertWhiteSpace
	beq	$t7, 32, ConvertWhiteSpace

	# not white space, start with the actual program
	j ConvertStartForReal

ConvertWhiteSpace:
	add	$a0, $a0, 1
	j ConvertCheckWhiteSpaceStart

ConvertStartForReal:

	# beginning of string -- store $a0's address into $t7 and use $t6 to traverse
	add	$t7, $a0, $zero

	# add 0x00000040 and 0x0000005a to $t4 and $t2, respectively
	addi	$t4, $zero, 65
	add	$t2, $zero, 0x0000005b

	add	$t7, $a0, $zero
	la	$a0, 0($t4)
	li	$v0, 4
	syscall
	
	add	$a0, $t7, $zero

	# use $t0 as a counter
	add	$t0, $zero, $zero
	
ConvertCheckForCapitalsStart:
	lb	$t6, 0($t7)

	# increment $t0
	addi	$t0, 1
	
	# break out of loop if $t6 is 0
	beq	$t6, $zero, ConvertCheckLoopFinished

	# check to see if the byte in $t6 is less than $t4 (capital A)
	slt	$t5, $t6, $t4
	bne	$t5, $zero, ConvertGoToEnd

	# greater than capital A, check if it is less than $t2 (capital Z +1)
	slt	$t5, $t2, $t6
	bne	$t5, $zero, ConvertGoToEnd

	# if it gets here, then it was a capital, therefore, add 32 to $t6
	add	$t6, $t6, 32
	sb	$t7, 0($t6)

ConvertGoToEnd:

	# store the byte at $t6 into $t7
	sb	$t6, 0($t7)
	
	# add 1 to $t7 to move on
	add	$t7, $t7, 1
	j ConvertCheckForCapitalsStart

ConvertCheckLoopFinished:

	# loop is finished, therefore, send the print function $a0
	add	$v0, $t0, $zero
	jal printLine

	# end sequence
	subu	$fp, $sp, 24
	lw	$ra, 4($sp)
	lw	$fp, 0($sp)
	addu	$sp, $sp, 24