ir: fix more register typing errors

This commit is contained in:
Irmen de Jong 2024-12-27 21:26:30 +01:00
parent 427451a23f
commit f42e12bc13
5 changed files with 36 additions and 91 deletions

View File

@ -259,17 +259,18 @@ internal class ExpressionGen(private val codeGen: IRCodeGen) {
val endLabel = codeGen.createLabelName()
val elementTr = translateExpression(check.needle)
addToResult(result, elementTr, elementTr.resultReg, -1)
val boolResultRegister = if(elementDt.isByteOrBool) elementTr.resultReg else codeGen.registers.nextFree()
result += IRCodeChunk(null, null).also {
for(value in haystack){
it += IRInstruction(Opcode.CMPI, irType(elementDt), elementTr.resultReg, immediate = value)
it += IRInstruction(Opcode.BSTEQ, labelSymbol = gottemLabel)
}
it += IRInstruction(Opcode.LOAD, IRDataType.BYTE, elementTr.resultReg, immediate = 0)
it += IRInstruction(Opcode.LOAD, IRDataType.BYTE, boolResultRegister, immediate = 0)
it += IRInstruction(Opcode.JUMP, labelSymbol = endLabel)
}
addInstr(result, IRInstruction(Opcode.LOAD, IRDataType.BYTE, elementTr.resultReg, immediate = 1), gottemLabel)
addInstr(result, IRInstruction(Opcode.LOAD, IRDataType.BYTE, boolResultRegister, immediate = 1), gottemLabel)
result += IRCodeChunk(endLabel, null)
return ExpressionCodeResult(result, IRDataType.BYTE, elementTr.resultReg, -1)
return ExpressionCodeResult(result, IRDataType.BYTE, boolResultRegister, -1)
}
elementDt.isFloat -> throw AssemblyError("containmentchecks for floats should always be done on an array variable with subroutine")
else -> throw AssemblyError("weird dt $elementDt")
@ -448,8 +449,12 @@ internal class ExpressionGen(private val codeGen: IRCodeGen) {
}
BaseDataType.UBYTE -> {
when(valueDt.base) {
BaseDataType.BOOL, BaseDataType.BYTE, BaseDataType.UWORD, BaseDataType.WORD -> {
actualResultReg2 = tr.resultReg // just keep the LSB as it is
BaseDataType.BOOL, BaseDataType.BYTE -> {
actualResultReg2 = tr.resultReg
}
BaseDataType.UWORD, BaseDataType.WORD -> {
actualResultReg2 = codeGen.registers.nextFree()
addInstr(result, IRInstruction(Opcode.LSIG, IRDataType.BYTE, reg1=actualResultReg2, reg2=tr.resultReg, immediate = 0), null)
}
BaseDataType.FLOAT -> {
actualResultReg2 = codeGen.registers.nextFree()
@ -460,8 +465,12 @@ internal class ExpressionGen(private val codeGen: IRCodeGen) {
}
BaseDataType.BYTE -> {
when(valueDt.base) {
BaseDataType.BOOL, BaseDataType.UBYTE, BaseDataType.UWORD, BaseDataType.WORD -> {
actualResultReg2 = tr.resultReg // just keep the LSB as it is
BaseDataType.BOOL, BaseDataType.UBYTE -> {
actualResultReg2 = tr.resultReg
}
BaseDataType.UWORD, BaseDataType.WORD -> {
actualResultReg2 = codeGen.registers.nextFree()
addInstr(result, IRInstruction(Opcode.LSIG, IRDataType.BYTE, reg1=actualResultReg2, reg2=tr.resultReg, immediate = 0), null)
}
BaseDataType.FLOAT -> {
actualResultReg2 = codeGen.registers.nextFree()

View File

@ -60,6 +60,11 @@ IR/VM
- add BZ and BNZ instructions? To replace CMPI #0 + Branch?
- fix TODO("IR rol/ror on split words array")
- fix "<< in array" / ">> in array"
- sometimes source lines get missing in the output p8ir, for example the first assignment is gone in:
sub start() {
cx16.r0L = cx16.r1 as ubyte
cx16.r0sL = cx16.r1s as byte
}
- implement missing operators in AssignmentGen (array shifts etc)
- fix call() return value handling
- try to get rid of LSIG opcode again (but this will introduce byte reads from word typed registers...)

View File

@ -1,90 +1,14 @@
%import textio
%import floats
%zeropage basicsafe
%option no_sysinit
main {
ubyte @shared width
sub start() {
bool derp
float @shared f1,f2
txt.nl()
cx16.r0 = $aaaa
cx16.r1 = $2222
f1 = 10000
cx16.r0=10000
; true false false
; true true false
; times 2.
txt.print_bool(f1 > 8000)
txt.spc()
txt.print_bool(f1 > 10000)
txt.spc()
txt.print_bool(f1 > 20000)
txt.nl()
txt.print_bool(f1 >= 8000)
txt.spc()
txt.print_bool(f1 >= 10000)
txt.spc()
txt.print_bool(f1 >= 20000)
txt.nl()
txt.print_bool(cx16.r0 > 8000)
txt.spc()
txt.print_bool(cx16.r0 > 10000)
txt.spc()
txt.print_bool(cx16.r0 > 20000)
txt.nl()
txt.print_bool(cx16.r0 >= 8000)
txt.spc()
txt.print_bool(cx16.r0 >= 10000)
txt.spc()
txt.print_bool(cx16.r0 >= 20000)
txt.nl()
cx16.r0L=0
derp=true
if cx16.r0L==0 and derp
txt.print("fl is 0\n")
else
txt.print("fl is not 0\n")
if cx16.r0L!=0 and derp
txt.print("fl is not 0\n")
else
txt.print("fl is 0\n")
cx16.r0L = 1
if cx16.r0L==0 and derp
txt.print("fl is 0\n")
else
txt.print("fl is not 0\n")
if cx16.r0L!=0 and derp
txt.print("fl is not 0\n")
else
txt.print("fl is 0\n")
cx16.r0L=99
derp=true
if cx16.r0L==99 and derp
txt.print("fl is 99\n")
else
txt.print("fl is not 99\n")
if cx16.r0L!=99 and derp
txt.print("fl is not 99\n")
else
txt.print("fl is 99\n")
cx16.r0L = 122
if cx16.r0L==99 and derp
txt.print("fl is 99\n")
else
txt.print("fl is not 99\n")
if cx16.r0L!=99 and derp
txt.print("fl is not 99\n")
else
txt.print("fl is 99\n")
if width==22 or width==33 {
cx16.r1++
}
}
}

View File

@ -143,7 +143,7 @@ class IRFileWriter(private val irProgram: IRProgram, outfileOverride: Path?) {
regs.append(" r$regnum -> $types")
if (types.size > 1) {
regs.append(" !!!! more than one type !!!!\n")
println("IR: Detected multi-type register usage: $regnum->$types in ${chunk.label} at ${chunk.sourceLinesPositions.firstOrNull()}")
println("IR: Detected multi-type register usage: $regnum->$types in ${chunk.label} at perhaps ${chunk.sourceLinesPositions.firstOrNull()}")
}
else
regs.append("\n")

View File

@ -976,6 +976,13 @@ data class IRInstruction(
}
private fun determineReg1Type(): IRDataType? {
if(type==IRDataType.FLOAT) {
// some float instructions have an integer register as well.
if(opcode in arrayOf(Opcode.FFROMUB, Opcode.FFROMSB, Opcode.FTOUB, Opcode.FTOSB, Opcode.FCOMP))
return IRDataType.BYTE
else
return IRDataType.WORD
}
if(opcode==Opcode.JUMPI || opcode==Opcode.CALLI || opcode==Opcode.STOREZI)
return IRDataType.WORD
if(opcode==Opcode.EXT || opcode==Opcode.EXTS)
@ -990,7 +997,7 @@ data class IRInstruction(
IRDataType.WORD -> TODO("concat.w from long type")
else -> null
}
if(opcode==Opcode.ASRNM || opcode==Opcode.LSRNM || opcode==Opcode.LSLNM)
if(opcode==Opcode.ASRNM || opcode==Opcode.LSRNM || opcode==Opcode.LSLNM || opcode==Opcode.SQRT)
return IRDataType.BYTE
return this.type
}