mirror of
https://github.com/irmen/prog8.git
synced 2024-10-17 10:24:55 +00:00
fixed missing non-boolean operand cast in logical expressions
This commit is contained in:
parent
f46e131f18
commit
10ddd5b127
@ -913,7 +913,7 @@ internal class AstChecker(private val program: Program,
|
||||
if(expr.operator !in ComparisonOperators) {
|
||||
if (leftDt == DataType.STR && rightDt == DataType.STR || leftDt in ArrayDatatypes && rightDt in ArrayDatatypes) {
|
||||
// str+str and str*number have already been const evaluated before we get here.
|
||||
errors.err("no computational expressions with strings or arrays are possible", expr.position)
|
||||
errors.err("no computational or logical expressions with strings or arrays are possible", expr.position)
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -82,14 +82,20 @@ internal class BoolRemover(val program: Program) : AstWalker() {
|
||||
"xor" -> "^"
|
||||
else -> "invalid"
|
||||
}
|
||||
return listOf(
|
||||
IAstModification.ReplaceNodeSafe(expr.left, wrapWithBooleanCastIfNeeded(expr.left), expr),
|
||||
IAstModification.ReplaceNodeSafe(expr.right, wrapWithBooleanCastIfNeeded(expr.right), expr),)
|
||||
val mods = mutableListOf<IAstModification>()
|
||||
val newLeft = wrapWithBooleanCastIfNeeded(expr.left, program)
|
||||
val newRight = wrapWithBooleanCastIfNeeded(expr.right, program)
|
||||
if(newLeft!=null)
|
||||
mods += IAstModification.ReplaceNodeSafe(expr.left, newLeft, expr)
|
||||
if(newRight!=null)
|
||||
mods += IAstModification.ReplaceNodeSafe(expr.right, newRight, expr)
|
||||
return mods
|
||||
}
|
||||
return noModifications
|
||||
}
|
||||
}
|
||||
|
||||
private fun wrapWithBooleanCastIfNeeded(expr: Expression): Expression {
|
||||
internal fun wrapWithBooleanCastIfNeeded(expr: Expression, program: Program): Expression? {
|
||||
fun isBoolean(expr: Expression): Boolean {
|
||||
return if(expr.inferType(program) istype DataType.BOOL)
|
||||
true
|
||||
@ -109,8 +115,7 @@ internal class BoolRemover(val program: Program) : AstWalker() {
|
||||
}
|
||||
|
||||
return if(isBoolean(expr))
|
||||
expr
|
||||
null
|
||||
else
|
||||
TypecastExpression(expr, DataType.BOOL, true, expr.position)
|
||||
}
|
||||
}
|
||||
|
@ -46,8 +46,20 @@ class TypecastsAdder(val program: Program, val options: CompilationOptions, val
|
||||
val leftCv = expr.left.constValue(program)
|
||||
val rightCv = expr.right.constValue(program)
|
||||
|
||||
if(leftDt.isKnown && rightDt.isKnown && leftDt!=rightDt) {
|
||||
|
||||
if(leftDt.isKnown && rightDt.isKnown) {
|
||||
if(expr.operator in LogicalOperators && leftDt.isInteger && rightDt.isInteger) {
|
||||
// see if any of the operands needs conversion to bool
|
||||
val modifications = mutableListOf<IAstModification>()
|
||||
val newLeft = wrapWithBooleanCastIfNeeded(expr.left, program)
|
||||
val newRight = wrapWithBooleanCastIfNeeded(expr.right, program)
|
||||
if(newLeft!=null)
|
||||
modifications += IAstModification.ReplaceNode(expr.left, newLeft, expr)
|
||||
if(newRight!=null)
|
||||
modifications += IAstModification.ReplaceNode(expr.right, newRight, expr)
|
||||
if(modifications.isNotEmpty())
|
||||
return modifications
|
||||
}
|
||||
if(leftDt!=rightDt) {
|
||||
// convert bool type to byte if needed
|
||||
if(leftDt istype DataType.BOOL && rightDt.isBytes && !rightDt.istype(DataType.BOOL)) {
|
||||
if(rightCv==null || (rightCv.number!=1.0 && rightCv.number!=0.0))
|
||||
@ -111,6 +123,8 @@ class TypecastsAdder(val program: Program, val options: CompilationOptions, val
|
||||
return modifications
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return noModifications
|
||||
}
|
||||
|
||||
|
@ -3,9 +3,6 @@ TODO
|
||||
|
||||
For next release
|
||||
^^^^^^^^^^^^^^^^
|
||||
- fix compiler bug: tehtriz: blocks fall through the bottom
|
||||
- fix compiler bug: maze: maze runner goes all wacky (both c64 and cx6)
|
||||
|
||||
...
|
||||
|
||||
|
||||
|
@ -3,8 +3,20 @@
|
||||
|
||||
main {
|
||||
sub start() {
|
||||
bool bb2=true
|
||||
bool @shared bb = bb2 and true
|
||||
txt.print_ub(bb)
|
||||
ubyte value1 = %1110
|
||||
ubyte value2 = %1111
|
||||
|
||||
bool[2] @shared barr = [true, false]
|
||||
|
||||
; if value1 and value2 ; TODO value1 isn't converted to bool in 6502 preprocess
|
||||
; txt.print("ok")
|
||||
; else
|
||||
; txt.print("fail!")
|
||||
; txt.nl()
|
||||
|
||||
if value1 and value2!=255 ; TODO value1 isn't converted to bool in 6502 preprocess
|
||||
txt.print("ok")
|
||||
else
|
||||
txt.print("fail!")
|
||||
}
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user