2011-10-23 109 views
1

感謝大家的幫助我做出了一些非常好的改變,但現在它給了我一個+4198498而不是5的答案,我知道第一組值是錯誤的。我推錯了什麼或沒有正確彈出一個reg?我通過使用ret 8清理堆棧,應該爲下一次調用清理堆棧是正確的?GCD遞歸彙編語言X86 MASM

這是我到目前爲止有:

TITLE MASM GCD      (GCD.asm) 


; Description:GCD recursive 
; 
; Revision date: 

INCLUDE Irvine32.inc 
.data 
myMessage BYTE "Assignment 7 GCD Recursive style",0dh,0ah,0 
myMess2 BYTE "GCD = " ,0dh,0ah,0 


;first set of nums 
val1 DWORD 5 
val2 DWORD 20 

;second set of nums 
val3 DWORD 24 
val4 DWORD 18 

;3rd set 
val5 DWORD 11 
val6 DWORD 7 

;4th set 
val7 DWORD 432 
val8 DWORD 226 

;5th set 
val9 DWORD 26 
val10 DWORD 13 

.code 
main PROC 
    call Clrscr 

    mov edx,offset myMessage 
    call WriteString  ;write message 
    call Crlf    ;new line 
    push val1 
    push val2 
    call GCD 

    exit 
main ENDP 

;------------------------------------------------ 
GCD PROC, 
; This finds GCD 
; Gets values from stored values 
;returns NA 

;------------------------------------------------ 

     xor edx,edx 
     mov eax,dword ptr[esp+8] ;dividend 
     mov ebx,dword ptr[esp+4] ;divisor 
     div ebx    ;eax/ebx 
     cmp edx,0   ;remainder in edx 
     je L1    ;yes: quit 
     call GCD    ;no: call GCD agian 
    L1: 
     mov eax,ebx   ;move the divisor into eax for printing i.e GCD  
     mov edx,offset myMess2 
     call WriteString 
     call WriteInt  ;Display GCD WriteInt uses EAX = qutent 
     call crlf 
     ret 8    ;clean up the stack 
GCD ENDP 

END main 

回答

0

首先,我看到了一些錯誤和不良的生活習慣:

GCD PROC, 
    dividend:DWORD, 
    divisor:DWORD 

聲明局部變量爲你的程序在我看來一個壞習慣。 (來自高級語言的結果)

您需要將其放入數據段。另外有一個語法錯誤,雙字因而未初始化應聲明它們是這樣的:

.DATA ? 
dividend dword ? 
divisor dword ? 

您也可以與寄存器DIV指令的一個問題:

xor edx,edx 
mov eax,xxx ;dividend 
mov ebx,yyy ;divisor 
div ebx  ;eax/ebx 
cmp edx,0 ;remainder in edx 

現在用你的套值的和除以他們你AVE不同的選擇:

手動1在寄存器1-移動他們1

mov eax,dword ptr[val01] ;dividend 
mov ebx,dword ptr[val02] ;divisor 

2-直接按下他們堆棧(類似功能參數)

push val01 
push val02 
call GDC 

;in GDC proc 
mov eax,dword ptr[esp+8] 
mov ebx,dword ptr[esp+4] 

3-把它們放在一個「陣列」和環上通過他們

exercise for you 
0

有幾件事情我看到(忽略的計算是否正確):

mov edx,dividend   ;this is value 1  
    mov ebx,divisor   ;this is the divider make sure its smaller number!  
    div ebx     ;divide int1 by int2 

DIV ebxEDX:EAX通過EBX,所以你應該將派息至EAX並清除EDX

cmp edx,0    ;does remainder = 0 ? 
    je L1     ;yes: quit 

    call GCD    ;no: call GCD agian 

你在哪裏設置這個調用的參數?

L1: 
    mov eax,ebx   ;EAX = GCD 

在這裏你用除數覆蓋商是故意的嗎?

pop edx 
    pop ebx 

我沒有看到你推送這些寄存器的位置。這是由MASM自動完成的嗎?如果沒有,你需要推他們。