Facebook
From Mature Crane, 3 Years ago, written in Plain Text.
This paste is a reply to Re: Re: Untitled from Jittery Dormouse - go back
Embed
Viewing differences between Re: Re: Untitled and Re: Re: Re: Untitled
#----------------------------------------------------------------
# Program LAB_4.S lab_5.s - Architektury Komputerów
#----------------------------------------------------------------
#
#  To compile: as compile&link: gcc -no-pie -o lab_4.o lab_4.lab_5 lab_5.s
#  To link:    ld -o lab_4 lab_4.o
#  To run:     ./lab_4
/lab_5
#
#---------------------------------------------------------------- 

#----------------------------------------------------------------


        .equ        write_64,        1
data
        
fmt_1:
        .equ        exit_64,        60
asciz        "Value = %d\n"                # format string
val_1:
        .equ        stdout,                1

#----------------------------------------------------------------

long        6                        # long number
fmt_2:
        .data

vector:                                        
string        "GCD(%d, %d) = %d\n"        vector of items
another format string
var_a:
        .long        10,70,50,90,60,80,40,20,0,30,98,78
count:                                        
3084                        count of items
first number
var_b:
        .quad        ( . - vector ) >> 2
item:        
long        1424                        # second number
fmt_3:
        .string        "Item "
line_no:        
string "%d %d"                        # format string for scanf
fmt_4:
        .string        "   "
itemval:        
string "A=%d, B=%d\n"                # yet another format string
fmt_lf:
        .string        " = "
number:        
string "\n"                        # just "\n"
ok_num:
        .string        "     \n"
FL_text:        
long        0                        # scanf result
argc:
        .string        "\nFrom first to last:\n"
LF_text:        
long        0                        # number of arguments
argc_tmp:
        .string        "\nFrom last to first:\n"
dataend:

long        0                        # number of arguments
argv:
        .equ        item_len, FL_text - item
quad        0                        # address of argv[]
env:
        .equ        FL_len, LF_text - FL_text
quad        0                        # address of env[]
fmt_argc:
        .equ        LF_len, dataend - LF_text

string        "Argc=%d\n"                # format for argc
fmt_argv:
        .string "Argv[%d]=%s\n"                # format for argv
fmt_env:
        .string "Env[%d]=%s\n"                # format for env

#----------------------------------------------------------------

        .text
        .global _start

        .macro disp_str_64 file_id, address, length
        mov $write_64, %rax
        mov \file_id, %rdi
        mov \address, %rsi
        mov \length, %rdx
        syscall
        .endm

        .macro exit_prog_64 exit_code
        mov $exit_64, %rax
        mov \exit_code, %rdi
        syscall
        .endm

main

#----------------------------------------------------------------
        
_start:
        disp_str_64 $stdout, $FL_text, $FL_len        
main:
        push %rbp

        mov %edi, argc
        mov %edi, argc_tmp
        mov %rsi, argv
        mov %rdx, env

        mov val_1, %rsi                
display message

        CALL        disp_vector_FL                        
printf( char *fmt, long num ) - second argument to %rsi;
        mov $fmt_1, %rdi        
display content printf( char *fmt, long num ) - first argument to %rdi;
        xor %rax, %rax                # printf( char *fmt, long num ) - number 
of vector

        disp_str_64 $stdout, $LF_text, $LF_len        
vector registers to %al 
        call printf

again:

        mov $fmt_3, %rdi
        mov $var_a, %rsi
        mov $var_b, %rdx
        mov $0, %al
        call scanf
        mov %eax, ok_num

        mov $fmt_lf, %rdi        
display message

        CALL        disp_vector_LF                        
printf( fmt ) - first argument to %rdi;
        xor %rax, %rax                
display content printf( fmt ) - number of vector

        exit_prog_64 $0                                
vector registers to %al 
        call printf

        cmp $2, ok_num
        jnz no_more_numbers        

        mov var_b, %rdx                
exit program

printf( fmt, num1, num2 ) - third argument to %rdx;
        mov var_a, %rsi                # printf( fmt, num1, num2 ) - second argument to %rsi;
        mov $fmt_4, %rdi        # printf( fmt, num1, num2 ) - first argument to %rdi;
        xor %rax, %rax                # printf( fmt, long num ) - number of vector registers to %al 
        call printf

        mov var_a, %edi                # nwd( long num1, long num2 ) - first argument to %rdi
        mov var_b, %esi                # nwd( long num1, long num2 ) - second argument to %rsi
        call gcd

        mov %rax, %rcx                # printf( fmt, num1, num2, result ) - fourth argument to %rcx
        mov var_b, %rdx                # printf( fmt, num1, num2, result ) - third argument to %rdx
        mov var_a, %rsi                # printf( fmt, num1, num2, result ) - second argument to %rsi
        mov $fmt_2, %rdi        # printf( fmt, num1, num2, result ) - first argument to %rdi
        mov $0, %al                # printf( fmt, num1, num2, result ) - number of vector registers to %al
        call printf

        jmp again


