From 34fb82969c0fc189477a2c21aa15d8e37c75ac81 Mon Sep 17 00:00:00 2001 From: Irmen de Jong Date: Tue, 2 Oct 2018 23:10:27 +0200 Subject: [PATCH] optimize assignment with literal value; const-convert value to target datatype literal if possible --- compiler/examples/test.p8 | 59 +++++-------------- .../src/prog8/optimizing/ConstantFolding.kt | 38 ++++++++++++ 2 files changed, 54 insertions(+), 43 deletions(-) diff --git a/compiler/examples/test.p8 b/compiler/examples/test.p8 index 3cb1f1837..508d88a63 100644 --- a/compiler/examples/test.p8 +++ b/compiler/examples/test.p8 @@ -1,53 +1,26 @@ +%option enable_floats ~ main { sub start() { - byte[10] barray1 - byte[10] barray2 = 11 - byte[10] barray3 = [1,2,3,4,5,6,7,8,9,255] + byte bvar = 128 + word wvar = 128 + float fvar = 128 - word[10] warray1 - word[10] warray2 = 112233 - word[10] warray3 = [1,2000,3000,4,5,6,7,8,9, 65535] - - byte[4,5] mvar1 - byte[4,5] mvar2 = 22 - byte[2,3] mvar3 = [1,2,3,4,5,6] - - float[3] farray1 - float[3] farray2 = 33.44 - float[3] farray2b = 33 - float[3] farray3 = [1,2,3] - float[3] farray4 = [1,2,35566] - float[3] farray5 = [1,2.22334,3.1415] - - str name = "irmen" - - byte i - word w - - _vm_write_str(name) - _vm_write_char('\n') - name[2] = '@' - _vm_write_str(name) - _vm_write_char('\n') - - for i in barray3 { - _vm_write_num(i) - _vm_write_char('\n') - } - - for w in warray3 { - _vm_write_num(w) - _vm_write_char('\n') - } - - for i in name { - _vm_write_num(i) - _vm_write_char('\n') - } + bvar = 1 + bvar = 2.0 + ;bvar = 2.w ; @todo don't crash + wvar = 1 ; @todo optimize byte literal to word literal + wvar = 2.w + wvar = 2.0 + wvar = bvar + fvar = 1 ; @todo optimize byte literal to float literal + fvar = 2.w ; @todo optimize word literal to float literal + fvar = 22.33 + fvar = bvar + fvar = wvar return diff --git a/compiler/src/prog8/optimizing/ConstantFolding.kt b/compiler/src/prog8/optimizing/ConstantFolding.kt index 134c085bd..ff8412a3f 100644 --- a/compiler/src/prog8/optimizing/ConstantFolding.kt +++ b/compiler/src/prog8/optimizing/ConstantFolding.kt @@ -5,6 +5,7 @@ import prog8.compiler.HeapValues import prog8.compiler.target.c64.FLOAT_MAX_NEGATIVE import prog8.compiler.target.c64.FLOAT_MAX_POSITIVE import prog8.compiler.target.c64.Petscii +import kotlin.math.floor class ConstantFolding(private val namespace: INameScope, private val heap: HeapValues) : IAstProcessor { @@ -382,6 +383,43 @@ class ConstantFolding(private val namespace: INameScope, private val heap: HeapV } return super.process(arrayIndexedExpression) } + + override fun process(assignment: Assignment): IStatement { + super.process(assignment) + val lv = assignment.value as? LiteralValue + if(lv!=null) { + val targetDt = assignment.target.determineDatatype(namespace, heap, assignment) + // see if we can promote/convert a literal value to the required datatype + when(targetDt) { + DataType.WORD -> { + if(lv.type==DataType.BYTE) + assignment.value = LiteralValue(DataType.WORD, wordvalue = lv.asIntegerValue, position=lv.position) + else if(lv.type==DataType.FLOAT) { + val d = lv.floatvalue!! + if(floor(d)==d && d in 0..65535) { + assignment.value = LiteralValue(DataType.WORD, wordvalue=floor(d).toInt(), position=lv.position) + } + } + } + DataType.FLOAT -> { + if(lv.isNumeric) + assignment.value = LiteralValue(DataType.FLOAT, floatvalue= lv.asNumericValue?.toDouble(), position=lv.position) + } + DataType.BYTE -> { + if(lv.type==DataType.WORD && lv.asIntegerValue in 0..255) { + assignment.value = LiteralValue(DataType.BYTE, lv.asIntegerValue?.toShort(), position=lv.position) + } else if(lv.type==DataType.FLOAT) { + val d = lv.floatvalue!! + if(floor(d)==d && d in 0..255) { + assignment.value = LiteralValue(DataType.BYTE, floor(d).toShort(), position=lv.position) + } + } + } + else -> {} + } + } + return assignment + } }