; Guide to Assembly Language
     ; Section 8.7 Complete Program
     ; Copyright 2019, James T. Streib
     .listall
     .686
     .model flat,c
     .stack 100h
scanf     PROTO arg2:Ptr Byte, inputlist:VARARG
printf    PROTO arg1:Ptr Byte, printlist:VARARG    
     .data
msg1fmt   byte 0Ah,"%s",0
msg2fmt   byte "%s",0
msg3fmt   byte 0Ah,"%s",0Ah,0Ah,0
msg4fmt   byte "   %d",0Ah,0
msg5fmt   byte 0Ah,0
in1fmt    byte "%d",0
msg1      byte "Enter the number of integers to be input: ",0
msg2      byte "Enter an integer: ",0
msg3      byte "Sorted",0
n         sdword ?
arry      sdword 20 dup(?)
temp      sdword ?
     .code
main      proc
     INVOKE printf,ADDR msg1fmt,ADDR msg1
     INVOKE scanf,ADDR in1fmt,ADDR n
     INVOKE printf,ADDR msg5fmt
     .if n>0              ; if n <= 0, don't continue
     mov ecx,n            ; load ecx with n
     mov edi,offset arry+0 ; load address of arry into edi
     .repeat
     push ecx             ; save ecx
     INVOKE printf,ADDR msg2fmt,ADDR msg2
     INVOKE scanf,ADDR in1fmt,ADDR [edi]
     add edi,4            ; incrment edi by 4      
     pop ecx              ; restore ecx
     .untilcxz
     .if n>1              ; check >1 elements in array
     mov ecx,n            ; load ecx with n               
     dec ecx              ; loop n-1 times   
     mov esi,offset arry+0 ; load esi with address of arry
     .repeat
     push ecx             ; save ecx
     push esi             ; save address, esi now smallest
     mov edi,esi          ; load address of esi in edi
     add edi,4            ; move edi to the next element
     .repeat
     mov eax,[esi]        ; move smallest to eax to compare
     .if [edi]<eax        ; compare smallest to next
     mov esi,edi          ; save the new smallest in esi
     .endif
     add edi,4            ; move to next element to compare
     .untilcxz
     mov edi,esi          ; edi points to smallest element
     pop esi              ; esi points to the start element
     mov eax,[esi]        ; move start element to temp
     xchg eax,[edi]       ; exchange start and smallest
     mov [esi],eax        ; move smallest back to start
     add esi,4            ; move start index to next
     pop ecx              ; restore ecx to be decremented
     .untilcxz
     .endif
     INVOKE printf, ADDR msg3fmt, ADDR msg3
     mov ecx, n            ; load ecx with n
     mov esi,offset arry+0 ; load esi with address of arry
     .repeat
     push ecx             ; save ecx
     mov eax,[esi]        ; load eax with element from arry
     mov temp,eax         ; store eax in temp for output
     INVOKE printf, ADDR msg4fmt, temp
     add esi,4            ; increment esi to next element
     pop ecx              ; restore ecx
     .untilcxz
     INVOKE printf, ADDR msg5fmt
     .endif
     ret
main      endp
     end