比较程序集中的整数值

sad*_*uee 2 assembly integer compare intel cmp

我们的任务是比较整数值并打印出适当的提示以显示哪些值更大.

我在下面的代码分别将'i'和'j'初始化为5和4.目标是比较"变量"而不是直接值本身.所以在这个例子中,我把'i'和'j'放在cmp中,而不是5和4.

global _main
extern _printf, _system 

section .text


_main:
; clear screen
    push clr
    call _system
    add esp, 4

;Test prints out i. Successfully does the job.
    push dword [i]          ; why did it work here and not in *cmp*?
    push prompt2
    call _printf      
    add esp, 8

;compare values and do a conditional jump.
    CMP dword [i], dword [j]            ; compares values stored in i and j. i and j are base 10 nums. This is where the error appears.
    JG igreat                           ; jumps if i is greater than j.
    JL jgreat                           ; jumps if j is greater than i.
    JE eks                              ; jumps if i and j are equal.
    ret                                 ; as a measure, this ends the code.

    igreat:                             ; prints out a prompt if i is greater than j.
    push dword [j]
    push dword [i]
    push ibig
    call _printf
    add esp, 16
    ret

    jgreat:                             ; prints out a prompt if j is greater than i.
    push dword [i]
    push dword [j]
    push jbig
    call _printf
    add esp, 16
    ret

    eks:                                ; prints out a prompt if i is equal to j.
    push dword [i]
    push dword [j]
    push ex
    call _printf
    add esp, 16
    ret



last:                                   ; terminates the code
ret

section .data
clr         db "cls",0              
i           dd 5                        ; i is initialized to 5
j           dd 4                        ; j is initialized to 4
prompt2     db "Value is %d",13,10,0
ibig        db "Test 1. Comparisons: %d is bigger than %d",13,10,0
jbig        db "Test 2. Comparisons: %d is bigger than %d",13,10,0
ex          db "Test 3. Comparisons: %d is bigger than %d",13,10,0
Run Code Online (Sandbox Code Playgroud)

我可以提出两个问题:

  1. CMP dword [i],dword [j]产生错误:操作码和操作数的无效组合; 但我使用前一个调用/代码行上的printf函数成功恢复了值.这是为什么?
  2. 我试图用一个直接的,例如CMP dword [i],9 替换dword [j].它会打印出正确的提示,但会使程序无响应.这是为什么?

请注意,我运行的是Windows 8 Intel 32位,此代码已经在运行在DoSBox中的NASM中进行了"编译",而在CMD中运行了GCC.

我是一个初学者,任何帮助将不胜感激.谢谢!

Sam*_*nen 6

CMP无法比较两个内存位置.它可以将寄存器与寄存器,常量或存储器进行比较,并且可以将存储器位置与常量或寄存器进行比较.这就是您收到错误并且正确的原因.您必须将其中一个的值存储到寄存器中然后进行比较.

该程序"没有响应"的原因是因为你搞砸了ESP.你推动堆栈,调用_printf,然后由于某种原因移动ESP16个字节.RET然后将跳转到堆栈中的第一个值,我确定它不正确.

你应该将存储ESP值转换成EBP在启动和恢复的回报ESP,然后RET.