Consider the following C function:
int *traverse(int vec[], int lim) {
int *ptr = vec + lim - 1, ix = lim - 2;
while (ix >= 0) {
ptr = (vec[ix] > *ptr) ? vec + ix : ptr;
ix--;
}
return ptr;
}
The Postfix code for the above function is as follows:
Postfix code |
---|
TEXT
ALIGN
GLOBL traverse, FUNC
LABEL traverse
ENTER 8 ; ptr@-4 ix@-8 vec@+8 lim@+12
; init prt (not assignment)
LOCAL +8
LDINT ; vec
LOCAL +12
LDINT ; lim
INT 4 ; sizeof int
MUL
ADD ; vec + lim
INT 1
INT 4 ; sizeof int
MUL
SUB ; vec + lim - 1
LOCAL -4
STINT ; ptr = vec + lim - 1
; init ix (not assignment)
LOCAL +12
LDINT ; lim
INT 2
SUB
LOCAL -8
STINT ; ix = lim -2
; while start: test
ALIGN
LABEL while_test
LOCAL -8
LDINT
INT 0
GE ; ix >= 0
JZ while_end
; while block
; ?: operator
LOCAL +8
LDINT ; vec
LOCAL -8
LDINT ; ix
INT 4 ; sizeof int
MUL
ADD ; vec + ix
LDINT ; *(vec+ix) --> vec[ix]
LOCAL -4
LDINT ; ptr
LDINT ; *ptr
GT
JZ three_false_part
; ?: true part
LOCAL +8
LDINT ; vec
LOCAL -8
LDINT ; ix
INT 4 ; sizeof int
MUL
ADD ; vec + ix
JMP three_end
; ?: false part
ALIGN
LABEL three_false_part
LOCAL -4
LDINT ; ptr
; ?: end
ALIGN
LABEL three_end
DUP32 ; for assignment
LOCAL -4
STINT ; ptr = ?: ...
; trash expression value (used as instruction)
TRASH 4
; decrement ix
LOCAL -8
LDINT ; ix
DUP32
INT 1
SUB
LOCAL -8
STINT ; ix = ix - 1
TRASH 4 ; (ix-- used as instruction)
; end while block
JMP while_test
; exit while cycle
ALIGN
LABEL while_end
; return ptr
LOCAL -4
LDINT
STFVAL32
LEAVE
RET
|
To compile the Postfix code directly, pf2asm can be used:
pf2asm traverse.pf yasm -felf traverse.asm