2014-04-22 4 views
0

현재 수행중인 프로그램에서 사용자가 입력 한 문자열을 뒤집어 써야합니다. 나는 사용자가 입력 한 단어를 입력해야하며, 바로 아래에 단어를 역순으로 인쇄하고 싶습니다. 내가 Tasm 컴파일러와 함께 DOSBox에서 실행하려고하면, "잘못된 메모리 참조"라는 줄을 189 번에서 역전 된 단어를 넣을 변수가 들어있는 줄을 제공합니다. 누군가 내가 알아낼 수있게 도와 줄 수 있습니까? 내가 뭘 잘못하고 있니? 나는 그것을 매우 감사 할 것이다! 또한 내 프로그램에만 4 상자가 있습니다. 첫 번째 상자에서 프롬프트 아래에 역 단어를 인쇄하려고합니다. 나머지 상자는 사용자가 입력 한 단어를 역순으로 인쇄합니다.어셈블리 언어로 문자열 반전하기 80x86

title  fill in title   ;program name 
    ;------------------------------------------------------------------ 
    stacksg segment para stack 'Stack' ;define the stack 
    db 32 dup(0) ;32 bytes, might want larger 
    stacksg ends 
    ;------------------------------------------------------------------ 
    datasg segment para 'Data' ;data segment 

    paralst Label Byte 
    maxlen db 21 
    actlen db ? 
    dbdata db 21 dup('$') 
    outit db 'Enter String: $' ;14 chars minus $ 
    switch db 21 dup('$') 
    datasg ends 
    ;------------------------------------------------------------------ 
    codesg segment para 'Code' ;code segment 
    main proc far  ;main procedure 
assume ss:stacksg, ds:datasg, cs:codesg ;define segment registers 
mov ax, datasg ;initialize data segment register 
mov ds, ax 

    ;--------------- --------------------------top left corner 
mov ah, 06h 
mov al, 00 
mov bh, 01000001b ; 4eh 
mov ch, 0 
mov cl, 0 
mov dl, 39 
mov dh, 12 
int 10h 
    ;-------------------------------------------top right corner 
mov ah, 06h 
mov al, 0 
mov bh, 11110010b 
;mov cx, 0c00h 
;mov dx, 184fh 
mov ch, 0 
mov cl, 39 
mov dh, 12 
mov dl, 79 
int 10h 
    ;--------------------------------------------bottom left corner 
mov ah, 06h 
mov al, 0 
mov bh, 11100100b ;yellow 
mov ch, 12 
mov cl, 0 
mov dh, 24 
mov dl, 39 
int 10h 
    ;------------------------------------------bottom right corner 
mov ah, 06h 
mov al, 0 
mov bh, 01011111b ; magenta 80 
mov ch, 12 
mov cl, 39 
mov dh, 24 
mov dl, 79 
int 10h 


    ;--------------------------------------------------- 1st quad 
mov ah, 02h 
mov bh, 0 
mov dh, 5 
mov dl, 5 
int 10h 
mov ah, 09h 
lea dx, outit 
int 21h 
    ;------------------------------------input 
mov ah, 0ah 
lea dx, paralst 
int 21h 
    ; -----------------------------------move cursor 
mov ah, 02h 
mov bh, 0 
mov dh, 7 
mov dl, 5 
int 10h 
call REVERSE 
    ;--------------------------------------print output 
mov ah, 09h 
lea dx, switch 
int 21h 
    ;----------------------------------------------------2nd quad 
mov ah, 02h 
mov bh, 0 
mov dh, 5 
mov dl, 44 
int 10h 
mov ah, 09h 
lea dx, outit 
int 21h 

    ;------------------------------------input 
mov ah, 0ah 
lea dx, paralst 
int 21h 
    ; -----------------------------------move cursor 
mov ah, 02h 
mov bh, 0 
mov dh, 7 
mov dl, 44 
int 10h 
    ;--------------------------------------print output 
mov ah, 09h 
lea dx, dbdata 
int 21h 


    ;------------------------------------------------------3rd quad 
mov ah, 02h 
mov bh, 0 
mov dh, 17 
mov dl, 5 
int 10h 
mov ah, 09h 
lea dx, outit 
int 21h 

    ;------------------------------------input 
mov ah, 0ah 
lea dx, paralst 
int 21h 
    ; -----------------------------------move cursor 
mov ah, 02h 
mov bh, 0 
mov dh, 19 
mov dl, 5 
int 10h 
    ;--------------------------------------print output 
mov ah, 09h 
lea dx, dbdata 
int 21h 

    ;------------------------------------------------------4th quad 
mov ah, 02h 
mov bh, 0 
mov dh, 17 
mov dl, 44 
int 10h 
mov ah, 09h 
lea dx, outit 
int 21h 


    ;------------------------------------input 
mov ah, 0ah 
lea dx, paralst 
int 21h 
    ; -----------------------------------move cursor 
mov ah, 02h 
mov bh, 0 
mov dh, 19 
mov dl, 44 
int 10h 
    ;--------------------------------------print output 
mov ah, 09h 
lea dx, dbdata 
int 21h 


mov ax, 4c00h ;end processing 
int 21h 

    main endp  ;end of procedure 
    ;----------------------------------------reverse procedure 
    REVERSE PROC NEAR 
mov cx, 0 
    ;-----figure out actlen here 
mov actlen, 0 
lea bx, dbdata ;may need to use paralst instead 
hi: cmp [bx], '$' 
jne sup 
inc actlen 
inc bx 
jmp hi 
sup: 

    ;------------ 
mov cx, 0 
mov cl, actlen 
lea bx, dbdata 
add bx, cx 
yo: cmp actlen, 0 
je hola 
mov switch, byte ptr[bx] 
dec bx 
inc switch 
dec actlen 
jmp yo 
hola: 

RET 
REVERSE ENDP 
    codesg ends  ;end of code segment 
    end main ;end of program 

답변

0

mov memory, memory 할 수 없습니다. 소스를 먼저 레지스터로 옮긴 다음 대상에 놓습니다.
또한 inc switch은 자신이 생각하는 것처럼 보이지 않습니다. 런타임에 switch의 주소를 변경할 수 없으므로 실제로 일어나고있는 것은 첫 번째 요소 인 switch (예 : inc [switch]으로 작성한 것)으로 증가시키고 있다는 것입니다. 주소를 수정해야하는 경우; 다시 레지스터에 넣으십시오. 그래서 예를 들면

:

lea si, dbdata 
add si,cx 
lea di, switch 
mov al,[bx] 
jcxz hola  ; jump if cx == 0 
cld    ; clear the direction flag; for stosb 
yo: mov al,[si] 
stosb   ; [di++] = al 
dec si 
loop yo   ; if (--cx) jmp yo 
hola: 

내가 코드의 전체 조각을 보이지 않았다, 그래서 역방향이 종료 ('$') 여부를 복사하도록되어 있는지 나에게 불분명하다. 필요한 경우 적어도 한 번 루프를 실행해야합니다 (그러면 jcxz이 필요하지 않습니다). 그렇지 않으면 소스 주소를 dbdata + cx 대신 dbdata + cx - 1으로 설정해야합니다.

관련 문제