From f00d2f06c9cca931be6fae8086e72f952b30e045 Mon Sep 17 00:00:00 2001 From: Irmen de Jong Date: Sat, 12 Jan 2019 02:36:43 +0100 Subject: [PATCH] fix stackvm comparison/jnz/bnz --- compiler/src/prog8/compiler/Compiler.kt | 5 +- compiler/src/prog8/stackvm/StackVm.kt | 63 ++- examples/test.p8 | 527 +----------------------- 3 files changed, 64 insertions(+), 531 deletions(-) diff --git a/compiler/src/prog8/compiler/Compiler.kt b/compiler/src/prog8/compiler/Compiler.kt index 006de5618..15543ce93 100644 --- a/compiler/src/prog8/compiler/Compiler.kt +++ b/compiler/src/prog8/compiler/Compiler.kt @@ -1860,10 +1860,7 @@ private class StatementTranslator(private val prog: IntermediateProgram, prog.instr(opcodeIncvar(indexVarType), callLabel = indexVar.scopedname) prog.instr(opcodePushvar(indexVarType), callLabel = indexVar.scopedname) prog.instr(opcodeCompare(indexVarType), Value(indexVarType, numElements)) - if(indexVarType==DataType.UWORD) - prog.instr(Opcode.JNZW, callLabel = loopLabel) - else - prog.instr(Opcode.JNZ, callLabel = loopLabel) + prog.instr(Opcode.BNZ, callLabel = loopLabel) prog.label(breakLabel) prog.instr(Opcode.NOP) diff --git a/compiler/src/prog8/stackvm/StackVm.kt b/compiler/src/prog8/stackvm/StackVm.kt index a1a1f49cd..dc231ac91 100644 --- a/compiler/src/prog8/stackvm/StackVm.kt +++ b/compiler/src/prog8/stackvm/StackVm.kt @@ -120,6 +120,10 @@ class StackVm(private var traceOutputFile: String?) { val mem = Memory() var P_carry: Boolean = false private set + var P_zero: Boolean = true + private set + var P_negative: Boolean = false + private set var P_irqd: Boolean = false private set var variables = mutableMapOf() // all variables (set of all vars used by all blocks/subroutines) key = their fully scoped name @@ -379,30 +383,71 @@ class StackVm(private var traceOutputFile: String?) { checkDt(second, DataType.FLOAT) evalstack.push(second.add(top)) } - Opcode.SUB_UB, Opcode.CMP_UB -> { + Opcode.SUB_UB -> { val (top, second) = evalstack.pop2() checkDt(top, DataType.UBYTE) checkDt(second, DataType.UBYTE) evalstack.push(second.sub(top)) } - Opcode.SUB_UW, Opcode.CMP_UW -> { + Opcode.SUB_UW -> { val (top, second) = evalstack.pop2() checkDt(top, DataType.UWORD) checkDt(second, DataType.UWORD) evalstack.push(second.sub(top)) } - Opcode.SUB_B, Opcode.CMP_B -> { + Opcode.SUB_B -> { val (top, second) = evalstack.pop2() checkDt(top, DataType.BYTE) checkDt(second, DataType.BYTE) evalstack.push(second.sub(top)) } - Opcode.SUB_W, Opcode.CMP_W -> { + Opcode.SUB_W -> { val (top, second) = evalstack.pop2() checkDt(top, DataType.WORD) checkDt(second, DataType.WORD) evalstack.push(second.sub(top)) } + Opcode.CMP_UB -> { + val value = evalstack.pop() + val other = ins.arg!! + checkDt(value, DataType.UBYTE) + checkDt(other, DataType.UBYTE) + val comparison = value.compareTo(other) + P_zero = comparison==0 + P_negative = comparison<0 + P_carry = comparison>=0 + } + Opcode.CMP_UW -> { + val value = evalstack.pop() + val other = ins.arg!! + checkDt(value, DataType.UWORD) + checkDt(other, DataType.UWORD) + val comparison = value.compareTo(other) + P_zero = comparison==0 + P_negative = comparison<0 + P_carry = comparison>=0 + } + Opcode.CMP_B -> { + val value = evalstack.pop() + val other = ins.arg!! + checkDt(value, DataType.BYTE) + checkDt(other, DataType.BYTE) + val comparison = value.compareTo(other) + P_zero = comparison==0 + P_negative = comparison<0 + P_carry = comparison>=0 + } + Opcode.CMP_W -> { + val value = evalstack.pop() + val other = ins.arg!! + checkDt(value, DataType.WORD) + checkDt(other, DataType.WORD) + val result = value.sub(other) + val comparison = value.compareTo(other) + P_zero = comparison==0 + P_negative = comparison<0 + P_carry = comparison>=0 + } Opcode.SUB_F -> { val (top, second) = evalstack.pop2() checkDt(top, DataType.FLOAT) @@ -771,8 +816,14 @@ class StackVm(private var traceOutputFile: String?) { return if(P_carry) ins.next else ins.nextAlt!! Opcode.BCC -> return if(P_carry) ins.nextAlt!! else ins.next - Opcode.BZ, Opcode.BNZ -> throw VmExecutionException("StackVM doesn't support the 'zero' cpu flag") - Opcode.BNEG, Opcode.BPOS -> throw VmExecutionException("StackVM doesn't support the 'neg' cpu flag") + Opcode.BZ -> + return if(P_zero) ins.next else ins.nextAlt!! + Opcode.BNZ -> + return if(P_zero) ins.nextAlt!! else ins.next + Opcode.BNEG -> + return if(P_negative) ins.next else ins.nextAlt!! + Opcode.BPOS -> + return if(P_negative) ins.nextAlt!! else ins.next Opcode.BVS, Opcode.BVC -> throw VmExecutionException("stackVM doesn't support the 'overflow' cpu flag") Opcode.JZ -> { val value = evalstack.pop().integerValue() and 255 diff --git a/examples/test.p8 b/examples/test.p8 index 3e6b7ccdb..6e404df57 100644 --- a/examples/test.p8 +++ b/examples/test.p8 @@ -4,528 +4,13 @@ sub start() { - ubyte i = 10 - ubyte ub2 - byte j = 5 - byte b2 - uword uw = 1000 - uword uw2 - word w = 1000 - word w2 - -; i=10 -; ub2=i*1 -; c64scr.print_ub(ub2) -; c64.CHROUT('\n') -; ub2=i*2 -; c64scr.print_ub(ub2) -; c64.CHROUT('\n') -; ub2=i*3 -; c64scr.print_ub(ub2) -; c64.CHROUT('\n') -; ub2=i*4 -; c64scr.print_ub(ub2) -; c64.CHROUT('\n') -; ub2=i*5 -; c64scr.print_ub(ub2) -; c64.CHROUT('\n') -; ub2=i*6 -; c64scr.print_ub(ub2) -; c64.CHROUT('\n') -; ub2=i*7 -; c64scr.print_ub(ub2) -; c64.CHROUT('\n') -; ub2=i*8 -; c64scr.print_ub(ub2) -; c64.CHROUT('\n') -; ub2=i*9 -; c64scr.print_ub(ub2) -; c64.CHROUT('\n') -; ub2=i*10 -; c64scr.print_ub(ub2) -; c64.CHROUT('\n') -; ub2=i*11 -; c64scr.print_ub(ub2) -; c64.CHROUT('\n') -; ub2=i*12 -; c64scr.print_ub(ub2) -; c64.CHROUT('\n') -; ub2=i*13 -; c64scr.print_ub(ub2) -; c64.CHROUT('\n') -; ub2=i*14 -; c64scr.print_ub(ub2) -; c64.CHROUT('\n') -; ub2=i*15 -; c64scr.print_ub(ub2) -; c64.CHROUT('\n') -; ub2=i*16 -; c64scr.print_ub(ub2) -; c64.CHROUT('\n') -; ub2=i*17 -; c64scr.print_ub(ub2) -; c64.CHROUT('\n') -; ub2=i*18 -; c64scr.print_ub(ub2) -; c64.CHROUT('\n') -; ub2=i*19 -; c64scr.print_ub(ub2) -; c64.CHROUT('\n') -; ub2=i*20 -; c64scr.print_ub(ub2) -; c64.CHROUT('\n') -; ub2=i*21 -; c64scr.print_ub(ub2) -; c64.CHROUT('\n') -; ub2=i*22 -; c64scr.print_ub(ub2) -; c64.CHROUT('\n') -; ub2=i*23 -; c64scr.print_ub(ub2) -; c64.CHROUT('\n') -; ub2=i*24 -; c64scr.print_ub(ub2) -; c64.CHROUT('\n') -; ub2=i*25 -; c64scr.print_ub(ub2) -; c64.CHROUT('\n') -; -; i=5 -; ub2=i*40 -; c64scr.print_ub(ub2) -; c64.CHROUT('\n') -; -; c64.CHROUT('\n') -; -; -; j=5 -; b2=j*1 -; c64scr.print_b(b2) -; c64.CHROUT('\n') -; b2=j*2 -; c64scr.print_b(b2) -; c64.CHROUT('\n') -; b2=j*3 -; c64scr.print_b(b2) -; c64.CHROUT('\n') -; b2=j*4 -; c64scr.print_b(b2) -; c64.CHROUT('\n') -; b2=j*5 -; c64scr.print_b(b2) -; c64.CHROUT('\n') -; b2=j*6 -; c64scr.print_b(b2) -; c64.CHROUT('\n') -; b2=j*7 -; c64scr.print_b(b2) -; c64.CHROUT('\n') -; b2=j*8 -; c64scr.print_b(b2) -; c64.CHROUT('\n') -; b2=j*9 -; c64scr.print_b(b2) -; c64.CHROUT('\n') -; b2=j*10 -; c64scr.print_b(b2) -; c64.CHROUT('\n') -; b2=j*11 -; c64scr.print_b(b2) -; c64.CHROUT('\n') -; b2=j*12 -; c64scr.print_b(b2) -; c64.CHROUT('\n') -; b2=j*13 -; c64scr.print_b(b2) -; c64.CHROUT('\n') -; b2=j*14 -; c64scr.print_b(b2) -; c64.CHROUT('\n') -; b2=j*15 -; c64scr.print_b(b2) -; c64.CHROUT('\n') -; b2=j*16 -; c64scr.print_b(b2) -; c64.CHROUT('\n') -; b2=j*17 -; c64scr.print_b(b2) -; c64.CHROUT('\n') -; b2=j*18 -; c64scr.print_b(b2) -; c64.CHROUT('\n') -; b2=j*19 -; c64scr.print_b(b2) -; c64.CHROUT('\n') -; b2=j*20 -; c64scr.print_b(b2) -; c64.CHROUT('\n') -; b2=j*21 -; c64scr.print_b(b2) -; c64.CHROUT('\n') -; b2=j*22 -; c64scr.print_b(b2) -; c64.CHROUT('\n') -; b2=j*23 -; c64scr.print_b(b2) -; c64.CHROUT('\n') -; b2=j*24 -; c64scr.print_b(b2) -; c64.CHROUT('\n') -; b2=j*25 -; c64scr.print_b(b2) -; c64.CHROUT('\n') -; -; j=3 -; b2=j*40 -; c64scr.print_b(b2) -; c64.CHROUT('\n') -; -; c64.CHROUT('\n') -; -; -; ; multiplication by negative values -; j=5 -; b2=j*-1 -; c64scr.print_b(b2) -; c64.CHROUT('\n') -; b2=j*-2 -; c64scr.print_b(b2) -; c64.CHROUT('\n') -; b2=j*-3 -; c64scr.print_b(b2) -; c64.CHROUT('\n') -; b2=j*-4 -; c64scr.print_b(b2) -; c64.CHROUT('\n') -; b2=j*-5 -; c64scr.print_b(b2) -; c64.CHROUT('\n') -; b2=j*-6 -; c64scr.print_b(b2) -; c64.CHROUT('\n') -; b2=j*-7 -; c64scr.print_b(b2) -; c64.CHROUT('\n') -; b2=j*-8 -; c64scr.print_b(b2) -; c64.CHROUT('\n') -; b2=j*-9 -; c64scr.print_b(b2) -; c64.CHROUT('\n') -; b2=j*-10 -; c64scr.print_b(b2) -; c64.CHROUT('\n') -; b2=j*-11 -; c64scr.print_b(b2) -; c64.CHROUT('\n') -; b2=j*-12 -; c64scr.print_b(b2) -; c64.CHROUT('\n') -; b2=j*-13 -; c64scr.print_b(b2) -; c64.CHROUT('\n') -; b2=j*-14 -; c64scr.print_b(b2) -; c64.CHROUT('\n') -; b2=j*-15 -; c64scr.print_b(b2) -; c64.CHROUT('\n') -; b2=j*-16 -; c64scr.print_b(b2) -; c64.CHROUT('\n') -; b2=j*-17 -; c64scr.print_b(b2) -; c64.CHROUT('\n') -; b2=j*-18 -; c64scr.print_b(b2) -; c64.CHROUT('\n') -; b2=j*-19 -; c64scr.print_b(b2) -; c64.CHROUT('\n') -; b2=j*-20 -; c64scr.print_b(b2) -; c64.CHROUT('\n') -; b2=j*-21 -; c64scr.print_b(b2) -; c64.CHROUT('\n') -; b2=j*-22 -; c64scr.print_b(b2) -; c64.CHROUT('\n') -; b2=j*-23 -; c64scr.print_b(b2) -; c64.CHROUT('\n') -; b2=j*-24 -; c64scr.print_b(b2) -; c64.CHROUT('\n') -; b2=j*-25 -; c64scr.print_b(b2) -; c64.CHROUT('\n') -; -; j=3 -; b2=j*-40 -; c64scr.print_b(b2) -; c64.CHROUT('\n') -; -; c64.CHROUT('\n') - - - ;@todo the same, for uword and word - - uw=1000 - uw2=uw*1 - c64scr.print_uw(uw2) - c64.CHROUT('\n') - uw2=uw*2 - c64scr.print_uw(uw2) - c64.CHROUT('\n') - uw2=uw*3 - c64scr.print_uw(uw2) - c64.CHROUT('\n') - uw2=uw*4 - c64scr.print_uw(uw2) - c64.CHROUT('\n') - uw2=uw*5 - c64scr.print_uw(uw2) - c64.CHROUT('\n') - uw2=uw*6 - c64scr.print_uw(uw2) - c64.CHROUT('\n') - uw2=uw*7 - c64scr.print_uw(uw2) - c64.CHROUT('\n') - uw2=uw*8 - c64scr.print_uw(uw2) - c64.CHROUT('\n') - uw2=uw*9 - c64scr.print_uw(uw2) - c64.CHROUT('\n') - uw2=uw*10 - c64scr.print_uw(uw2) - c64.CHROUT('\n') - uw2=uw*11 - c64scr.print_uw(uw2) - c64.CHROUT('\n') - uw2=uw*12 - c64scr.print_uw(uw2) - c64.CHROUT('\n') - uw2=uw*13 - c64scr.print_uw(uw2) - c64.CHROUT('\n') - uw2=uw*14 - c64scr.print_uw(uw2) - c64.CHROUT('\n') - uw2=uw*15 - c64scr.print_uw(uw2) - c64.CHROUT('\n') - uw2=uw*16 - c64scr.print_uw(uw2) - c64.CHROUT('\n') - uw2=uw*17 - c64scr.print_uw(uw2) - c64.CHROUT('\n') - uw2=uw*18 - c64scr.print_uw(uw2) - c64.CHROUT('\n') - uw2=uw*19 - c64scr.print_uw(uw2) - c64.CHROUT('\n') - uw2=uw*20 - c64scr.print_uw(uw2) - c64.CHROUT('\n') - uw2=uw*21 - c64scr.print_uw(uw2) - c64.CHROUT('\n') - uw2=uw*22 - c64scr.print_uw(uw2) - c64.CHROUT('\n') - uw2=uw*23 - c64scr.print_uw(uw2) - c64.CHROUT('\n') - uw2=uw*24 - c64scr.print_uw(uw2) - c64.CHROUT('\n') - uw2=uw*25 - c64scr.print_uw(uw2) - c64.CHROUT('\n') - - uw=500 - uw2=uw*40 - c64scr.print_uw(uw2) - c64.CHROUT('\n') - - c64.CHROUT('\n') - - - w=500 - w2=w*1 - c64scr.print_w(w2) - c64.CHROUT('\n') - w2=w*2 - c64scr.print_w(w2) - c64.CHROUT('\n') - w2=w*3 - c64scr.print_w(w2) - c64.CHROUT('\n') - w2=w*4 - c64scr.print_w(w2) - c64.CHROUT('\n') - w2=w*5 - c64scr.print_w(w2) - c64.CHROUT('\n') - w2=w*6 - c64scr.print_w(w2) - c64.CHROUT('\n') - w2=w*7 - c64scr.print_w(w2) - c64.CHROUT('\n') - w2=w*8 - c64scr.print_w(w2) - c64.CHROUT('\n') - w2=w*9 - c64scr.print_w(w2) - c64.CHROUT('\n') - w2=w*10 - c64scr.print_w(w2) - c64.CHROUT('\n') - w2=w*11 - c64scr.print_w(w2) - c64.CHROUT('\n') - w2=w*12 - c64scr.print_w(w2) - c64.CHROUT('\n') - w2=w*13 - c64scr.print_w(w2) - c64.CHROUT('\n') - w2=w*14 - c64scr.print_w(w2) - c64.CHROUT('\n') - w2=w*15 - c64scr.print_w(w2) - c64.CHROUT('\n') - w2=w*16 - c64scr.print_w(w2) - c64.CHROUT('\n') - w2=w*17 - c64scr.print_w(w2) - c64.CHROUT('\n') - w2=w*18 - c64scr.print_w(w2) - c64.CHROUT('\n') - w2=w*19 - c64scr.print_w(w2) - c64.CHROUT('\n') - w2=w*20 - c64scr.print_w(w2) - c64.CHROUT('\n') - w2=w*21 - c64scr.print_w(w2) - c64.CHROUT('\n') - w2=w*22 - c64scr.print_w(w2) - c64.CHROUT('\n') - w2=w*23 - c64scr.print_w(w2) - c64.CHROUT('\n') - w2=w*24 - c64scr.print_w(w2) - c64.CHROUT('\n') - w2=w*25 - c64scr.print_w(w2) - c64.CHROUT('\n') - - w=500 - w2=w*40 - c64scr.print_w(w2) - c64.CHROUT('\n') - - c64.CHROUT('\n') - - - ; multuwpluwcatuwon by negatuwve values - w=500 - w2=w*-1 - c64scr.print_w(w2) - c64.CHROUT('\n') - w2=w*-2 - c64scr.print_w(w2) - c64.CHROUT('\n') - w2=w*-3 - c64scr.print_w(w2) - c64.CHROUT('\n') - w2=w*-4 - c64scr.print_w(w2) - c64.CHROUT('\n') - w2=w*-5 - c64scr.print_w(w2) - c64.CHROUT('\n') - w2=w*-6 - c64scr.print_w(w2) - c64.CHROUT('\n') - w2=w*-7 - c64scr.print_w(w2) - c64.CHROUT('\n') - w2=w*-8 - c64scr.print_w(w2) - c64.CHROUT('\n') - w2=w*-9 - c64scr.print_w(w2) - c64.CHROUT('\n') - w2=w*-10 - c64scr.print_w(w2) - c64.CHROUT('\n') - w2=w*-11 - c64scr.print_w(w2) - c64.CHROUT('\n') - w2=w*-12 - c64scr.print_w(w2) - c64.CHROUT('\n') - w2=w*-13 - c64scr.print_w(w2) - c64.CHROUT('\n') - w2=w*-14 - c64scr.print_w(w2) - c64.CHROUT('\n') - w2=w*-15 - c64scr.print_w(w2) - c64.CHROUT('\n') - w2=w*-16 - c64scr.print_w(w2) - c64.CHROUT('\n') - w2=w*-17 - c64scr.print_w(w2) - c64.CHROUT('\n') - w2=w*-18 - c64scr.print_w(w2) - c64.CHROUT('\n') - w2=w*-19 - c64scr.print_w(w2) - c64.CHROUT('\n') - w2=w*-20 - c64scr.print_w(w2) - c64.CHROUT('\n') - w2=w*-21 - c64scr.print_w(w2) - c64.CHROUT('\n') - w2=w*-22 - c64scr.print_w(w2) - c64.CHROUT('\n') - w2=w*-23 - c64scr.print_w(w2) - c64.CHROUT('\n') - w2=w*-24 - c64scr.print_w(w2) - c64.CHROUT('\n') - w2=w*-25 - c64scr.print_w(w2) - c64.CHROUT('\n') - - w=500 - w2=w*-40 - c64scr.print_w(w2) - c64.CHROUT('\n') - - c64.CHROUT('\n') + str question = "how are you?\n" + ; use iteration to write text + for ubyte char in question { ; @todo fix iteration + ;vm_write_char(char) + c64.CHROUT(char) + } } }