Academic Integrity: tutoring, explanations, and feedback — we don’t complete graded work or submit on a student’s behalf.

Visual studio is the compiler. This is a x86 assembly program. In this lab we wi

ID: 3606637 • Letter: V

Question

Visual studio is the compiler. This is a x86 assembly program.

In this lab we will write an assembly program that uses loops with indirect or indexed addressing to permutates (re-arranges) an integer array. The following example shows how an array is re-arranged based on the permutation:

   Position/Index:

Array before permutation:        

                              0          1           2           3          4            5           6          7            8          9  

12

9

54

20

3

38

72

17

91

25

Permutation:

8

3

5

9

2

6

0

4

1

7

Array after permutation:

91

20

38

25

54

72

12

3

9

17

In your program you are allowed to define only two arrays – one for the array and the other for the permutation. Do not copy the array elements to any other array! The runtime screen shot can be as follows (you can use different numbers):

            Welcome! This program permutates an array of any size.

            Please enter the size of the array: 10

Please enter the 10 elements of your array:

12       9        54        20       3       38       72       17       91       25

Please enter the permutation:

8         3         5          9        2        6         0          4             1          7

The array after permutation is:

           91       20      38        25       54      72      12       3         9          17

Hint:

     The following algorithm gives one possible solution to the problem

Enter array size as SIZE;

for i from 0 to (SIZE - 2)

Array[i] <-> Array[Permutation[i]];

for j from (i+1) from (SIZE – 1)

            if (i == permutation[j])

                        permutation[i] <-> permutation[j];

                        break;

   Position/Index:

Explanation / Answer

.LC0:

.string " Welcome! This program permutates an array of any size."

.LC1:

.string " Please enter the size of the array: "

.LC2:

.string "Please enter the {0} elements of your array:"

.LC3:

.string "Please enter the permutation:"

.LC4:

.string "The array after permutation is:"

.LC5:

.string " "

main:

push rbp

mov rbp, rsp

push r15

push r14

push r13

push r12

push rbx

sub rsp, 104

mov rax, rsp

mov rbx, rax

mov esi, OFFSET FLAT:.LC0

mov edi, OFFSET FLAT:std::cout

call std::basic_ostream<char, std::char_traits<char> >& std::operator<< <std::char_traits<char> >(std::basic_ostream<char, std::char_traits<char> >&, char const*)

mov esi, OFFSET FLAT:std::basic_ostream<char, std::char_traits<char> >& std::endl<char, std::char_traits<char> >(std::basic_ostream<char, std::char_traits<char> >&)

mov rdi, rax

call std::basic_ostream<char, std::char_traits<char> >::operator<<(std::basic_ostream<char, std::char_traits<char> >& (*)(std::basic_ostream<char, std::char_traits<char> >&))

mov esi, OFFSET FLAT:.LC1

mov edi, OFFSET FLAT:std::cout

call std::basic_ostream<char, std::char_traits<char> >& std::operator<< <std::char_traits<char> >(std::basic_ostream<char, std::char_traits<char> >&, char const*)

mov esi, OFFSET FLAT:std::basic_ostream<char, std::char_traits<char> >& std::endl<char, std::char_traits<char> >(std::basic_ostream<char, std::char_traits<char> >&)

mov rdi, rax

call std::basic_ostream<char, std::char_traits<char> >::operator<<(std::basic_ostream<char, std::char_traits<char> >& (*)(std::basic_ostream<char, std::char_traits<char> >&))

lea rax, [rbp-100]

mov rsi, rax

mov edi, OFFSET FLAT:std::cin

call std::basic_istream<char, std::char_traits<char> >::operator>>(int&)

mov eax, DWORD PTR [rbp-100]

cdqe

sub rax, 1

mov QWORD PTR [rbp-64], rax

mov rdx, rax

add rdx, 1

mov QWORD PTR [rbp-128], rdx

mov QWORD PTR [rbp-120], 0

mov rdx, rax

add rdx, 1

mov QWORD PTR [rbp-144], rdx

mov QWORD PTR [rbp-136], 0

add rax, 1

sal rax, 2

lea rdx, [rax+3]

mov eax, 16

sub rax, 1

add rax, rdx

mov ecx, 16

mov edx, 0

div rcx

imul rax, rax, 16

sub rsp, rax

mov rax, rsp

add rax, 3

shr rax, 2

