2010-04-04 7 views
5

Ich schreibe einen MIPS-Assemblercode, der den Benutzer nach dem Dateinamen fragt und einige Statistiken über den Inhalt der Datei erzeugt.Lesen des Dateinamens von Benutzereingabe in MIPS-Assembly

Allerdings, wenn ich den Dateinamen in eine Variable von Anfang an hart Code macht es funktioniert gut, aber wenn ich den Benutzer bitten, den Dateinamen einzugeben, funktioniert es nicht.

Ich habe festgestellt, dass das Programm 0x00 char und 0x0a char (überprüfen asciitable.com) am Ende der Benutzereingabe in den Speicher und deshalb die Datei nicht auf der Grundlage der Benutzereingabe öffnet.

hat jemand eine Idee darüber, wie man diese zusätzlichen Zeichen los wird, oder wie man die Datei öffnet, nachdem sie ihren Namen vom Benutzer bekommen hat ??

hier ist mein kompletter Code (es vom Benutzer Sache außer für die Dateinamen fein arbeitet, und jeder ist frei, es für jeden Zweck ihn/sie will verwenden):

 .data 
fin: .ascii ""  # filename for input 
msg0: .asciiz "aaaa" 
msg1: .asciiz "Please enter the input file name:" 
msg2: .asciiz "Number of Uppercase Char: " 
msg3: .asciiz "Number of Lowercase Char: " 
msg4: .asciiz "Number of Decimal Char: " 
msg5: .asciiz "Number of Words:   " 
nline: .asciiz "\n" 
buffer: .asciiz "" 
     .text 

#----------------------- 
    li $v0, 4 
    la $a0, msg1 
    syscall 

    li $v0, 8 
    la $a0, fin 
    li $a1, 21 
    syscall 

    jal fileRead   #read from file 

    move $s1, $v0   #$t0 = total number of bytes 

    li $t0, 0 # Loop counter 
    li $t1, 0 # Uppercase counter 
    li $t2, 0 # Lowercase counter 
    li $t3, 0 # Decimal counter 
    li $t4, 0 # Words counter 

loop: 
    bge $t0, $s1, end   #if end of file reached OR if there is an error in the file 
    lb $t5, buffer($t0)   #load next byte from file 

    jal checkUpper    #check for upper case 
    jal checkLower    #check for lower case 
    jal checkDecimal   #check for decimal 
    jal checkWord    #check for words 


    addi $t0, $t0, 1   #increment loop counter 

j loop 

end: 

    jal output 
    jal fileClose 

    li $v0, 10 
    syscall 







fileRead: 
    # Open file for reading 
    li $v0, 13  # system call for open file 
    la $a0, fin  # input file name 
    li $a1, 0  # flag for reading 
    li $a2, 0  # mode is ignored 
    syscall   # open a file 
    move $s0, $v0  # save the file descriptor 

    # reading from file just opened 
    li $v0, 14  # system call for reading from file 
    move $a0, $s0  # file descriptor 
    la $a1, buffer # address of buffer from which to read 
    li $a2, 100000 # hardcoded buffer length 
    syscall   # read from file 

jr $ra 

output: 
    li $v0, 4 
    la $a0, msg2 
    syscall 

    li $v0, 1 
    move $a0, $t1 
    syscall 

    li $v0, 4 
    la $a0, nline 
    syscall 

    li $v0, 4 
    la $a0, msg3 
    syscall 

    li $v0, 1 
    move $a0, $t2 
    syscall 

    li $v0, 4 
    la $a0, nline 
    syscall 

    li $v0, 4 
    la $a0, msg4 
    syscall 

    li $v0, 1 
    move $a0, $t3 
    syscall 

    li $v0, 4 
    la $a0, nline 
    syscall 

    li $v0, 4 
    la $a0, msg5 
    syscall 

    addi $t4, $t4, 1 
    li $v0, 1 
    move $a0, $t4 
    syscall 

jr $ra 

checkUpper: 
    blt $t5, 0x41, L1   #branch if less than 'A' 
    bgt $t5, 0x5a, L1   #branch if greater than 'Z' 
    addi $t1, $t1, 1   #increment Uppercase counter 

    L1: 
jr $ra 

checkLower: 
    blt $t5, 0x61, L2   #branch if less than 'a' 
    bgt $t5, 0x7a, L2   #branch if greater than 'z' 
    addi $t2, $t2, 1   #increment Lowercase counter 

    L2: 
jr $ra 

checkDecimal: 
    blt $t5, 0x30, L3   #branch if less than '0' 
    bgt $t5, 0x39, L3   #branch if greater than '9' 
    addi $t3, $t3, 1   #increment Decimal counter 

    L3: 
jr $ra 

checkWord: 
    bne $t5, 0x20, L4   #branch if 'space' 
    addi $t4, $t4, 1   #increment words counter 

    L4: 
jr $ra 

fileClose: 
    # Close the file 
    li $v0, 16  # system call for close file 
    move $a0, $s0  # file descriptor to close 
    syscall   # close file 
jr $ra 

Hinweis: I ist MARS Simulator verwendet wird, wenn das anders

-Update macht: ich das Problem durch das Schreiben und rufen Sie das folgende Verfahren gelöst:

 
nameClean: 
    li $t0, 0  #loop counter 
    li $t1, 21  #loop end 
clean: 
    beq $t0, $t1, L5 
    lb $t3, fin($t0) 
    bne $t3, 0x0a, L6 
    sb $zero, fin($t0) 
    L6: 
    addi $t0, $t0, 1 
j clean 
L5: 
jr $ra 

Antwort

4

Characte r 10 (0xa) ist der Ascii-Code für den Zeilenvorschub, den viele * nix-Betriebssysteme für den Zeilenabschluss verwenden. Es sollte nicht Teil des Dateinamens sein. Einfach abziehen. Auch solche Betriebssysteme verwenden 0 für einen String-Terminator. Es sollte am Ende des Dateinamens sein, es sei denn, der geöffnete Anruf nimmt eine Anzahl von Zeichen Parameter.

Die Lösung ist, die Antwort des Benutzers zu nehmen, Zeichen 10 zu finden und es durch Null zu ersetzen. Verwenden Sie das Ergebnis als den zu öffnenden Dateinamen.

+0

Danke ich das Problem gelöst haben, durch das Schreiben und rufen Sie das folgende Verfahren

 nameClean: \t li $t0, 0 \t \t #loop counter \t li $t1, 21 \t \t #loop end clean: \t beq $t0, $t1, L5 \t lb $t3, fin($t0) \t bne $t3, 0x0a, L6 \t sb $zero, fin($t0) \t L6: \t addi $t0, $t0, 1 j clean L5: jr $ra