lendo o nome do arquivo de entrada do usuário na montagem MIPS

votos
5

Eu estou escrevendo um código assembly MIPS que irá perguntar ao usuário o nome do arquivo e vai produzir algumas estatísticas sobre o conteúdo do arquivo.

No entanto, quando eu codificar o nome do arquivo em uma variável desde o início ele funciona muito bem, mas quando eu pedir ao usuário inserir o nome do arquivo não funciona.

depois de alguma depuração, eu descobri que o programa adiciona caractere 0x00 e carvão 0x0A (verifique asciitable.com) no final da entrada do usuário na memória e é por isso que ele não abrir o arquivo com base na entrada do usuário.

Alguém tem alguma idéia sobre como se livrar desses caracteres extras, ou como abrir o arquivo depois de obter o seu nome do usuário ??

aqui é o meu código completo (ele está funcionando bem, exceto para o nome do arquivo a partir de coisa usuário, e qualquer um é livre para usá-lo para qualquer fim que ele / ela quer):

        .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

Nota: eu estou usando MARS Simulator, se isso faz algum diferente

Update: Eu ter resolvido o problema escrevendo e chamando o seguinte procedimento:

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

Publicado 04/04/2010 em 20:01
fonte usuário
Em outras línguas...                            


1 respostas

votos
4

Character 10 (0xA) é o código ASCII para avanço de linha, que muitos sistemas operacionais * nix usar para a linha terminator. Ele não deve ser parte do nome do arquivo. Apenas tira-lo fora. Além disso, esses sistemas operacionais usam 0 para um terminador de string. Deve ser no final do nome do arquivo, a menos que a chamada aberta leva um número de caracteres parâmetro.

A solução é tomar a resposta do usuário, encontrar caráter 10 e substituí-lo com zero. Use o resultado como o nome do arquivo para abrir.

Respondeu 04/04/2010 em 20:08
fonte usuário

Cookies help us deliver our services. By using our services, you agree to our use of cookies. Learn more