mirror of
https://github.com/irmen/prog8.git
synced 2025-01-10 20:30:23 +00:00
fix const value of AddressOf for certain types
This commit is contained in:
parent
38dc7fb7bd
commit
f27e3478b9
@ -20,6 +20,11 @@ class ConstantFoldingOptimizer(private val program: Program, private val errors:
|
||||
|
||||
private val evaluator = ConstExprEvaluator()
|
||||
|
||||
override fun after(addressOf: AddressOf, parent: Node): Iterable<IAstModification> {
|
||||
val constAddr = addressOf.constValue(program) ?: return noModifications
|
||||
return listOf(IAstModification.ReplaceNode(addressOf, constAddr, parent))
|
||||
}
|
||||
|
||||
override fun before(memread: DirectMemoryRead, parent: Node): Iterable<IAstModification> {
|
||||
// @( &thing ) --> thing (but only if thing is a byte type!)
|
||||
val addrOf = memread.addressExpression as? AddressOf
|
||||
@ -432,6 +437,11 @@ class ConstantFoldingOptimizer(private val program: Program, private val errors:
|
||||
return noModifications
|
||||
}
|
||||
|
||||
override fun after(typecast: TypecastExpression, parent: Node): Iterable<IAstModification> {
|
||||
val constValue = typecast.constValue(program) ?: return noModifications
|
||||
return listOf(IAstModification.ReplaceNode(typecast, constValue, parent))
|
||||
}
|
||||
|
||||
private class ShuffleOperands(val expr: BinaryExpression,
|
||||
val exprOperator: String?,
|
||||
val subExpr: BinaryExpression,
|
||||
|
@ -43,6 +43,10 @@ internal class VariousCleanups(val program: Program, val errors: IErrorReporter,
|
||||
}
|
||||
|
||||
override fun after(typecast: TypecastExpression, parent: Node): Iterable<IAstModification> {
|
||||
val constValue = typecast.constValue(program)
|
||||
if(constValue!=null)
|
||||
return listOf(IAstModification.ReplaceNode(typecast, constValue, parent))
|
||||
|
||||
if(typecast.expression is NumericLiteral) {
|
||||
val value = (typecast.expression as NumericLiteral).cast(typecast.type)
|
||||
if(value.isValid)
|
||||
|
@ -271,4 +271,27 @@ main {
|
||||
(assignv2 as NumericLiteral).number shouldBe 0.0
|
||||
}
|
||||
|
||||
test("const address-of memory mapped arrays") {
|
||||
val src="""
|
||||
main {
|
||||
sub start() {
|
||||
&uword[30] wb = ${'$'}2000
|
||||
&uword[100] array1 = ${'$'}9e00
|
||||
&uword[30] array2 = &array1[len(wb)]
|
||||
|
||||
cx16.r0 = &array1 ; ${'$'}9e00
|
||||
cx16.r1 = &array1[len(wb)] ; ${'$'}9e3c
|
||||
cx16.r2 = &array2 ; ${'$'}9e3c
|
||||
}
|
||||
}"""
|
||||
val result = compileText(Cx16Target(), false, src, writeAssembly = false)!!
|
||||
val st = result.compilerAst.entrypoint.statements
|
||||
st.size shouldBe 6
|
||||
((st[0] as VarDecl).value as NumericLiteral).number shouldBe 0x2000
|
||||
((st[1] as VarDecl).value as NumericLiteral).number shouldBe 0x9e00
|
||||
((st[2] as VarDecl).value as NumericLiteral).number shouldBe 0x9e00+2*30
|
||||
((st[3] as Assignment).value as NumericLiteral).number shouldBe 0x9e00
|
||||
((st[4] as Assignment).value as NumericLiteral).number shouldBe 0x9e00+2*30
|
||||
((st[5] as Assignment).value as NumericLiteral).number shouldBe 0x9e00+2*30
|
||||
}
|
||||
})
|
||||
|
@ -444,7 +444,11 @@ class AstToSourceTextConverter(val output: (text: String) -> Unit, val program:
|
||||
override fun visit(addressOf: AddressOf) {
|
||||
output("&")
|
||||
addressOf.identifier.accept(this)
|
||||
addressOf.arrayIndex?.accept(this)
|
||||
if(addressOf.arrayIndex!=null) {
|
||||
output("[")
|
||||
addressOf.arrayIndex?.accept(this)
|
||||
output("]")
|
||||
}
|
||||
}
|
||||
|
||||
override fun visit(inlineAssembly: InlineAssembly) {
|
||||
|
@ -408,9 +408,17 @@ data class AddressOf(var identifier: IdentifierReference, var arrayIndex: ArrayI
|
||||
override fun constValue(program: Program): NumericLiteral? {
|
||||
val target = this.identifier.targetStatement(program) as? VarDecl
|
||||
if(target?.type==VarDeclType.MEMORY) {
|
||||
val address = target.value?.constValue(program)
|
||||
if(address!=null)
|
||||
return NumericLiteral(DataType.UWORD, address.number, position)
|
||||
var address = target.value?.constValue(program)?.number
|
||||
if(address!=null) {
|
||||
if(arrayIndex!=null) {
|
||||
val index = arrayIndex?.constIndex()
|
||||
if (index != null)
|
||||
address += program.memsizer.memorySize(target.datatype, index)
|
||||
else
|
||||
return null
|
||||
}
|
||||
return NumericLiteral(DataType.UWORD, address, position)
|
||||
}
|
||||
}
|
||||
return null
|
||||
}
|
||||
|
@ -3,6 +3,8 @@ TODO
|
||||
|
||||
IR: use SCC and SCS, to optimize some code that sets 0/1 based on carry flag status
|
||||
|
||||
try to get rid of ArrayIndex class
|
||||
|
||||
...
|
||||
|
||||
|
||||
|
@ -1,17 +1,16 @@
|
||||
%import floats
|
||||
%import textio
|
||||
%zeropage basicsafe
|
||||
%option no_sysinit
|
||||
|
||||
mpb {
|
||||
const uword HIGH_MEMORY_START = $A000
|
||||
}
|
||||
|
||||
main {
|
||||
&uword[20] wa = mpb.HIGH_MEMORY_START
|
||||
; &uword[20] wa = $A000
|
||||
|
||||
sub start() {
|
||||
wa[0] = "smile"
|
||||
txt.print(wa[0])
|
||||
&uword[30] wb = $2000
|
||||
&uword[100] array1 = $9e00
|
||||
&uword[30] array2 = &array1[len(wb)]
|
||||
|
||||
txt.print_uwhex(&array1, true) ; $9e00
|
||||
txt.print_uwhex(&array1[len(wb)], true) ; $9e3c
|
||||
txt.print_uwhex(&array2, true) ; $9e3c
|
||||
}
|
||||
}
|
||||
|
Loading…
x
Reference in New Issue
Block a user