no_more_numbers:

        mov argc, %rsi                # printf( fmt, num ) - second argument to %rsi;
        mov $fmt_argc, %rdi        # printf( fmt, num ) - first argument to %rdi;
        xor %rax, %rax                # printf( fmt, num ) - number of vector registers to %al 
        call printf


        mov argv, %rbp                # %rbp = argv;

next_argv:
        mov (%rbp), %rdx        # printf( fmt, num, str ) - third argument to %rdx;
        mov argc, %esi
        sub argc_tmp, %esi        # printf( fmt, num, str ) - second argument to %rsi;
        mov $fmt_argv, %rdi        # printf( fmt, num, str ) - first argument to %rdi;
        xor %rax, %rax                # printf( fmt, num ) - number of vector registers to %al 
        call printf
        
        add $8, %rbp                # next argv
        decl argc_tmp                # argc_tmp--;
        jnz next_argv                # 


        mov env, %rbp                # %rbp = env;

next_env:
        cmp $0,(%rbp)                # while( env[i] != NULL )
        jz no_more_env
        mov (%rbp), %rdx        # printf( fmt, num, str ) - third argument to %rdx;
        mov argc_tmp, %esi        # printf( fmt, num, str ) - second argument to %rsi;
        mov $fmt_env, %rdi        # printf( fmt, num, str ) - first argument to %rdi;
        xor %rax, %rax                # printf( fmt, num ) - number of vector registers to %al 
        call printf
        
        add $8, %rbp                # next env
        incl argc_tmp                # argc_tmp++;
        jmp next_env

no_more_env:

#        xor %rdi, %rdi                # exit( code ) - first argument to %rdi
#        call exit
 
        pop %rbp

        ret

#----------------------------------------------------------------
#
# gcd - computes greatest common divisor
#        Function:        disp_vector_FL
Arguments:        %rdi - first number
#                        %rsi - second number
#        Parameters:        none
#
Returns:        %rax - gcd value
#----------------------------------------------------------------

        .type disp_vector_FL,@function
disp_vector_FL:
        MOV        count,%rcx                
gcd, @function

gcd:
        cmp %rdi, %rsi                
data count
        XOR        %rsi,%rsi                
(a==b)?
        jz computed                
data index
next_item:
        MOV        vector(,%rsi,4),%ebx        
yes
        jb b_below_a                
get data
        CALL        make_string                # convert to string
        push %rcx
        push %rsi
        disp_str_64 $stdout, $item, $item_len        # display prepared string
        pop %rsi
        pop %rcx
        INC        %rsi                        # next element
        LOOP        next_item                # { rcx--; if( rcx ) 
if(b < a) goto next_item }

        RET                                
b_below_a
        sub %rdi, %rsi                
return to main program
#----------------------------------------------------------------
#
#        Function:        disp_vector_LF
#        Parameters:        none
#
        .type disp_vector_LF,@function
disp_vector_LF:
        MOV        count,%rcx                # data count
        MOV        %rcx,%rsi                # data index
        DEC        %rsi                        # data index--
prev_item:
        MOV        vector(,%rsi,4),%ebx        # get data
        CALL        make_string                # convert to string
        push %rcx
        push %rsi
        disp_str_64 $stdout, $item, $item_len        # display prepared string
        pop %rsi
        pop %rcx
        DEC        %rsi                        # previous element
        LOOP        prev_item                # { rcx--; if( rcx ) goto prev_item }

        RET                                # return to main program
#----------------------------------------------------------------
#
#        Function:        make_string
#        Parameters:        %esi - index of element
#                        %ebx - value of element
#
        .type make_string,@function
make_string:
#        MOVL $0x20202020, number
        MOVW $0x2020, line_no
        MOV        %esi,%eax                # convert index of vector element t
        MOV        $line_no + 2,%rdi
        CALL        num2dec
        MOV        %ebx,%eax                # convert value of vector element to
        MOV        $number + 4,%rdi
        CALL        num2dec

        RET                                # return to disp_vector function
#----------------------------------------------------------------
#
#        Function:        num2dec
#        Parameters:        %eax - value
#                        %rdi - address of last character
#
        .type num2dec,@function
num2dec:
        PUSH        %rbx                # save register on stack
        PUSH        %rdx                # save register on stack
        MOV        $10,%ebx        # divisor in EBX, dividend in EAX
nextdig:                        
        XOR        %edx,%edx        # EDX = 0
        DIV        %ebx                # EDX:EAX div EBX
        ADD        $'0',%dl        # convert remainder (in EDX) to character
        MOV        %dl,(%rdi)        # *(RDI) = character (decimal digit)
        CMP        $0,%eax                # quotient in EAX 
        JZ        empty
        DEC        
else b=b-a
        jmp gcd
b_below_a:
        sub %rsi, 
%rdi                # RDI--
        JMP        nextdig                
empty:                
        POP        %rdx                
a=a-b
        jmp gcd                
computed:
        mov %rdi, %rax                
restore register from stack
        POP        %rbx                # restore register from stack

        RET                        # return to make_string function
#----------------------------------------------------------------
result (a==b)
        ret

Replies to Re: Re: Re: Untitled rss

Title Name Language When
Re: Re: Re: Re: Untitled Crippled Meerkat text 3 Years ago.