Difference between revisions of "Code Generation/Example 4"

From Wiki**3

< Code Generation
(Postfix Code)
Line 39: Line 39:
 
LT
 
LT
 
JZ whileend
 
JZ whileend
 +
 +
; start while body
 +
LOCV -4    ; second printf arg: read ix
  
 
; put string literal in read-only memory
 
; put string literal in read-only memory
Line 45: Line 48:
 
LABEL strlit
 
LABEL strlit
 
STR "%d\n"
 
STR "%d\n"
 +
; now get the address of the string literal (strlit)
 +
TEXT
 +
ADDR strlit ; first printf arg: string literal address
  
TEXT
+
; args are in the stack: call the function
; start while body
 
LOCV -4    ; second printf arg: read ix
 
ADDR strlit ; first printf arg: string lit address
 
 
CALL printf
 
CALL printf
  

Revision as of 11:25, 11 May 2015

The Original Code

Consider the following C function:

<c> extern int printf(const char *format, ...); int printlist(int lo, int hi) {

 int ix = lo;
 while (ix < hi) {
   printf("%d\n", ix);
   ix++;
 }
 return ix;

} </c>

Postfix Code

The Postfix code for the above function is as follows:

<asm> EXTRN printf

TEXT ALIGN GLOBL printlist, FUNC LABEL printlist

ENTER 4  ; ix@-4 lo@+8 hi@+12

int ix = lo is NOT an assignment

LOCV +8 ; read lo LOCA -4 ; write to ix

ALIGN LABEL whiletest LOCV -4  ; read ix LOCV +12 ; read hi LT JZ whileend

start while body

LOCV -4  ; second printf arg: read ix

put string literal in read-only memory

RODATA ALIGN LABEL strlit STR "%d\n"

now get the address of the string literal (strlit)

TEXT ADDR strlit ; first printf arg: string literal address

args are in the stack
call the function

CALL printf

clean args

TRASH 8

get printf return value

PUSH

get rid of return value (printf used as instruction)

TRASH 4

increment ix

LOCV -4 ; read ix DUP INT 1 ADD LOCA -4 ; ix = ix + 1

end while body
restart while cycle

JMP whiletest

this is the while exit point

ALIGN LABEL whileend

prepare return value

LOCV -4 ; read ix

put it in the accumulator (register) to conform with Cdecl

POP

release stack frame

LEAVE

return control to caller

RET

</asm>

Compiling and Running

To compile the Postfix code directly, pf2asm can be used:

  • pf2asm while.pf
  • yasm -felf while.asm