From 513a68584ce58e382ce9bf624ac6953991dcb1a1 Mon Sep 17 00:00:00 2001 From: Irmen de Jong Date: Thu, 20 Aug 2020 21:42:38 +0200 Subject: [PATCH] implemented more optimized prefix expression codegen --- .../codegen/AugmentableAssignmentAsmGen.kt | 64 +++++++++++++++---- .../target/c64/codegen/PostIncrDecrAsmGen.kt | 2 +- examples/test.p8 | 58 ++++------------- 3 files changed, 65 insertions(+), 59 deletions(-) diff --git a/compiler/src/prog8/compiler/target/c64/codegen/AugmentableAssignmentAsmGen.kt b/compiler/src/prog8/compiler/target/c64/codegen/AugmentableAssignmentAsmGen.kt index 7df7b3142..c13a9f77d 100644 --- a/compiler/src/prog8/compiler/target/c64/codegen/AugmentableAssignmentAsmGen.kt +++ b/compiler/src/prog8/compiler/target/c64/codegen/AugmentableAssignmentAsmGen.kt @@ -3,13 +3,12 @@ package prog8.compiler.target.c64.codegen import prog8.ast.Program import prog8.ast.base.DataType import prog8.ast.base.IterableDatatypes -import prog8.ast.expressions.BinaryExpression -import prog8.ast.expressions.PrefixExpression -import prog8.ast.expressions.TypecastExpression +import prog8.ast.expressions.* import prog8.ast.statements.AssignTarget import prog8.ast.statements.Assignment import prog8.compiler.AssemblyError import prog8.compiler.target.c64.C64MachineDefinition.C64Zeropage +import prog8.compiler.toHex internal class AugmentableAssignmentAsmGen(private val program: Program, private val assignmentAsmGen: AssignmentAsmGen, @@ -98,7 +97,32 @@ internal class AugmentableAssignmentAsmGen(private val program: Program, sta $name""") } memory!=null -> { - TODO("in-place not of ubyte memory") + when (memory.addressExpression) { + is NumericLiteralValue -> { + val addr = (memory.addressExpression as NumericLiteralValue).number.toHex() + asmgen.out(""" + lda $addr + beq + + lda #1 ++ eor #1 + sta $addr""") + } + is IdentifierReference -> { + val name = asmgen.asmIdentifierName(memory.addressExpression as IdentifierReference) + asmgen.out(""" + lda $name + sta ${C64Zeropage.SCRATCH_W1} + lda $name+1 + sta ${C64Zeropage.SCRATCH_W1+1} + ldy #0 + lda (${C64Zeropage.SCRATCH_W1}),y + beq + + lda #1 ++ eor #1 + sta (${C64Zeropage.SCRATCH_W1}),y""") + } + else -> throw AssemblyError("weird address value") + } } arrayIdx!=null -> { TODO("in-place not of ubyte array") @@ -143,8 +167,28 @@ internal class AugmentableAssignmentAsmGen(private val program: Program, sta $name""") } memory!=null -> { - TODO("in-place invert ubyte memory") - } + when (memory.addressExpression) { + is NumericLiteralValue -> { + val addr = (memory.addressExpression as NumericLiteralValue).number.toHex() + asmgen.out(""" + lda $addr + eor #255 + sta $addr""") + } + is IdentifierReference -> { + val name = asmgen.asmIdentifierName(memory.addressExpression as IdentifierReference) + asmgen.out(""" + lda $name + sta ${C64Zeropage.SCRATCH_W1} + lda $name+1 + sta ${C64Zeropage.SCRATCH_W1+1} + ldy #0 + lda (${C64Zeropage.SCRATCH_W1}),y + eor #255 + sta (${C64Zeropage.SCRATCH_W1}),y""") + } + else -> throw AssemblyError("weird address value") + } } arrayIdx!=null -> { TODO("in-place invert ubyte array") } @@ -186,12 +230,8 @@ internal class AugmentableAssignmentAsmGen(private val program: Program, sbc $name sta $name""") } - memory!=null -> { - TODO("in-place negate byte memory") - } - arrayIdx!=null -> { - TODO("in-place negate byte array") - } + memory!=null -> throw AssemblyError("can't in-place negate memory ubyte") + arrayIdx!=null -> TODO("in-place negate byte array") } } DataType.WORD -> { diff --git a/compiler/src/prog8/compiler/target/c64/codegen/PostIncrDecrAsmGen.kt b/compiler/src/prog8/compiler/target/c64/codegen/PostIncrDecrAsmGen.kt index 86db3994b..915bc62a1 100644 --- a/compiler/src/prog8/compiler/target/c64/codegen/PostIncrDecrAsmGen.kt +++ b/compiler/src/prog8/compiler/target/c64/codegen/PostIncrDecrAsmGen.kt @@ -53,7 +53,7 @@ internal class PostIncrDecrAsmGen(private val program: Program, private val asmg else asmgen.out("+\tdec ${'$'}ffff\t; modified") } - else -> throw AssemblyError("weird target type $targetMemory") + else -> TODO("asmgen postincrdecr on memory expression") } } targetArrayIdx!=null -> { diff --git a/examples/test.p8 b/examples/test.p8 index 9e8bb7570..f44b7efc6 100644 --- a/examples/test.p8 +++ b/examples/test.p8 @@ -7,55 +7,21 @@ main { sub start() { - byte A = 99 - ubyte U = $18 - word B = 9999 - uword W = $18f0 - - c64scr.print_b(A) - c64.CHROUT('\n') - A = -A - c64scr.print_b(A) - c64.CHROUT('\n') - - U = ~U - c64scr.print_ubhex(U, true) - c64.CHROUT('\n') - U = not U - c64scr.print_ubhex(U, true) - c64.CHROUT('\n') - U = not U - c64scr.print_ubhex(U, true) - c64.CHROUT('\n') - - c64scr.print_w(B) - c64.CHROUT('\n') - B = -B - c64scr.print_w(B) - c64.CHROUT('\n') - - W = ~W - c64scr.print_uwhex(W, true) - c64.CHROUT('\n') - W = not W - c64scr.print_uwhex(W, true) - c64.CHROUT('\n') - W = not W - c64scr.print_uwhex(W, true) - c64.CHROUT('\n') - ;@($d020) += @($d020) ; TODO fix compiler hang + ;@($c000+A) ++ ; TODO implement this - W += 3 - @($d020) += 3 - - W = 43210 - W = W as ubyte - c64scr.print_uw(W) + uword addr = $c000 + @(addr) = $f1 + c64scr.print_ubhex(@(addr), true) + c64.CHROUT('\n') + @(addr) = - @(addr) + c64scr.print_ubhex(@(addr), true) + c64.CHROUT('\n') + @(addr) = - @(addr) + c64scr.print_ubhex(@(addr), true) c64.CHROUT('\n') - ubyte[] array = [1,2,3] - array[1] = array[1] as ubyte - W = array[0] + ;@($c000) = ! @($c000) + ;@($c000) = ~ @($c000) } }