; Listing10-2.asm ; ; A program that demonstrates macros ; for the yield, foreach, and endfor ; iterator statements. option casemap:none .nolist include aoalib.inc include aoaProcs.inc use1var = 1 ;Use Ver1 _push and _pop include ctPushPop.inc includelib aoalib.lib .list ; Program title: .const align word ttlStr byte "Listing 10-2", 0 .code ; Macros to implement iterators: yield macro push qword ptr [rbp] call qword ptr [rbp+8] endm iterStk textequ <> foreach macro iterator local failureAdrs _push (iterStk, failureAdrs) lea rax, failureAdrs push rax call iterator push rbp mov rbp, [rsp+16] endm endfor macro local failureAdrs pop rbp ret 8 failureAdrs _pop (iterStk) failureAdrs: endm ; iterator range( start:dword, stop:dword ) parms range, rbp, 24, \ start:dword, \ stop:dword range proc push rbp mov rbp, rsp mov edx, range$start mov r8d, range$stop call print byte "in range, %d to %d", nl, 0 ForEverLbl: mov eax, range$start cmp eax, range$stop jg ForDone yield ; Move on to next iteration of the loop inc range$start jmp ForEverLbl ForDone: pop rbp add rsp, 8 ret range endp ;-------------------------------------------------- ; ; Here is the main assembly language function. public asmMain asmMain proc push rbp mov rbp, rsp sub rsp, 80 mov eax, 10 ; Push stop parameter value. push rax ; Remember, push in reverse order! mov eax, 1 ; Push start parameter value push rax foreach range ;Call the iterator ; Body of the foreach loop: mov edx, eax ;Display i’s value call print byte "%d", nl, 0 endfor leave ret asmMain endp end