mirror of
https://github.com/irmen/prog8.git
synced 2025-01-11 13:29:45 +00:00
vm: more optimal code when array index is constant value
This commit is contained in:
parent
2b7c09e6ee
commit
d78bfcc35c
@ -138,15 +138,20 @@ internal class ExpressionGen(private val codeGen: CodeGen) {
|
||||
val vmDt = codeGen.vmType(arrayIx.type)
|
||||
val code = VmCodeChunk()
|
||||
val idxReg = codeGen.vmRegisters.nextFree()
|
||||
// TODO: optimized code when the index is a constant value
|
||||
code += translateExpression(arrayIx.index, idxReg)
|
||||
if(eltSize>1) {
|
||||
val factorReg = codeGen.vmRegisters.nextFree()
|
||||
code += VmCodeInstruction(Opcode.LOAD, VmDataType.BYTE, reg1=factorReg, value=eltSize)
|
||||
code += VmCodeInstruction(Opcode.MUL, VmDataType.BYTE, reg1=idxReg, reg2=idxReg, reg3=factorReg)
|
||||
}
|
||||
val arrayLocation = codeGen.allocations.get(arrayIx.variable.targetName)
|
||||
code += VmCodeInstruction(Opcode.LOADX, vmDt, reg1=resultRegister, reg2=idxReg, value = arrayLocation)
|
||||
if(arrayIx.index is PtNumber) {
|
||||
// optimized code when index is known - just calculate the memory address here
|
||||
val memOffset = (arrayIx.index as PtNumber).number.toInt() * eltSize
|
||||
code += VmCodeInstruction(Opcode.LOADM, vmDt, reg1=resultRegister, value=arrayLocation+memOffset)
|
||||
} else {
|
||||
code += translateExpression(arrayIx.index, idxReg)
|
||||
if(eltSize>1) {
|
||||
val factorReg = codeGen.vmRegisters.nextFree()
|
||||
code += VmCodeInstruction(Opcode.LOAD, VmDataType.BYTE, reg1=factorReg, value=eltSize)
|
||||
code += VmCodeInstruction(Opcode.MUL, VmDataType.BYTE, reg1=idxReg, reg2=idxReg, reg3=factorReg)
|
||||
}
|
||||
code += VmCodeInstruction(Opcode.LOADX, vmDt, reg1=resultRegister, reg2=idxReg, value = arrayLocation)
|
||||
}
|
||||
return code
|
||||
}
|
||||
|
||||
|
@ -7,13 +7,9 @@
|
||||
main {
|
||||
|
||||
sub start() {
|
||||
ubyte counter
|
||||
uword[] array = [1111,2222,3333,4444,5555]
|
||||
|
||||
repeat 256 {
|
||||
txt.print_ub(counter)
|
||||
txt.spc()
|
||||
counter ++
|
||||
}
|
||||
txt.print_uw(array[3])
|
||||
txt.nl()
|
||||
|
||||
; a "pixelshader":
|
||||
|
@ -588,7 +588,7 @@ class VirtualMachine(val memory: Memory, program: List<Instruction>) {
|
||||
if(right==0.toUByte()) 0xffu
|
||||
else left % right
|
||||
}
|
||||
else -> TODO("operator byte $operator")
|
||||
else -> throw IllegalArgumentException("operator byte $operator")
|
||||
}
|
||||
registers.setUB(reg1, result.toUByte())
|
||||
}
|
||||
@ -608,7 +608,7 @@ class VirtualMachine(val memory: Memory, program: List<Instruction>) {
|
||||
if(right==0.toUShort()) 0xffffu
|
||||
else left % right
|
||||
}
|
||||
else -> TODO("operator word $operator")
|
||||
else -> throw IllegalArgumentException("operator word $operator")
|
||||
}
|
||||
registers.setUW(reg1, result.toUShort())
|
||||
}
|
||||
@ -624,7 +624,7 @@ class VirtualMachine(val memory: Memory, program: List<Instruction>) {
|
||||
private fun InsEXT(i: Instruction) {
|
||||
when(i.type!!){
|
||||
VmDataType.BYTE -> registers.setUW(i.reg1!!, registers.getUB(i.reg1).toUShort())
|
||||
VmDataType.WORD -> TODO("ext.w requires 32 bits registers")
|
||||
VmDataType.WORD -> TODO("ext.w not yet supported, requires 32 bits registers")
|
||||
}
|
||||
pc++
|
||||
}
|
||||
@ -632,7 +632,7 @@ class VirtualMachine(val memory: Memory, program: List<Instruction>) {
|
||||
private fun InsEXTS(i: Instruction) {
|
||||
when(i.type!!){
|
||||
VmDataType.BYTE -> registers.setSW(i.reg1!!, registers.getSB(i.reg1).toShort())
|
||||
VmDataType.WORD -> TODO("ext.w requires 32 bits registers")
|
||||
VmDataType.WORD -> TODO("exts.w not yet supported, requires 32 bits registers")
|
||||
}
|
||||
pc++
|
||||
}
|
||||
@ -716,7 +716,7 @@ class VirtualMachine(val memory: Memory, program: List<Instruction>) {
|
||||
val newValue = value.toUByte()*256u + (value.toInt() ushr 8).toUInt()
|
||||
registers.setUW(i.reg1, newValue.toUShort())
|
||||
}
|
||||
VmDataType.WORD -> TODO("swap.w requires 32-bits registers")
|
||||
VmDataType.WORD -> TODO("swap.w not yet supported, requires 32-bits registers")
|
||||
}
|
||||
pc++
|
||||
}
|
||||
@ -728,7 +728,7 @@ class VirtualMachine(val memory: Memory, program: List<Instruction>) {
|
||||
val lsb = registers.getUB(i.reg3!!)
|
||||
registers.setUW(i.reg1!!, ((msb.toInt() shl 8) or lsb.toInt()).toUShort())
|
||||
}
|
||||
VmDataType.WORD -> TODO("swap.w requires 32-bits registers")
|
||||
VmDataType.WORD -> TODO("concat.w not yet supported, requires 32-bits registers")
|
||||
}
|
||||
pc++
|
||||
}
|
||||
|
Loading…
x
Reference in New Issue
Block a user