Hello,
This is my first post. I try to write program using Euclidean algorithm. I made the fallowing C prototype main.c (I am aware not to use goto, but it's only prototype for assembly jumps):
#include<stdio.h>
#include<stdlib.h>
int main()
{
int a = 18;
int b = 81;
int c;
beginwhile:
if(b == 0)
goto endwhile;
c = a % b;
a = b;
b = c;
if(b != 0)
goto beginwhile;
endwhile:
printf("\n%d\n", a);
return 0;
}
It works. This is my asembler program main.asm:
section .text ; begin of the code section
global main ; gcc needs that label
; load library
%include "library.asm"
main:
; printf("read a: ")
mov eax, read_a
call print_c_str
; scanf("%d", &a)
call read_c_int ; scanf("%d", EAX)
mov [a], eax
; printf("You typed: %d\n", a)
mov eax, test_str
call print_c_str
mov eax, [a]
call print_c_int
call print_c_nl
; printf("read b: ")
mov eax, read_b
call print_c_str
call read_c_int ; scanf("%d", EAX)
mov [b], eax
; printf("You typed: %d\n", b)
mov eax, test_str
call print_c_str
mov eax, [b]
call print_c_int
call print_c_nl
; Search the greatest common divisor of a and b.
mov eax, [a] ; EAX = a
mov ebx, [b] ; EBX = b
; EDX = c
; while (b != 0) {
; c = a % b;
; a = b;
; b = c;
; }
; GCD: a
while:
cmp ebx, 0
je endwhile
push eax
idiv ebx ; EDX = EAX % EBX
; EAX = EAX div EBX
pop eax
mov eax, ebx ; a = b
mov ebx, edx ; b = c
cmp ebx, 0 ; if(b == 0)
jne while ; jump not equal
endwhile:
; print GCD
push eax
mov eax, print_gcd
call print_c_str
pop eax
call print_c_int ; EAX
call print_c_nl
; exit to C
mov eax, 0
ret
section .bss ; uninitialized data section
a resw 2 ; long a - reserve 2 words (4 bytes)
b resw 2 ; long b
section .data ; initialized data section
read_a db "Read a: ", 0
read_b db "Read b: ", 0
print_gcd db "GCD is: ", 0
test_str db "You typed: ", 0
To compile program it is necessary to use library.asm:
; external libc functions
extern printf
extern puts
extern scanf
; ************************ ;
; * library C procedures * ;
; ************************ ;
print_c_nl: ; puts("");
pusha
push 0
push dword str_empty
call puts ; call C
pop ecx ; pop stack 1 times 4 bytes
pop eax
popa
retn ; return to previous block
; print_string: prints string which pointer is stored in EAX
print_c_str: ; printf("%s", EAX)
pusha
; do: printf("%s", EAX)
push eax ; address of string to printf
push dword str_string ; address of: "%s", 0
call printf ; call C function
pop ecx
pop ecx ; pop stack 2 times 4 bytes
popa
ret ; return to previous block
; print_char: prints char stored in EAX
print_c_char: ; printf("%c", EAX)
pusha
; do: printf("%c", EAX)
push eax ; value of char to print
push dword str_char ; address of: "%c", 0
call printf ; call C function
pop ecx
pop ecx ; pop stack 2 times 4 bytes
popa
ret ; return to previous block
; read_int: scanf("%d", EAX)
read_c_int:
push 0 ; push local integer
push esp
push dword str_int
call scanf ; call C
pop ecx
pop ecx ; pop 8 bytes
pop eax
ret ; return to previous block
; print_c_int: printf("%d", EAX)
print_c_int:
pusha
; do: printf("%d", EAX)
push eax ; value of int to printf
push dword str_int ; address of: "%d", 0
call printf ; call C function
pop ecx
pop ecx ; pop 2 times 4 bytes
popa
ret ; return to previous block
section .data ; initialized data section
str_int db "%d", 0
str_char db "%c", 0
str_string db "%s", 0
str_empty db 0
nl db 0ah
It seems to me that loops are analogous. I get floting point error. Thanks for any help.