sal rax, 2

mov QWORD PTR [rbp-72], rax

mov esi, OFFSET FLAT:.LC2

mov edi, OFFSET FLAT:std::cout

call std::basic_ostream<char, std::char_traits<char> >& std::operator<< <std::char_traits<char> >(std::basic_ostream<char, std::char_traits<char> >&, char const*)

mov esi, OFFSET FLAT:std::basic_ostream<char, std::char_traits<char> >& std::endl<char, std::char_traits<char> >(std::basic_ostream<char, std::char_traits<char> >&)

mov rdi, rax

call std::basic_ostream<char, std::char_traits<char> >::operator<<(std::basic_ostream<char, std::char_traits<char> >& (*)(std::basic_ostream<char, std::char_traits<char> >&))

mov DWORD PTR [rbp-56], 0

.L3:

mov eax, DWORD PTR [rbp-100]

cmp DWORD PTR [rbp-56], eax

jge .L2

mov eax, DWORD PTR [rbp-56]

cdqe

lea rdx, [0+rax*4]

mov rax, QWORD PTR [rbp-72]

add rax, rdx

mov rsi, rax

mov edi, OFFSET FLAT:std::cin

call std::basic_istream<char, std::char_traits<char> >::operator>>(int&)

add DWORD PTR [rbp-56], 1

jmp .L3

.L2:

mov esi, OFFSET FLAT:.LC3

mov edi, OFFSET FLAT:std::cout

call std::basic_ostream<char, std::char_traits<char> >& std::operator<< <std::char_traits<char> >(std::basic_ostream<char, std::char_traits<char> >&, char const*)

mov esi, OFFSET FLAT:std::basic_ostream<char, std::char_traits<char> >& std::endl<char, std::char_traits<char> >(std::basic_ostream<char, std::char_traits<char> >&)

mov rdi, rax

call std::basic_ostream<char, std::char_traits<char> >::operator<<(std::basic_ostream<char, std::char_traits<char> >& (*)(std::basic_ostream<char, std::char_traits<char> >&))

mov eax, DWORD PTR [rbp-100]

cdqe

sub rax, 1

mov QWORD PTR [rbp-80], rax

mov rdx, rax

add rdx, 1

mov r14, rdx

mov r15d, 0

mov rdx, rax

add rdx, 1

mov r12, rdx

mov r13d, 0

add rax, 1

sal rax, 2

lea rdx, [rax+3]

mov eax, 16

sub rax, 1

add rax, rdx

mov ecx, 16

mov edx, 0

div rcx

imul rax, rax, 16

sub rsp, rax

mov rax, rsp

add rax, 3

shr rax, 2

sal rax, 2

mov QWORD PTR [rbp-88], rax

mov DWORD PTR [rbp-56], 0

.L5:

mov eax, DWORD PTR [rbp-100]

cmp DWORD PTR [rbp-56], eax

jge .L4

mov eax, DWORD PTR [rbp-56]

cdqe

lea rdx, [0+rax*4]

mov rax, QWORD PTR [rbp-88]

add rax, rdx

mov rsi, rax

mov edi, OFFSET FLAT:std::cin

call std::basic_istream<char, std::char_traits<char> >::operator>>(int&)

add DWORD PTR [rbp-56], 1

jmp .L5

.L4:

mov DWORD PTR [rbp-56], 0

.L10:

mov eax, DWORD PTR [rbp-100]

sub eax, 2

cmp DWORD PTR [rbp-56], eax

jg .L6

mov rax, QWORD PTR [rbp-72]

mov edx, DWORD PTR [rbp-56]

movsx rdx, edx

mov eax, DWORD PTR [rax+rdx*4]

mov DWORD PTR [rbp-92], eax

mov rax, QWORD PTR [rbp-88]

mov edx, DWORD PTR [rbp-56]

movsx rdx, edx

mov edx, DWORD PTR [rax+rdx*4]

mov rax, QWORD PTR [rbp-72]

movsx rdx, edx

mov ecx, DWORD PTR [rax+rdx*4]

mov rax, QWORD PTR [rbp-72]

mov edx, DWORD PTR [rbp-56]

movsx rdx, edx

mov DWORD PTR [rax+rdx*4], ecx

mov rax, QWORD PTR [rbp-88]

mov edx, DWORD PTR [rbp-56]

movsx rdx, edx

