我在汇编语言程序中遇到问题

时间:2012-09-26 19:32:36

标签: assembly x86

这是装配程序。

“输入3名员工的姓名和工资,然后加上工资并显示总工资,然后显示平均工资”

这是代码

Msg_display Macro str
    mov ah,09h
    mov dx,offset str
    int 21h
EndM Msg_display

.model small
.stack 100h
.data
        e1 db "Enter Name And Salary of 1st Employee","$"
        e2 db "Enter Name And Salary of 2nd Employee","$"
        e3 db "Enter Name And Salary of 3rd Employee","$"
    N1 db 20 dup(?)
    N2 db 20 dup(?)
    N3 db 20 dup(?)
    s1 db 0
    s2 db 0
    s3 db 0
        num db 0
        msg1 db "After Adding their Salaries, Result is....","$"
        msg2 db "Average Salary Is....","$"
        Ent db 0ah,0dh,"$"

.code
    mov ax,@data
    mov ds,ax

        Msg_display e1
    mov si,offset N1
    call input_str
    call No_input
    mov s1,ax

        Msg_display e2
    mov si,offset N2
    call input_str
    call No_input
    mov s2,ax

        Msg_display e3
    mov si,offset N3
    call input_str
    call No_input
    mov s3,ax

Input_str Proc
    mov ah,01h
    int 21h
    mov [si],al
    inc si
        cmp al,0dh
    JE end_input
    Jmp Input_str
End_input:
    mov [si],"$"
Input_str EndP

No_input Proc
    mov ah,01h
    int 21h
    cmp al,0dh
    JE skip

    sub al,48
    xor ah,ah
    mov num ,ax
    pop ax
    mul bx
    add ax,num
    push ax

skip:
    pop ax
    ret
No_Input endp

mov ax,s1
add s2,ax
add s2,s3

mov ah,09h
mov dx, offset msg1
int 21h

mov ah, 02h
mov al, s2
int 21h

mov ax,s2
mov bx,3

div bx
mov ah,09h
mov dx, offset msg2
int 21h

mov ah, 02h
mov dl,al
int 21h

mov ah,04ch
int 21h


End

我一直收到这个错误“第32,38,44,66,69,77,78,79,86行的无效指令操作符”

1 个答案:

答案 0 :(得分:1)

cmp [si],[di]

是无效指令。由于以下几个原因,它无效:

  1. cmp不占用2个内存操作数,只执行很少的指令,当它们执行时,最多只有一个内存操作数被明确指定,另一个应该以预定义的方式隐式地处理,而不会告诉你它是汇编程序。
  2. 内存操作数的大小不明确,汇编程序无法确定它应该是byteword还是dword(双字)。< / LI>

    您应该将一个内存操作数加载到一个寄存器中,然后使用该寄存器和另一个内存操作数执行cmp

    顺便说一下,像mov [si],"$"这样的行也可能有上面描述的问题2,因为一个数字(“$”解析成,“$”的ASCII代码)没有与之相关的大小,内存操作数是裸的,缺少大小规格。正确/明确的方法是拼出内存操作数大小,如下所示:

    mov byte ptr [si],"$"
    

    宏不是子程序,你不称它们为:

    call Msg_display e1
    

    这是宏的无效使用。它应该类似于Msg_display e1Msg_display(e1)Msg_display<e>

    这里没有div指令的这种形式:

    div ax,3
    

    div接受一个显式操作数(除数),它不是立即数(3)。它可以是寄存器或内存操作数。另一个操作数(被除数)要么在ax(当做16/8 = 8,8除法时)要么在dx:ax中(当做32/16 = 16,16除法时)。另外,如果您的股息是16位,请记得将dx归零。