optimize multiplication expr

This commit is contained in:
Irmen de Jong 2023-05-08 01:03:54 +02:00
parent ab02e8a546
commit 6db715d879
3 changed files with 140 additions and 28 deletions

View File

@ -686,6 +686,120 @@ internal class AssignmentAsmGen(private val program: PtProgram,
}
}
}
else if(expr.operator=="*") {
val value = expr.right.asConstInteger()
if(value==null) {
when(expr.type) {
in ByteDatatypes -> {
assignExpressionToRegister(expr.left, RegisterOrPair.A, expr.type in SignedDatatypes)
asmgen.out(" pha")
assignExpressionToRegister(expr.right, RegisterOrPair.Y, expr.type in SignedDatatypes)
asmgen.out(" pla | jsr math.multiply_bytes")
assignRegisterByte(assign.target, CpuRegister.A, false)
return true
}
in WordDatatypes -> {
assignExpressionToVariable(expr.left, "P8ZP_SCRATCH_W1", expr.type)
assignExpressionToRegister(expr.right, RegisterOrPair.AY, expr.type in SignedDatatypes)
asmgen.out("""
jsr math.multiply_words
lda math.multiply_words.result
ldy math.multiply_words.result+1""")
assignRegisterpairWord(assign.target, RegisterOrPair.AY)
return true
}
else -> return false
}
} else {
when (expr.type) {
in ByteDatatypes -> {
assignExpressionToRegister(expr.left, RegisterOrPair.A, expr.type in SignedDatatypes)
if (value in asmgen.optimizedByteMultiplications)
asmgen.out(" jsr math.mul_byte_${value}")
else
asmgen.out(" ldy #$value | jsr math.multiply_bytes")
assignRegisterByte(assign.target, CpuRegister.A, false)
return true
}
in WordDatatypes -> {
assignExpressionToRegister(expr.left, RegisterOrPair.AY, expr.type in SignedDatatypes)
if (value in asmgen.optimizedWordMultiplications)
asmgen.out(" jsr math.mul_word_${value}")
else
asmgen.out("""
sta P8ZP_SCRATCH_W1
sty P8ZP_SCRATCH_W1+1
lda #<$value
ldy #>$value
jsr math.multiply_words
lda math.multiply_words.result
ldy math.multiply_words.result+1""")
assignRegisterpairWord(assign.target, RegisterOrPair.AY)
return true
}
else -> return false
}
}
}
else if(expr.operator=="/") {
when(expr.type) {
DataType.UBYTE -> {
assignExpressionToRegister(expr.left, RegisterOrPair.A, false)
asmgen.out(" pha")
assignExpressionToRegister(expr.right, RegisterOrPair.Y, false)
asmgen.out(" pla | jsr math.divmod_ub_asm")
assignRegisterByte(assign.target, CpuRegister.Y, false)
return true
}
DataType.BYTE -> {
assignExpressionToRegister(expr.left, RegisterOrPair.A, true)
asmgen.out(" pha")
assignExpressionToRegister(expr.right, RegisterOrPair.Y, true)
asmgen.out(" pla | jsr math.divmod_b_asm")
assignRegisterByte(assign.target, CpuRegister.Y, true)
return true
}
DataType.UWORD -> {
assignExpressionToVariable(expr.left, "P8ZP_SCRATCH_W1", DataType.UWORD)
assignExpressionToRegister(expr.right, RegisterOrPair.AY, false)
asmgen.out(" jsr math.divmod_uw_asm")
assignRegisterpairWord(assign.target, RegisterOrPair.AY)
return true
}
DataType.WORD -> {
assignExpressionToVariable(expr.left, "P8ZP_SCRATCH_W1", DataType.WORD)
assignExpressionToRegister(expr.right, RegisterOrPair.AY, true)
asmgen.out(" jsr math.divmod_w_asm")
assignRegisterpairWord(assign.target, RegisterOrPair.AY)
return true
}
else -> return false
}
}
else if(expr.operator=="%") {
when(expr.type) {
DataType.UBYTE -> {
assignExpressionToRegister(expr.left, RegisterOrPair.A, false)
asmgen.out(" pha")
assignExpressionToRegister(expr.right, RegisterOrPair.Y, false)
asmgen.out(" pla | jsr math.divmod_ub_asm")
if(assign.target.register==RegisterOrPair.A)
asmgen.out(" cmp #0") // fix the status register
else
assignRegisterByte(assign.target, CpuRegister.A, false)
return true
}
DataType.UWORD -> {
assignExpressionToVariable(expr.left, "P8ZP_SCRATCH_W1", DataType.UWORD)
assignExpressionToRegister(expr.right, RegisterOrPair.AY, false)
asmgen.out(" jsr math.divmod_uw_asm")
assignVariableWord(assign.target, "P8ZP_SCRATCH_W2")
return true
}
else -> return false
}
}
return false
}

View File

@ -3,7 +3,7 @@ TODO
For next minor release
^^^^^^^^^^^^^^^^^^^^^^
- find bcc/bcs + lda branches that could be a rol? (see "TODO optimize Carry expr with rol")
- fix crash: uword remainder = seconds_uword % $0003 ==0
- try to optimize newexpr a bit more
...

View File

@ -2,34 +2,32 @@
%zeropage basicsafe
main {
uword vv = 60
sub print_time(uword seconds) {
ubyte remainder = seconds % $0003 ==0
txt.print_uw(remainder)
txt.nl()
}
sub print_time2(ubyte seconds) {
ubyte remainder = seconds % 3 ==0
txt.print_uw(remainder)
txt.nl()
}
sub start() {
ubyte[10] envelope_attacks = 99
ubyte @shared xx = 4
ubyte yy
; 110
xx = 4
yy = 10
xx = xx <= yy
if xx
txt.chrout('1')
else
txt.chrout('0')
xx = 4
yy = 4
xx = xx <= yy
if xx
txt.chrout('1')
else
txt.chrout('0')
xx = 4
yy = 2
xx = xx <= yy
if xx
txt.chrout('1')
else
txt.chrout('0')
print_time(9870)
print_time(9871)
print_time(9872)
print_time(9873)
txt.nl()
print_time2(50)
print_time2(51)
print_time2(52)
print_time2(53)
}
}