1. Consider the following arrays with the contents given (you have to declare them in your program).
Array1:
3 8 13 12 20 25 19 17 30 13
Array2:
10 blocks of no numbers
Array3:
Block 1: E0A1+E9A2 Block 2:E1A1+E8A2 Block 3: E2A1+E7A2
Blocks 4 to 9 have nothing stored
Block 10 has E9A1+E0A2
Write an assembly program to do the followings:
a. Convert each of the even number in Array1 to its immediate next higher odd number and each of the odd number in the array to its immediate lower even number. This conversion will be done in a subroutine named Modifier. The modification will be done using logic so that the modifier works for any data in the given array. Before modifications, all the data in the array needs to be saved in the stack so that in future we can use the original data again.
b. Now, populate Array 2 with the saved data in the stack. Multiply each of the data (only the even numbers) by 4. This modification will be done by another subroutine named Incrementor.
c. Now populate Array3 such that element 0 of Array3 is the summation of element 0 0f Array1 and element 9 of Array2. Element 1 0f Array3 is the sum of element 1 of aArray1 and element 8 0f Array2 and so on.
d. Finally, send the content of element 0 of Array3 to PORT 0 of the trainer kit.
1 answer
```assembly
.include "m32def.inc" ; Include the microcontroller specific definitions
.def temp = r17 ; Temporary register for calculations
.def index = r18 ; Index register for looping
.def result = r19 ; Result register for holding intermediate results
.def counter = r20 ; Counter for loop iterations
.cseg ; Program code starts here
; Subroutine to convert even numbers to next higher odd number and odd numbers to next lower even number
Modifier:
push r16 ; Push registers to stack
push r17
push r18
push r19
push r20
; Save original data from Array1 to stack
ldi index, 0 ; Initialize index to 0
ldi counter, 10 ; Loop for 10 iterations (length of Array1)
Modifier_Loop:
mov temp, Array1(index) ; Load element from Array1
cpse temp, 0 ; Check if element is even (temp == 0)
breq Modifier_Odd ; If even, jump to Modifier_Odd
; If odd, decrement to next lower even number
subi temp, 1 ; Decrement value by 1
andi temp, 0xFE ; Clear LSB to make it even
jmp Modifier_Continue
Modifier_Odd:
; If even, increment to next higher odd number
addi temp, 1 ; Increment value by 1
sbrc temp, 0 ; Check if LSB is 1
ori temp, 0x01 ; Set LSB to make it odd
Modifier_Continue:
st -Z, temp ; Store modified value to stack
inc index ; Increment index
dec counter ; Decrement counter
brne Modifier_Loop ; Loop until counter != 0
pop r20 ; Pop registers from stack
pop r19
pop r18
pop r17
pop r16
ret ; Return from subroutine
; Subroutine to multiply even numbers in Array2 by 4
Incrementor:
push r16 ; Push registers to stack
push r17
push r18
push r19
push r20
; Multiply each even number by 4
ldi index, 0 ; Initialize index to 0
ldi counter, 10 ; Loop for 10 iterations (length of Array2)
Incrementor_Loop:
mov temp, Array2(index) ; Load element from Array2
cpse temp, 0 ; Check if element is even (temp == 0)
breq Incrementor_Next ; If odd, skip multiplication
mov result, temp ; Multiply by 4
lsl result
st -Z, result ; Store modified value to Array2
Incrementor_Next:
inc index ; Increment index
dec counter ; Decrement counter
brne Incrementor_Loop ; Loop until counter != 0
pop r20 ; Pop registers from stack
pop r19
pop r18
pop r17
pop r16
ret ; Return from subroutine
.org 0x0000 ; Reset vector, program starts here
rjmp Main ; Jump to main program
; Constants
.equ PORT0 = 0x00 ; Define PORT 0 address
; Arrays
.def Array1 = r21 ; Declare Array1 starting address
.def Array2 = r31 ; Declare Array2 starting address
.def Array3 = r41 ; Declare Array3 starting address
Main:
ldi r16, low(RAMEND) ; Initialize stack pointer
out SPL, r16 ; Set stack pointer to RAMEND
; Initialize Array1
ldi index, 0
ldi counter, 10
Array1_Init:
mov temp, index
add temp, temp ; Multiply index by 2 (each element is 2 bytes)
sts Array1 + temp, counter ; Store counter value to Array1
inc index ; Increment index
inc counter ; Increment counter
brne Array1_Init ; Loop until counter != 0
; Save original data of Array1 to stack
push r16 ; Push registers to stack
push r17
push r18
push r19
push r20
ldi index, 0 ; Initialize index to 0
ldi counter, 10 ; Loop for 10 iterations (length of Array1)
SaveOriginalData_Loop:
mov temp, Array1(index) ; Load element from Array1
st -Z, temp ; Store value to stack
inc index ; Increment index
dec counter ; Decrement counter
brne SaveOriginalData_Loop ; Loop until counter != 0
pop r20 ; Pop registers from stack
pop r19
pop r18
pop r17
pop r16
; Call Modifier subroutine to modify Array1
call Modifier
; Save modified data of Array1 to stack
push r16 ; Push registers to stack
push r17
push r18
push r19
push r20
ldi index, 0 ; Initialize index to 0
ldi counter, 10 ; Loop for 10 iterations (length of Array1)
SaveModifiedData_Loop:
ld temp, -Z ; Load value from stack
sts Array1 + index, temp ; Store modified value to Array1
inc index ; Increment index
dec counter ; Decrement counter
brne SaveModifiedData_Loop ; Loop until counter != 0
pop r20 ; Pop registers from stack
pop r19
pop r18
pop r17
pop r16
; Call Incrementor subroutine to modify Array2
call Incrementor
; Calculate Array3 using Array1 and Array2
ldi counter, 10 ; Loop for 10 iterations (length of Array1 and Array2)
ldi index, 0 ; Initialize index to 0
CalculateArray3_Loop:
ld temp, Array1(index) ; Load element from Array1
add temp, Array2(index) ; Add element from Array2
sts Array3 + index, temp ; Store result to Array3
inc index ; Increment index
dec counter ; Decrement counter
brne CalculateArray3_Loop ; Loop until counter != 0
; Send content of element 0 of Array3 to PORT0
ld temp, Array3 ; Load content of element 0 (starting address of Array3)
out PORT0, temp ; Send data to PORT0
End:
rjmp End ; Infinite loop to prevent program from ending
.end ; End of program
```
Note: This program is written in Atmel AVR Assembly syntax and is specific to a particular microcontroller. You may need to modify it based on your target platform and its specific instruction set.