LAB 05 PART 1

SPO600 Lab5 64-Bit Assembly Language

In this lab I am going to explore the assembler on the following platform

AArch64 part 1


REVIEW THE ASSEMBLY CODE

Modify the AArch64 Loop Example

STEP ONE:  I have to modify a provided code block in the aarch64 system to print loop for 6 times.
RESULT
Here is the Code ==>


.text
.globl _start
min = 0                          /* starting value for the loop index; **note that this is a symbol (constant)**, not a variable */
max = 6                          /* loop exits when the index hits this number (loop condition is i<max) */

_start:
    mov     x19, min

loop:
    /* ... body of the loop ... do something useful here ... */                          //print the String "Loop"
    mov     x0, 1           /* file descriptor: 1 is stdout */
    adr     x1, msg         /* message location (memory address) */
    mov     x2, len         /* message length (bytes) */
    mov     x8, 64          /* write is syscall #64 */
    svc     0               /* invoke syscall */

    add     x19, x19, 1     /* increment the loop counter */
    cmp     x19, max        /* see if we've hit the max */
    b.ne    loop            /* if not, then continue the loop */

    mov     x0, 0           /* set exit status to 0 */
    mov     x8, 93          /* exit is syscall #93 */
    svc     0               /* invoke syscall */

.data
msg:    .ascii "Loop\n"      /* message string */
len = . - msg                /* length of the message */

STEP 2:Modify the code so that it also show the iteration number, i,e, Loop: 1, Loop: 2..etc

RESULT

HERE IS THE CODE==>


.text
.globl _start

min = 0                          /* starting value for the loop index; **note that this is a symbol (constant)**, not a variable */
max = 6                          /* loop exits when the index hits this number (loop condition is i<max) */

_start:
    mov     x19, min     
    adr     x21, num

loop:
    /* ... body of the loop ... do something useful here ... */
    mov     x0, 1           /* file descriptor: 1 is stdout */
    adr     x1, msg         /* message location (memory address) */
    mov     x2, len1        /* message length (bytes) */
    mov     x8, 64          /* write is syscall #64 */
    svc     0               /* invoke syscall */

    /* print the number */         //print the num variable in .data                                                                        
   mov     x0, 1           /* file descriptor: 1 is stdout */
    adr     x1, num         /* message location (memory address) */
    mov     x2, len2        /* message length (bytes) */
    mov     x8, 64          /* write is syscall #64 */
    svc     0               /* invoke syscall */

    add     w19, w19, 1     /* increment the loop counter */

    /* update the num value in .data */     //change the num variable in .data                                                  
    mov     w20, w19
    add     w20, w20, 48    /* convert integer to ASCII */
    strb    w20, [x21]      /* store byte at address pointed by x21 */

    cmp     x19, max        /* see if we've hit the max */
    b.ne    loop            /* if not, then continue the loop */

    mov     x0, 0           /* set exit status to 0 */
    mov     x8, 93          /* exit is syscall #93 */
    svc     0               /* invoke syscall */

.data
msg:    .ascii "Loop: "
len1=   . - msg
num:    .ascii "0 \n"     //variable added to print the iteration number    

len2=   . - num

STEP 3: Extend the code to loop from 00 to 32

RESULT


HERE IS THE CODE==>
.text
.globl _start

min = 0                          /* starting value for the loop index; **note that this is a symbol (constant)**, not a variable */
max = 33                         /* loop exits when the index hits this number (loop condition is i<max) */

_start:
    mov     x19, min      //Initialize the register to store the address 
    adr     x22, num          /* address of the first digit */
    add     x23, x22, 1       /* address of the second digit */
    mov     w21, 48           /* the ten's digit */
    mov     w20, 48           /* the one's digit */

loop:
    /* Print "Loop: " message */
    mov     x0, 1             /* file descriptor: 1 is stdout */
    adr     x1, msg           /* message location (memory address) */
    mov     x2, len1          /* message length (bytes) */
    mov     x8, 64            /* write is syscall #64 */
    svc     0                 /* invoke syscall */

    /* Print the number (num value) */
    mov     x0, 1             /* file descriptor: 1 is stdout */
    adr     x1, num           /* message location (memory address) */
    mov     x2, len2          /* message length (bytes) */
    mov     x8, 64            /* write is syscall #64 */
    svc     0                 /* invoke syscall */

    add     x19, x19, 1       /* increment the loop counter */
    add     w20, w20, 1         //Check if the units digit>10
    cmp     w20, 58           /* if one's digit >= '9' (ASCII 58) */
    b.lt    update

    /* Update the ten's digit when the one's digit reaches '10' */
    add     w21, w21, 1
    strb    w21, [x22]
    mov     w20, 48           /* reset one's digit back to '0' */ 

update:
    /* Update the num value in .data */
    strb    w20, [x23]
    cmp     x19, max          /* see if we've hit the max */
    b.ne    loop              /* if not, continue the loop */

    mov     x0, 0             /* set exit status to 0 */
    mov     x8, 93            /* exit syscall #93 */
    svc     0                 /* invoke syscall */

.data
msg:    .ascii "Loop: "
len1=   . - msg
num:    .ascii "00\n"
len2=   . - num

 STEP 4: Modify the code to make it suppress the leading zero



