diff --git a/codeGenCpu6502/src/prog8/codegen/cpu6502/assignment/AssignmentAsmGen.kt b/codeGenCpu6502/src/prog8/codegen/cpu6502/assignment/AssignmentAsmGen.kt index 069fdb510..1cccb3890 100644 --- a/codeGenCpu6502/src/prog8/codegen/cpu6502/assignment/AssignmentAsmGen.kt +++ b/codeGenCpu6502/src/prog8/codegen/cpu6502/assignment/AssignmentAsmGen.kt @@ -324,18 +324,24 @@ internal class AssignmentAsmGen(private val program: Program, } internal fun assignPrefixedExpressionToArrayElt(assign: AsmAssignment) { - // array[x] = -value ... use a tempvar then store that back into the array. require(assign.source.expression is PrefixExpression) - val tempvar = asmgen.getTempVarName(assign.target.datatype).joinToString(".") - val assignToTempvar = AsmAssignment(assign.source, - AsmAssignTarget(TargetStorageKind.VARIABLE, asmgen, assign.target.datatype, assign.target.scope, variableAsmName=tempvar, origAstTarget = assign.target.origAstTarget), - false, program.memsizer, assign.position) - asmgen.translateNormalAssignment(assignToTempvar) - when(assign.target.datatype) { - in ByteDatatypes -> assignVariableByte(assign.target, tempvar) - in WordDatatypes -> assignVariableWord(assign.target, tempvar) - DataType.FLOAT -> assignVariableFloat(assign.target, tempvar) - else -> throw AssemblyError("weird dt") + if(assign.source.datatype==DataType.FLOAT) { + // floatarray[x] = -value ... just use FAC1 to calculate the expression into and then store that back into the array. + assignExpressionToRegister(assign.source.expression, RegisterOrPair.FAC1, true) + assignFAC1float(assign.target) + } else { + // array[x] = -value ... use a tempvar then store that back into the array. + val tempvar = asmgen.getTempVarName(assign.target.datatype).joinToString(".") + val assignToTempvar = AsmAssignment(assign.source, + AsmAssignTarget(TargetStorageKind.VARIABLE, asmgen, assign.target.datatype, assign.target.scope, variableAsmName=tempvar, origAstTarget = assign.target.origAstTarget), + false, program.memsizer, assign.position) + asmgen.translateNormalAssignment(assignToTempvar) + when(assign.target.datatype) { + in ByteDatatypes -> assignVariableByte(assign.target, tempvar) + in WordDatatypes -> assignVariableWord(assign.target, tempvar) + DataType.FLOAT -> assignVariableFloat(assign.target, tempvar) + else -> throw AssemblyError("weird dt") + } } } diff --git a/codeGenCpu6502/src/prog8/codegen/cpu6502/assignment/AugmentableAssignmentAsmGen.kt b/codeGenCpu6502/src/prog8/codegen/cpu6502/assignment/AugmentableAssignmentAsmGen.kt index 4853e5d87..57679696b 100644 --- a/codeGenCpu6502/src/prog8/codegen/cpu6502/assignment/AugmentableAssignmentAsmGen.kt +++ b/codeGenCpu6502/src/prog8/codegen/cpu6502/assignment/AugmentableAssignmentAsmGen.kt @@ -1965,6 +1965,13 @@ internal class AugmentableAssignmentAsmGen(private val program: Program, } DataType.FLOAT -> { when (target.kind) { + TargetStorageKind.REGISTER -> { + when(target.register!!) { + RegisterOrPair.FAC1 -> asmgen.out(" jsr floats.NEGOP") + RegisterOrPair.FAC2 -> asmgen.out(" jsr floats.MOVFA | jsr floats.NEGOP | jsr floats.MOVEF") + else -> throw AssemblyError("invalid float register") + } + } TargetStorageKind.VARIABLE -> { // simply flip the sign bit in the float asmgen.out(""" @@ -1975,7 +1982,7 @@ internal class AugmentableAssignmentAsmGen(private val program: Program, } TargetStorageKind.STACK -> TODO("no asm gen for float stack negate") TargetStorageKind.ARRAY -> assignmentAsmGen.assignPrefixedExpressionToArrayElt(assign) - else -> throw AssemblyError("weird target for float negation") + else -> throw AssemblyError("weird target for in-place float negation") } } else -> throw AssemblyError("negate of invalid type") diff --git a/codeOptimizers/src/prog8/optimizer/StatementOptimizer.kt b/codeOptimizers/src/prog8/optimizer/StatementOptimizer.kt index 57dc67daf..6c44d5ce4 100644 --- a/codeOptimizers/src/prog8/optimizer/StatementOptimizer.kt +++ b/codeOptimizers/src/prog8/optimizer/StatementOptimizer.kt @@ -293,9 +293,9 @@ class StatementOptimizer(private val program: Program, val bexpr=assignment.value as? BinaryExpression if(bexpr!=null) { val rightCv = bexpr.right.constValue(program)?.number - if(bexpr.operator=="-" && rightCv==null) { + if(bexpr.operator=="-" && rightCv==null && targetIDt.isInteger) { if(bexpr.right.isSimple && bexpr.right isSameAs assignment.target) { - // X = value - X --> X = -X ; X += value (to avoid need of stack-evaluation) + // X = value - X --> X = -X ; X += value (to avoid need of stack-evaluation, for integers) val negation = PrefixExpression("-", bexpr.right.copy(), bexpr.position) val addValue = Assignment(assignment.target.copy(), BinaryExpression(bexpr.right, "+", bexpr.left, bexpr.position), AssignmentOrigin.OPTIMIZER, assignment.position) return listOf( diff --git a/docs/source/todo.rst b/docs/source/todo.rst index 6626813e1..6cbfb7c9a 100644 --- a/docs/source/todo.rst +++ b/docs/source/todo.rst @@ -3,7 +3,6 @@ TODO For next release ^^^^^^^^^^^^^^^^ -- check StatementOptimizer "optimize binary expressions a bit": flt[1] = 3.0-flt[1] beneficial or not? what about integer array? - ir: get rid of '_' label prefix? - fix expericodegen (ir code gen for regular cx16 target) @@ -53,7 +52,7 @@ Libraries: - optimize several inner loops in gfx2 even further? - add modes 3 and perhaps even 2 to gfx2 (lores 16 color and 4 color)? - add a flood fill (span fill/scanline fill) routine to gfx2? -- add a p +- add a pget() to gfx2 to get the pixel color value Expressions: diff --git a/examples/test.p8 b/examples/test.p8 index 99a0ac434..1ce3a2084 100644 --- a/examples/test.p8 +++ b/examples/test.p8 @@ -7,7 +7,7 @@ main { sub start() { flt[1] = 42.42 - flt[1] = 3-flt[1] + flt[1] = -flt[1] floats.print_f(flt[1]) } }