a1	RN 0
a2	RN 1
a3	RN 2
a4	RN 3
z_fp    RN 7
z_sp    RN 8
z_pc    RN 9
ip	RN 12
sp      RN 13
lr	RN 14
pc	RN 15

	GET	hdr.apcs

        AREA |C$$code|, CODE, READONLY

        EXPORT  load_operand
        EXPORT  load_operand_s

;        IMPORT  fp
        IMPORT  h_globals_offset
        IMPORT  datap

; load_operand must use ONLY a1-a3. interpret depends on it.

load_operand
        CMP     a1,#1           ; LT = word; EQ = byte; GT = variable
load_operand_s
        LDRB    a1,[z_pc],#1    ; a1 = next byte
        LDRLTB  a3,[z_pc],#1    ; a3 = next byte (if word)
        ORRLT   a1,a3,a1,LSL #8
        Return  ,LinkNotStacked,LE

        TEQS    a1,#0
        LDREQ   a1,[z_sp],#4    ; var 0 => pop stack
        Return  ,LinkNotStacked,EQ

        SUBS    a2,a1,#16
        LDRLT   a1,[z_fp,-a1,LSL #2]
        Return  ,LinkNotStacked,LT

        LDR     a1,=globalp
        LDR     a3,[a1]
        LDRB    a1,[a3,a2,LSL #1]!
        LDRB    a2,[a3,#1]
        ORR     a1,a2,a1,LSL #8
        Return  ,LinkNotStacked

        EXPORT  load_variable
load_variable
        TEQS    a1,#0
        LDREQ   a1,[z_sp]       ; var 0 => peek stack
        Return  ,LinkNotStacked,EQ

        SUBS    a2,a1,#16
        LDRLT   a1,[z_fp,-a1,LSL #2]
        Return  ,LinkNotStacked,LT

        LDR     a1,=globalp
        LDR     a3,[a1]
        LDRB    a1,[a3,a2,LSL #1]!
        LDRB    a2,[a3,#1]
        ORR     a1,a2,a1,LSL #8
        Return  ,LinkNotStacked

        EXPORT  store_operand
store_operand
        MOV     ip,a1,LSL #16
        LDRB    a1,[z_pc],#1
        MOV     a2,ip,LSR #16
        TEQS    a1,#0
        STREQ   a2,[z_sp,#-4]!  ; var 0 => push stack
        Return  ,LinkNotStacked,EQ
        SUBS    a3,a1,#16
        STRLT   a2,[z_fp,-a1,LSL #2]
        Return  ,LinkNotStacked,LT

        LDR     a1,=globalp
        LDR     a1,[a1]
        MOV     ip,a2,LSR #8
        STRB    ip,[a1,a3,LSL #1]!
        STRB    a2,[a1,#1]
        Return  ,LinkNotStacked

        EXPORT  z_store
z_store
        TEQS    a1,#0
        STREQ   a2,[z_sp]       ; var 0 => poke stack
        Return  ,LinkNotStacked,EQ
        SUBS    a3,a1,#16
        STRLT   a2,[z_fp,-a1,LSL #2]
        Return  ,LinkNotStacked,LT

        LDR     a1,=globalp
        LDR     a1,[a1]
        MOV     ip,a2,LSR #8
        STRB    ip,[a1,a3,LSL #1]!
        STRB    a2,[a1,#1]
        Return  ,LinkNotStacked

        IMPORT  z_ret
        EXPORT  conditional_jump
        ; We require a1 to be 0 or 1 only...
conditional_jump
        LDRB    a2,[z_pc],#1
        EOR     a2,a2,a1,LSL #7
        AND     a1,a2,#&3F
        MOVS    a2,a2,LSL #25           ; C = False/True, N = Short
        LDRPLB  a4,[z_pc],#1
        Return  ,LinkNotStacked,CS
        ORRPL   a1,a4,a1,LSL #8
        CMP     a1,#1
        BLS     z_ret
        MOV     a1,a1,LSL #18
        ADD     z_pc,z_pc,a1,ASR #18
        SUB     z_pc,z_pc,#2
        Return  ,LinkNotStacked

        EXPORT  conditional_jump_eq
conditional_jump_eq
        LDRB    a2,[z_pc],#1
        EORNE   a2,a2,#&80
        AND     a1,a2,#&3F
        MOVS    a2,a2,LSL #25           ; C = True/False, N = Short
        LDRPLB  a4,[z_pc],#1
        Return  ,LinkNotStacked,CC
        ORRPL   a1,a4,a1,LSL #8
        CMP     a1,#1
        BLS     z_ret
        MOV     a1,a1,LSL #18
        ADD     z_pc,z_pc,a1,ASR #18
        SUB     z_pc,z_pc,#2
        Return  ,LinkNotStacked

	EXPORT	z_push
z_push
	STR	a1,[z_sp,#-4]!
        Return  ,LinkNotStacked

        EXPORT  globalp

        AREA    |Asm$$zidata|,DATA,NOINIT
globalp
        %       4

        END