RESULT

HERE IS THE CODE==>
.text
.globl _start

min = 0                          /* starting value for the loop index; **note that this is a symbol (constant)**, not a variable */
max = 33                         /* loop exits when the index hits this number (loop condition is i<max) */

_start:
    mov     x19, min
    adr     x22, num          /* address of the first digit */
    adr     x23, num          /* address which increments during the loop */
    mov     w21, 48           /* the ten's digit (ASCII '0') */
    mov     w20, 48           /* the one's digit (ASCII '0') */

loop:
    /* Print "Loop: " message */
    mov     x0, 1             /* file descriptor: 1 is stdout */
    adr     x1, msg           /* message location (memory address) */
    mov     x2, len1          /* message length (bytes) */
    mov     x8, 64            /* write is syscall #64 */
    svc     0                 /* invoke syscall */

    /* Print the number (num value) */
    mov     x0, 1             /* file descriptor: 1 is stdout */
    adr     x1, num           /* message location (memory address) */
    mov     x2, len2          /* message length (bytes) */
    mov     x8, 64            /* write is syscall #64 */
    svc     0                 /* invoke syscall */

    add     x19, x19, 1       /* increment the loop counter */
    add     w20, w20, 1       /* increment the one's digit */

    cmp     x19, 10
    b.ne    checkten

    /* The first time reaching 10 */
    add     x23, x22, 1       /* move to the second digit (tens place) */
    mov     w20, 58           /* set one's digit to '0' (ASCII 48) after 10 is reached */
    mov     w21, 48           /* reset tens digit to '0' (ASCII 48) */

checkten:
    cmp     w20, 58
    b.lt    update

    /* Update the tens digit when the one's digit reaches '10' */
    add     w21, w21, 1
    strb    w21, [x22]        /* store the updated tens digit */
    mov     w20, 48           /* reset one's digit back to '0' */

update:
    /* Update the num value in .data (the number string) */
    strb    w20, [x23]

    cmp     x19, max          /* check if we've hit the max */
    b.ne    loop              /* if not, continue the loop */

    /* Exit program */
    mov     x0, 0             /* set exit status to 0 */
    mov     x8, 93            /* exit syscall #93 */
    svc     0                 /* invoke syscall */

.data
msg:    .ascii "Loop: "
len1=   . - msg
num:    .ascii "0 \n"
len2=   . - num

Step 5: Modify the code so that it output in hexadecimal (0-20) instead of decimal (0-32)

RESULT

HERE IS THE CODE==>
.text
.globl _start

min = 0                          /* starting value for the loop index; **note that this is a symbol (constant)**, not a variable */
max = 33                         /* loop exits when the index hits this number (loop condition is i<max) */

_start:
    mov     x19, min
    adr     x22, num          /* address of the first digit */
    adr     x23, num          /* address which increments during the loop */
    mov     w21, 48           /* the ten's digit (ASCII '0') */
    mov     w20, 48           /* the one's digit (ASCII '0') */

loop:
    /* Print "Loop: " message */
    mov     x0, 1             /* file descriptor: 1 is stdout */
    adr     x1, msg           /* message location (memory address) */
    mov     x2, len1          /* message length (bytes) */
    mov     x8, 64            /* write is syscall #64 */
    svc     0                 /* invoke syscall */

    /* Print the number (num value) */
    mov     x0, 1             /* file descriptor: 1 is stdout */
    adr     x1, num           /* message location (memory address) */
    mov     x2, len2          /* message length (bytes) */
    mov     x8, 64            /* write is syscall #64 */
    svc     0                 /* invoke syscall */

    add     x19, x19, 1       /* increment the loop counter */
    add     w20, w20, 1       /* increment the one's digit */

    cmp     w20, 58           /* check if one's digit reaches '10' (ASCII 58) */
    b.ne    chknewdg
    add     w20, w20, 7       /* adjust to start from '0' after 10 (ASCII '48') */

chknewdg:
    cmp     x19, 16           /* check if loop counter reaches 16 */
    b.ne    check16
    /* The first time reaching 16 */
    add     x23, x22, 1       /* move to the second digit (tens place) */
    mov     w20, 71           /* reset one's digit to '0' after reaching 16 (ASCII '48') */
    mov     w21, 48           /* reset tens digit to '0' (ASCII '48') */

check16:
    cmp     w20, 71           /* check if one's digit is '0' after 16 */
    b.lt    update

    /* Update the tens digit when one's digit exceeds 16 */
    add     w21, w21, 1
    strb    w21, [x22]        /* store the updated tens digit */
    mov     w20, 48           /* reset one's digit back to '0' */

update:
    /* Update the num value in .data (the number string) */
    strb    w20, [x23]

    cmp     x19, max          /* check if we've hit the max value */
    b.ne    loop              /* if not, continue the loop */

    /* Exit program */
    mov     x0, 0             /* set exit status to 0 */
    mov     x8, 93            /* exit syscall #93 */
    svc     0                 /* invoke syscall */

.data
msg:    .ascii "Loop: "
len1=   . - msg
num:    .ascii "0 \n"
len2=   . - num


TO BE CONTINUED


Comments

Popular posts from this blog

Project Stage 1: Create a GCC pass

LAB 03

Project Stage 2: Part 2( The End)