assembly MASM打印质数

mu0hgdu0  于 2023-03-02  发布在  其他
关注(0)|答案(1)|浏览(150)

大家好,我的汇编项目遇到了问题。我应该按顺序打印出x个质数。但是我不能使用函数USES。当我试图删除它时,我得到了一个无限循环。有人能帮帮我吗,谢谢

isPrime PROC USES ECX EBX
; Checks whether a number is prime or not. If given number is prime, returns
; boolean value 1. Otherwise, returns 0.
; receives: A number in EAX
; returns: boolean value(0 or 1) in EAX
; preconditions: eax is in [1..200]
; registers changed: eax, ebx, ecx, edx
;-------------------------------------------------------------------------
        mov ecx,eax                         ; copy the number p into ECX
        mov esi, 2                          ; i=2
  startLoop:
        cmp esi,ecx                         
        jge PrimeNum                        ; if i>=p, p is prime and goto PrimeNum
        mov edx,0
        mov eax,ecx
        div esi                             ; calculate p/i. EAX=p/i and EDX=p%i
        cmp edx, 0                          
        je  NotPrime                        ; if remainder = 0, p is not prime
        inc esi                             ; otherwise, continue search
        jmp startLoop
PrimeNum:   
    mov eax, TRUE                           ; if p is prime , return true
    ret
NotPrime:
    mov eax, FALSE                          ; if p is not prime, return true
    ret
isPrime ENDP

当我移除USES部分时

mov ecx,eax                         ; copy the number p into ECX
        mov try2, 2                         ; i=2
  startLoop:
        cmp try2,ecx                            
        jge PrimeNum                        ; if i>=p, p is prime and goto PrimeNum
        mov edx,0
        mov eax,ecx
        div try2                                ; calculate p/i. EAX=p/i and EDX=p%i
        cmp edx, 0                          
        je  NotPrime                        ; if remainder = 0, p is not prime
        inc try2                                ; otherwise, continue search
        jmp startLoop
PrimeNum:   
    mov eax, TRUE                           ; if p is prime , return true
    
    
    ret
NotPrime:
    mov eax, FALSE                          ; if p is not prime, return true
    ret
ia2d9nvy

ia2d9nvy1#

isPrime PROC USES ECX EBX

虽然这段代码声称使用EBX,但实际上使用的是ESI,甚至没有触及EBX。
如果你不想依赖USES,你需要保留你想要保留的寄存器,因为你的代码有多个ret指令,你也需要多个恢复序列:

isPrime PROC
    push ecx         ;
    push edx         ; Preserves ECX EDX ESI
    push esi         ;
    mov  ecx, eax    ; copy the number p into ECX
    mov  esi, 2      ; i=2
  startLoop:
    cmp  esi, ecx                          
    jge  PrimeNum    ; if i>=p, p is prime and goto PrimeNum
    mov  edx, 0
    mov  eax, ecx
    div  esi         ; calculate p/i. EAX=p/i and EDX=p%i
    cmp  edx, 0                          
    je   NotPrime    ; if remainder = 0, p is not prime
    inc  esi         ; otherwise, continue search
    jmp  startLoop
  PrimeNum:   
    mov  eax, TRUE   ; if p is prime , return true
    pop  esi         ;
    pop  edx         ; Restores ESI EDX ECX
    pop  ecx         ;
    ret
  NotPrime:
    mov  eax, FALSE  ; if p is not prime, return true
    pop  esi         ;
    pop  edx         ; Restores ESI EDX ECX
    pop  ecx         ;
    ret
isPrime ENDP

很容易避免这种双ret

isPrime PROC
    push ecx         ;
    push edx         ; Preserves ECX EDX ESI
    push esi         ;
    mov  ecx, eax    ; copy the number p into ECX
    mov  esi, 2      ; i=2
  startLoop:
    mov  eax, TRUE   ; if p is prime , return true
    cmp  esi, ecx                          
    jge  PrimeNum    ; if i>=p, p is prime and goto PrimeNum
    mov  edx, 0
    mov  eax, ecx
    div  esi         ; calculate p/i. EAX=p/i and EDX=p%i
    cmp  edx, 0                          
    je   NotPrime    ; if remainder = 0, p is not prime
    inc  esi         ; otherwise, continue search
    jmp  startLoop
  NotPrime:
    mov  eax, FALSE  ; if p is not prime, return true
  PrimeNum:   
    pop  esi         ;
    pop  edx         ; Restores ESI EDX ECX
    pop  ecx         ;
    ret
isPrime ENDP

这段代码仍然不是检查素性的最佳代码。你可以在下面的答案中找到更多关于快速检查素性的想法

相关问题