mirror of
https://github.com/irmen/prog8.git
synced 2024-11-29 17:50:35 +00:00
fix containment check on memory mapped arrays
This commit is contained in:
parent
3126959576
commit
71261525e8
@ -1,7 +1,6 @@
|
||||
package prog8.codegen.intermediate
|
||||
|
||||
import prog8.code.StRomSub
|
||||
import prog8.code.StStaticVariable
|
||||
import prog8.code.StSub
|
||||
import prog8.code.ast.*
|
||||
import prog8.code.core.AssemblyError
|
||||
@ -106,8 +105,7 @@ internal class ExpressionGen(private val codeGen: IRCodeGen) {
|
||||
|
||||
private fun translate(check: PtContainmentCheck): ExpressionCodeResult {
|
||||
val result = mutableListOf<IRCodeChunkBase>()
|
||||
val iterable = codeGen.symbolTable.lookup(check.iterable.name) as StStaticVariable // TODO FIX/TEST for memory mapped array , replace with check.iterable.type???
|
||||
when(iterable.dt) {
|
||||
when(check.iterable.type) {
|
||||
DataType.STR -> {
|
||||
val elementTr = translateExpression(check.element)
|
||||
addToResult(result, elementTr, elementTr.resultReg, -1)
|
||||
@ -122,7 +120,8 @@ internal class ExpressionGen(private val codeGen: IRCodeGen) {
|
||||
val iterableTr = translateExpression(check.iterable)
|
||||
addToResult(result, iterableTr, iterableTr.resultReg, -1)
|
||||
val lengthReg = codeGen.registers.nextFree()
|
||||
addInstr(result, IRInstruction(Opcode.LOAD, IRDataType.BYTE, reg1=lengthReg, immediate = iterable.length!!), null)
|
||||
val iterableLength = codeGen.symbolTable.getLength(check.iterable.name)
|
||||
addInstr(result, IRInstruction(Opcode.LOAD, IRDataType.BYTE, reg1=lengthReg, immediate = iterableLength!!), null)
|
||||
result += codeGen.makeSyscall(IMSyscall.BYTEARRAY_CONTAINS, listOf(IRDataType.BYTE to elementTr.resultReg, IRDataType.WORD to iterableTr.resultReg, IRDataType.BYTE to lengthReg), IRDataType.BYTE to elementTr.resultReg)
|
||||
return ExpressionCodeResult(result, IRDataType.BYTE, elementTr.resultReg, -1)
|
||||
}
|
||||
@ -132,12 +131,13 @@ internal class ExpressionGen(private val codeGen: IRCodeGen) {
|
||||
val iterableTr = translateExpression(check.iterable)
|
||||
addToResult(result, iterableTr, iterableTr.resultReg, -1)
|
||||
val lengthReg = codeGen.registers.nextFree()
|
||||
addInstr(result, IRInstruction(Opcode.LOAD, IRDataType.BYTE, reg1=lengthReg, immediate = iterable.length!!), null)
|
||||
val iterableLength = codeGen.symbolTable.getLength(check.iterable.name)
|
||||
addInstr(result, IRInstruction(Opcode.LOAD, IRDataType.BYTE, reg1=lengthReg, immediate = iterableLength!!), null)
|
||||
result += codeGen.makeSyscall(IMSyscall.WORDARRAY_CONTAINS, listOf(IRDataType.WORD to elementTr.resultReg, IRDataType.WORD to iterableTr.resultReg, IRDataType.BYTE to lengthReg), IRDataType.BYTE to elementTr.resultReg)
|
||||
return ExpressionCodeResult(result, IRDataType.BYTE, elementTr.resultReg, -1)
|
||||
}
|
||||
DataType.ARRAY_F -> throw AssemblyError("containment check in float-array not supported")
|
||||
else -> throw AssemblyError("weird iterable dt ${iterable.dt} for ${check.iterable.name}")
|
||||
else -> throw AssemblyError("weird iterable dt ${check.iterable.type} for ${check.iterable.name}")
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -1618,7 +1618,7 @@ class IRCodeGen(
|
||||
private fun translate(parameters: List<PtSubroutineParameter>) =
|
||||
parameters.map {
|
||||
val flattenedName = it.definingSub()!!.name + "." + it.name
|
||||
val orig = symbolTable.lookup(flattenedName) as StStaticVariable // TODO FIX/TEST for memory mapped array or other
|
||||
val orig = symbolTable.lookup(flattenedName) as StStaticVariable
|
||||
IRSubroutine.IRParam(flattenedName, orig.dt)
|
||||
}
|
||||
|
||||
|
@ -194,8 +194,10 @@ internal class VariousCleanups(val program: Program, val errors: IErrorReporter,
|
||||
else
|
||||
noModifications
|
||||
}
|
||||
else
|
||||
else if(variable.value is ArrayLiteral) {
|
||||
checkArray((variable.value as ArrayLiteral).value)
|
||||
}
|
||||
else noModifications
|
||||
}
|
||||
|
||||
fun checkString(stringVal: StringLiteral): Iterable<IAstModification> {
|
||||
@ -214,14 +216,14 @@ internal class VariousCleanups(val program: Program, val errors: IErrorReporter,
|
||||
return checkArray(array)
|
||||
}
|
||||
is IdentifierReference -> {
|
||||
val variable = (containment.iterable as IdentifierReference).targetVarDecl(program)!!
|
||||
when(variable.datatype) {
|
||||
val variable = (containment.iterable as IdentifierReference).targetVarDecl(program)
|
||||
when(variable?.datatype) {
|
||||
DataType.STR -> {
|
||||
val stringVal = (variable.value as StringLiteral)
|
||||
return checkString(stringVal)
|
||||
}
|
||||
in ArrayDatatypes -> {
|
||||
return checkArray(variable)
|
||||
return checkArray(variable!!)
|
||||
}
|
||||
else -> {}
|
||||
}
|
||||
|
@ -8,11 +8,14 @@ main {
|
||||
|
||||
&ubyte[5] cells = $4000
|
||||
cells = [1,2,3,4,5]
|
||||
ubyte ub
|
||||
for ub in cells {
|
||||
txt.print_ub(ub)
|
||||
txt.spc()
|
||||
}
|
||||
str name = "irmen"
|
||||
|
||||
ubyte[5] othercells = [11,22,33,44,55]
|
||||
|
||||
txt.print_ub(1 in cells)
|
||||
txt.print_ub(44 in othercells)
|
||||
txt.print_ub('a' in name)
|
||||
txt.print_ub('e' in name)
|
||||
}
|
||||
|
||||
sub command() {
|
||||
|
Loading…
Reference in New Issue
Block a user