mirror of
https://github.com/irmen/prog8.git
synced 2026-03-15 18:16:28 +00:00
fix invalid augmented assignment optimization, and a call to pop() that crashed a symbol prefix test because the call wasn't defined as a builtin
This commit is contained in:
@@ -946,21 +946,25 @@ _after:
|
||||
// consolidates simple assignment followed by augmented assignment into a single combined assignment.
|
||||
// a = simplevalue | a += expression --> a = simplevalue + expression (for all augmented operators)
|
||||
// NOTE: this is NOT SAFE to do when dealing with pointer arithmetic because the semantics of the combined expression is different!
|
||||
// NOTE: this is also NOT SAFE when the augmented assignment's RHS references the target variable (e.g., a = b; a *= a)
|
||||
if(!assignment.isAugmentable && assignment.value.isSimple) {
|
||||
val next = assignment.nextSibling() as? Assignment
|
||||
if(next?.isAugmentable==true && next.value is BinaryExpression && next.target.isSameAs(assignment.target, program)) {
|
||||
val combined = next.value as BinaryExpression
|
||||
if(combined.left isSameAs assignment.target) {
|
||||
if(!assignment.target.inferType(program).isPointer && (assignment.value.inferType(program).isPointer || combined.right.inferType(program).isPointer)) {
|
||||
// avoid pointer arithmetic: a = (simplevalue as uword) + expression
|
||||
combined.left = TypecastExpression(assignment.value, DataType.UWORD, true, combined.left.position)
|
||||
} else {
|
||||
// no pointer arithmetic done, just transform it into a = simplevalue + expression
|
||||
combined.left = assignment.value
|
||||
// Check if RHS also references the target variable - if so, can't optimize
|
||||
if(!(combined.right isSameAs assignment.target)) {
|
||||
if(!assignment.target.inferType(program).isPointer && (assignment.value.inferType(program).isPointer || combined.right.inferType(program).isPointer)) {
|
||||
// avoid pointer arithmetic: a = (simplevalue as uword) + expression
|
||||
combined.left = TypecastExpression(assignment.value, DataType.UWORD, true, combined.left.position)
|
||||
} else {
|
||||
// no pointer arithmetic done, just transform it into a = simplevalue + expression
|
||||
combined.left = assignment.value
|
||||
}
|
||||
assignment.value = combined
|
||||
combined.linkParents(assignment)
|
||||
return listOf(IAstModification.Remove(next, parent as IStatementContainer))
|
||||
}
|
||||
assignment.value = combined
|
||||
combined.linkParents(assignment)
|
||||
return listOf(IAstModification.Remove(next, parent as IStatementContainer))
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -50,7 +50,7 @@ internal fun makePushPopFunctionCalls(value: PtExpression): Pair<PtFunctionCall,
|
||||
val popCall = if(popTypecast!=null) {
|
||||
PtTypeCast(popTypecast, true, value.position).also {
|
||||
val returnDt = if(pushWord) DataType.UWORD else if(pushLong) DataType.LONG else if(pushFloat) DataType.FLOAT else DataType.UBYTE
|
||||
it.add(PtFunctionCall(popFunc, false, false, arrayOf(returnDt), value.position))
|
||||
it.add(PtFunctionCall(popFunc, true, false, arrayOf(returnDt), value.position))
|
||||
}
|
||||
} else
|
||||
PtFunctionCall(popFunc, true, false, arrayOf(value.type), value.position)
|
||||
|
||||
@@ -1,9 +1,6 @@
|
||||
TODO
|
||||
====
|
||||
|
||||
BUG in unzip: lookup error p8s_pop [unzip.p8: line 262 col 16-24]
|
||||
|
||||
|
||||
Known bugs:
|
||||
- fix chained aliasing errors see test "chained aliasing"
|
||||
- fix crash in ir loader/vm for deeply nested symbol reference, see test "deeply scoped variable references"
|
||||
|
||||
@@ -6,9 +6,16 @@ main {
|
||||
sub start() {
|
||||
long @shared z1, z2
|
||||
z1=1111
|
||||
|
||||
z2 = z1*z1
|
||||
z2=z1
|
||||
z2*=z2
|
||||
txt.print_l(z2)
|
||||
txt.nl()
|
||||
|
||||
z1=-1111
|
||||
z2=z1
|
||||
z2*=z2
|
||||
txt.print_l(z2)
|
||||
txt.nl()
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user