diff --git a/compiler/src/prog8/compiler/target/c64/codegen/AsmGen.kt b/compiler/src/prog8/compiler/target/c64/codegen/AsmGen.kt index 5646ab4d1..b044a9cf3 100644 --- a/compiler/src/prog8/compiler/target/c64/codegen/AsmGen.kt +++ b/compiler/src/prog8/compiler/target/c64/codegen/AsmGen.kt @@ -740,38 +740,40 @@ internal class AsmGen(private val program: Program, loopContinueLabels.pop() } - private fun repeatWordCountInAY(counterLabel: String, repeatLabel: String, endLabel: String, body: AnonymousScope) { + private fun repeatWordCountInAY(counterVar: String, repeatLabel: String, endLabel: String, body: AnonymousScope) { // note: A/Y must have been loaded with the number of iterations already! + // TODO allocate word counterVar on zeropage preferrably out(""" - sta $counterLabel - sty $counterLabel+1 -$repeatLabel lda $counterLabel + sta $counterVar + sty $counterVar+1 +$repeatLabel lda $counterVar bne + - lda $counterLabel+1 + lda $counterVar+1 beq $endLabel -+ lda $counterLabel ++ lda $counterVar bne + - dec $counterLabel+1 -+ dec $counterLabel + dec $counterVar+1 ++ dec $counterVar """) translate(body) out(""" jmp $repeatLabel -$counterLabel .word 0 +$counterVar .word 0 $endLabel""") } - private fun repeatByteCountInA(counterLabel: String, repeatLabel: String, endLabel: String, body: AnonymousScope) { + private fun repeatByteCountInA(counterVar: String, repeatLabel: String, endLabel: String, body: AnonymousScope) { // note: A must have been loaded with the number of iterations already! + // TODO allocate word counterVar on zeropage preferrably out(""" - sta $counterLabel -$repeatLabel lda $counterLabel + sta $counterVar +$repeatLabel lda $counterVar beq $endLabel - dec $counterLabel""") + dec $counterVar""") translate(body) out(""" jmp $repeatLabel -$counterLabel .byte 0 +$counterVar .byte 0 $endLabel""") } diff --git a/compiler/src/prog8/compiler/target/c64/codegen/ForLoopsAsmGen.kt b/compiler/src/prog8/compiler/target/c64/codegen/ForLoopsAsmGen.kt index 6dd99eaa2..abfd2c8e2 100644 --- a/compiler/src/prog8/compiler/target/c64/codegen/ForLoopsAsmGen.kt +++ b/compiler/src/prog8/compiler/target/c64/codegen/ForLoopsAsmGen.kt @@ -14,9 +14,10 @@ import prog8.compiler.target.c64.C64MachineDefinition.ESTACK_LO_PLUS1_HEX import prog8.compiler.toHex import kotlin.math.absoluteValue +// todo optimized loop code for common simple cases 0..N, N..0, >=1..N , N..>=1 where N<=255 // todo choose more efficient comparisons to avoid needless lda's // todo optimize common case when step == 2 or -2 - +// todo allocate loop counter variable dynamically, preferrably on zeropage internal class ForLoopsAsmGen(private val program: Program, private val asmgen: AsmGen) { @@ -277,7 +278,7 @@ $continueLabel inc $loopLabel+1 $endLabel""") } DataType.ARRAY_UB, DataType.ARRAY_B -> { - // TODO: optimize loop code when the length of the array is < 256, don't need a separate counter var in such cases + // TODO: optimize loop code when the length of the array is < 256 val length = decl.arraysize!!.size()!! val counterLabel = asmgen.makeLabel("for_counter") val modifiedLabel = asmgen.makeLabel("for_modified") @@ -301,7 +302,7 @@ $counterLabel .byte 0 $endLabel""") } DataType.ARRAY_W, DataType.ARRAY_UW -> { - // TODO: optimize loop code when the length of the array is < 256, don't need a separate counter var in such cases + // TODO: optimize loop code when the length of the array is < 256 val length = decl.arraysize!!.size()!! * 2 val counterLabel = asmgen.makeLabel("for_counter") val modifiedLabel = asmgen.makeLabel("for_modified") @@ -343,7 +344,7 @@ $endLabel""") } private fun translateForOverConstRange(stmt: ForLoop, iterableDt: DataType, range: IntProgression) { - // TODO: optimize loop code when the range is < 256 iterations, don't need a separate counter var in such cases + // TODO: optimize loop code when the range is < 256 iterations if (range.isEmpty()) throw AssemblyError("empty range") val loopLabel = asmgen.makeLabel("for_loop")