don't apply absorption law on functioncall operands

This commit is contained in:
Irmen de Jong 2024-03-15 01:04:27 +01:00
parent 28eae5a0fd
commit a94cfd34f5
3 changed files with 28 additions and 33 deletions

View File

@ -1,11 +1,8 @@
package prog8.optimizer
import prog8.ast.IStatementContainer
import prog8.ast.Node
import prog8.ast.Program
import prog8.ast.*
import prog8.ast.base.FatalAstException
import prog8.ast.expressions.*
import prog8.ast.maySwapOperandOrder
import prog8.ast.statements.AnonymousScope
import prog8.ast.statements.Assignment
import prog8.ast.statements.IfElse
@ -454,8 +451,13 @@ class ExpressionSimplifier(private val program: Program, private val options: Co
}
private fun applyAbsorptionLaws(expr: BinaryExpression): Expression? {
// NOTE: only when the terms are not function calls!!!
if(expr.left is IFunctionCall || expr.right is IFunctionCall)
return null
val rightB = expr.right as? BinaryExpression
if(rightB!=null) {
if(rightB.left is IFunctionCall || rightB.right is IFunctionCall)
return null
// absorption laws: a or (a and b) --> a, a and (a or b) --> a
if(expr.operator=="or" && rightB.operator=="and") {
if(expr.left isSameAs rightB.left || expr.left isSameAs rightB.right) {
@ -482,6 +484,8 @@ class ExpressionSimplifier(private val program: Program, private val options: Co
}
val leftB = expr.left as? BinaryExpression
if(leftB!=null) {
if(leftB.left is IFunctionCall || leftB.right is IFunctionCall)
return null
// absorption laws: (a and b) or a --> a, (a or b) and a --> a
if(expr.operator=="or" && leftB.operator=="and") {
if(expr.right isSameAs leftB.left || expr.right isSameAs leftB.right) {

View File

@ -1,9 +1,6 @@
TODO
====
fix logical expressione eval:
there's something wrong with the short-circuiting of logical expressions, it sometimes skips terms. Or perhaps bug in the common subexpression optimizer.
...

View File

@ -110,21 +110,15 @@ main {
txt.print("\npreparing 64kb test file")
bool success = false
if diskio.f_open_w("@:benchmark64.dat") {
if diskio.f_write(large, 20000) {
if diskio.f_write(large, 20000) {
if diskio.f_write(large, 20000) {
if diskio.f_write(large, 5536) {
diskio.f_close_w()
success=true
}
}
if not diskio.f_write(large, 20000)
or not diskio.f_write(large, 20000)
or not diskio.f_write(large, 20000)
or not diskio.f_write(large, 5536) {
txt.print("\ni/o error! ")
txt.print(diskio.status())
sys.exit(1)
}
}
}
if not success {
txt.print("\ni/o error! ")
txt.print(diskio.status())
sys.exit(1)
diskio.f_close_w()
}
txt.print("\n\x12diskio.vload()\x92 reading 512kb into vram (8*64kb)")
@ -145,18 +139,18 @@ main {
txt.print(diskio.status())
txt.print("\ndone.\n")
diskio.delete("benchmark0.dat")
diskio.delete("benchmark1.dat")
diskio.delete("benchmark2.dat")
diskio.delete("benchmark3.dat")
diskio.delete("benchmark4.dat")
diskio.delete("benchmark5.dat")
diskio.delete("benchmark6.dat")
diskio.delete("benchmark7.dat")
diskio.delete("benchmark8.dat")
diskio.delete("benchmark9.dat")
diskio.delete("benchmark64.dat")
diskio.delete("benchmark256.dat")
; diskio.delete("benchmark0.dat")
; diskio.delete("benchmark1.dat")
; diskio.delete("benchmark2.dat")
; diskio.delete("benchmark3.dat")
; diskio.delete("benchmark4.dat")
; diskio.delete("benchmark5.dat")
; diskio.delete("benchmark6.dat")
; diskio.delete("benchmark7.dat")
; diskio.delete("benchmark8.dat")
; diskio.delete("benchmark9.dat")
; diskio.delete("benchmark64.dat")
; diskio.delete("benchmark256.dat")
}
sub verify_20k(str filename, uword crc32_low, uword crc32_high) {