mirror of
https://github.com/irmen/prog8.git
synced 2025-01-23 15:30:10 +00:00
added more constfolding
This commit is contained in:
parent
abca618008
commit
3d743a1ba1
@ -212,21 +212,27 @@ class ConstantFoldingOptimizer(private val program: Program) : AstWalker() {
|
||||
}
|
||||
}
|
||||
}
|
||||
else if(expr.operator=="*" && leftBinExpr.operator=="*") {
|
||||
else if(expr.operator=="*") {
|
||||
val c2 = leftBinExpr.right.constValue(program)
|
||||
if(c2!=null) {
|
||||
// (X * C1) * C2 --> X * (C1*C2)
|
||||
// TODO (X * C1) / C2 --> X * (C1/C2)
|
||||
val constants = BinaryExpression(c2, "*", rightconst, c2.position)
|
||||
val newExpr = BinaryExpression(leftBinExpr.left, "*", constants, expr.position)
|
||||
return listOf(IAstModification.ReplaceNode(expr, newExpr, parent))
|
||||
if(leftBinExpr.operator=="*") {
|
||||
// (X * C2) * rightConst --> X * (rightConst*C2)
|
||||
val constants = BinaryExpression(rightconst, "*", c2, c2.position)
|
||||
val newExpr = BinaryExpression(leftBinExpr.left, "*", constants, expr.position)
|
||||
return listOf(IAstModification.ReplaceNode(expr, newExpr, parent))
|
||||
} else if (leftBinExpr.operator=="/") {
|
||||
// (X / C2) * rightConst --> X * (rightConst/C2)
|
||||
val constants = BinaryExpression(rightconst, "/", c2, c2.position)
|
||||
val newExpr = BinaryExpression(leftBinExpr.left, "*", constants, expr.position)
|
||||
return listOf(IAstModification.ReplaceNode(expr, newExpr, parent))
|
||||
}
|
||||
}
|
||||
}
|
||||
else if(expr.operator=="/" && leftBinExpr.operator=="/") {
|
||||
else if(expr.operator=="/") {
|
||||
val c2 = leftBinExpr.right.constValue(program)
|
||||
if(c2!=null) {
|
||||
if(c2!=null && leftBinExpr.operator=="/") {
|
||||
// (X / C1) / C2 --> X / (C1*C2)
|
||||
// TODO (X / C1) * C2 --> X * (C2/C1)
|
||||
// NOTE: do not optimize (X * C1) / C2 --> X * (C1/C2) because this causes precision loss on integers
|
||||
val constants = BinaryExpression(c2, "*", rightconst, c2.position)
|
||||
val newExpr = BinaryExpression(leftBinExpr.left, "/", constants, expr.position)
|
||||
return listOf(IAstModification.ReplaceNode(expr, newExpr, parent))
|
||||
|
@ -167,11 +167,12 @@ class TestOptimization: FunSpec({
|
||||
val source = """
|
||||
main {
|
||||
sub start() {
|
||||
; TODO other variants of this const folding
|
||||
word llw = 300
|
||||
cx16.r0s = 9 * 2 * 10 * llw
|
||||
cx16.r1s = llw * 9 * 2 * 10
|
||||
cx16.r2s = llw / 20 / 3
|
||||
cx16.r2s = llw / 30 / 3
|
||||
cx16.r3s = llw / 2 * 10
|
||||
cx16.r4s = llw * 90 / 5 ; not optimized because of loss of integer division precision
|
||||
}
|
||||
}"""
|
||||
val result = compileText(C64Target, true, source, writeAssembly = false).assertSuccess()
|
||||
@ -184,9 +185,14 @@ class TestOptimization: FunSpec({
|
||||
// cx16.r1s = llw
|
||||
// cx16.r1s *= 180
|
||||
// cx16.r2s = llw
|
||||
// cx16.r2s /= 100
|
||||
// cx16.r2s /= 90
|
||||
// cx16.r3s = llw
|
||||
// cx16.r3s *= 5
|
||||
// cx16.r4s = llw
|
||||
// cx16.r4s *= 90
|
||||
// cx16.r4s /= 5
|
||||
val stmts = result.program.entrypoint.statements
|
||||
stmts.size shouldBe 8
|
||||
stmts.size shouldBe 13
|
||||
|
||||
val mulR0Value = (stmts[3] as Assignment).value
|
||||
val binexpr0 = mulR0Value as BinaryExpression
|
||||
@ -199,7 +205,19 @@ class TestOptimization: FunSpec({
|
||||
val divR2Value = (stmts[7] as Assignment).value
|
||||
val binexpr2 = divR2Value as BinaryExpression
|
||||
binexpr2.operator shouldBe "/"
|
||||
binexpr2.right shouldBe NumericLiteralValue(DataType.UWORD, 60.0, Position.DUMMY)
|
||||
binexpr2.right shouldBe NumericLiteralValue(DataType.UWORD, 90.0, Position.DUMMY)
|
||||
val mulR3Value = (stmts[9] as Assignment).value
|
||||
val binexpr3 = mulR3Value as BinaryExpression
|
||||
binexpr3.operator shouldBe "*"
|
||||
binexpr3.right shouldBe NumericLiteralValue(DataType.UWORD, 5.0, Position.DUMMY)
|
||||
val mulR4Value = (stmts[11] as Assignment).value
|
||||
val binexpr4 = mulR4Value as BinaryExpression
|
||||
binexpr4.operator shouldBe "*"
|
||||
binexpr4.right shouldBe NumericLiteralValue(DataType.UWORD, 90.0, Position.DUMMY)
|
||||
val divR4Value = (stmts[12] as Assignment).value
|
||||
val binexpr4b = divR4Value as BinaryExpression
|
||||
binexpr4b.operator shouldBe "/"
|
||||
binexpr4b.right shouldBe NumericLiteralValue(DataType.UWORD, 5.0, Position.DUMMY)
|
||||
}
|
||||
|
||||
test("constantfolded and silently typecasted for initializervalues") {
|
||||
|
@ -3,7 +3,6 @@ TODO
|
||||
|
||||
For next compiler release (7.5)
|
||||
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
||||
more const-foldings
|
||||
check correctness of inplaceModification_byte_value_to_pointer()
|
||||
...
|
||||
|
||||
|
@ -3,12 +3,11 @@
|
||||
|
||||
main {
|
||||
sub start() {
|
||||
; TODO other variants of this const folding
|
||||
word llw = 300
|
||||
cx16.r0s = 9 * 2 * 10 * llw
|
||||
cx16.r1s = llw * 9 * 2 * 10
|
||||
cx16.r2s = llw * 9 / 4
|
||||
cx16.r3s = llw / 20 / 5
|
||||
cx16.r4s = llw / 20 * 5
|
||||
cx16.r3s = llw / 30 / 3
|
||||
cx16.r4s = llw / 2 * 10
|
||||
cx16.r5s = llw * 90 / 5 ; not optimized because of loss of integer division precision
|
||||
}
|
||||
}
|
||||
|
Loading…
x
Reference in New Issue
Block a user