mov edx, DWORD PTR [rax+rdx*4]

mov rax, QWORD PTR [rbp-72]

movsx rdx, edx

mov ecx, DWORD PTR [rbp-92]

mov DWORD PTR [rax+rdx*4], ecx

mov eax, DWORD PTR [rbp-56]

add eax, 1

mov DWORD PTR [rbp-52], eax

.L9:

mov eax, DWORD PTR [rbp-100]

sub eax, 1

cmp DWORD PTR [rbp-52], eax

jg .L7

mov rax, QWORD PTR [rbp-88]

mov edx, DWORD PTR [rbp-52]

movsx rdx, edx

mov eax, DWORD PTR [rax+rdx*4]

cmp DWORD PTR [rbp-56], eax

jne .L8

mov rax, QWORD PTR [rbp-88]

mov edx, DWORD PTR [rbp-56]

movsx rdx, edx

mov eax, DWORD PTR [rax+rdx*4]

mov DWORD PTR [rbp-96], eax

mov rax, QWORD PTR [rbp-88]

mov edx, DWORD PTR [rbp-52]

movsx rdx, edx

mov ecx, DWORD PTR [rax+rdx*4]

mov rax, QWORD PTR [rbp-88]

mov edx, DWORD PTR [rbp-56]

movsx rdx, edx

mov DWORD PTR [rax+rdx*4], ecx

mov rax, QWORD PTR [rbp-88]

mov edx, DWORD PTR [rbp-52]

movsx rdx, edx

mov ecx, DWORD PTR [rbp-96]

mov DWORD PTR [rax+rdx*4], ecx

jmp .L7

.L8:

add DWORD PTR [rbp-52], 1

jmp .L9

.L7:

add DWORD PTR [rbp-56], 1

jmp .L10

.L6:

mov esi, OFFSET FLAT:.LC4

mov edi, OFFSET FLAT:std::cout

call std::basic_ostream<char, std::char_traits<char> >& std::operator<< <std::char_traits<char> >(std::basic_ostream<char, std::char_traits<char> >&, char const*)

mov esi, OFFSET FLAT:std::basic_ostream<char, std::char_traits<char> >& std::endl<char, std::char_traits<char> >(std::basic_ostream<char, std::char_traits<char> >&)

mov rdi, rax

call std::basic_ostream<char, std::char_traits<char> >::operator<<(std::basic_ostream<char, std::char_traits<char> >& (*)(std::basic_ostream<char, std::char_traits<char> >&))

mov DWORD PTR [rbp-56], 0

.L12:

mov eax, DWORD PTR [rbp-100]

cmp DWORD PTR [rbp-56], eax

jge .L11

mov esi, OFFSET FLAT:.LC5

mov edi, OFFSET FLAT:std::cout

call std::basic_ostream<char, std::char_traits<char> >& std::operator<< <std::char_traits<char> >(std::basic_ostream<char, std::char_traits<char> >&, char const*)

mov rcx, rax

mov rax, QWORD PTR [rbp-72]

mov edx, DWORD PTR [rbp-56]

movsx rdx, edx

mov eax, DWORD PTR [rax+rdx*4]

mov esi, eax

mov rdi, rcx

call std::basic_ostream<char, std::char_traits<char> >::operator<<(int)

add DWORD PTR [rbp-56], 1

jmp .L12

.L11:

mov eax, 0

mov rsp, rbx

lea rsp, [rbp-40]

pop rbx

pop r12

pop r13

pop r14

pop r15

pop rbp

ret

__static_initialization_and_destruction_0(int, int):

push rbp

mov rbp, rsp

sub rsp, 16

mov DWORD PTR [rbp-4], edi

mov DWORD PTR [rbp-8], esi

cmp DWORD PTR [rbp-4], 1

jne .L16

cmp DWORD PTR [rbp-8], 65535

jne .L16

mov edi, OFFSET FLAT:std::__ioinit

call std::ios_base::Init::Init()

mov edx, OFFSET FLAT:__dso_handle

mov esi, OFFSET FLAT:std::__ioinit

mov edi, OFFSET FLAT:std::ios_base::Init::~Init()

call __cxa_atexit

.L16:

nop

leave

ret

_GLOBAL__sub_I_main:

push rbp

mov rbp, rsp

mov esi, 65535

mov edi, 1

call __static_initialization_and_destruction_0(int, int)

pop rbp

ret