fix VM sgn() function for floats

This commit is contained in:
Irmen de Jong 2024-01-16 01:23:41 +01:00
parent e0de662f8e
commit 0cfcc5cd29
4 changed files with 29 additions and 33 deletions

View File

@ -260,14 +260,21 @@ internal class BuiltinFuncGen(private val codeGen: IRCodeGen, private val exprGe
private fun funcSgn(call: PtBuiltinFunctionCall): ExpressionCodeResult { private fun funcSgn(call: PtBuiltinFunctionCall): ExpressionCodeResult {
val result = mutableListOf<IRCodeChunkBase>() val result = mutableListOf<IRCodeChunkBase>()
val vmDt = irType(call.type)
val tr = exprGen.translateExpression(call.args.single()) val tr = exprGen.translateExpression(call.args.single())
addToResult(result, tr, tr.resultReg, -1)
val resultReg = codeGen.registers.nextFree() val resultReg = codeGen.registers.nextFree()
result += IRCodeChunk(null, null).also {
it += IRInstruction(Opcode.SGN, vmDt, reg1 = resultReg, reg2 = tr.resultReg) if(tr.dt==IRDataType.FLOAT) {
addToResult(result, tr, -1, tr.resultFpReg)
result += IRCodeChunk(null, null).also {
it += IRInstruction(Opcode.SGN, tr.dt, reg1 = resultReg, fpReg1 = tr.resultFpReg)
}
} else {
addToResult(result, tr, tr.resultReg, -1)
result += IRCodeChunk(null, null).also {
it += IRInstruction(Opcode.SGN, tr.dt, reg1 = resultReg, reg2 = tr.resultReg)
}
} }
return ExpressionCodeResult(result, vmDt, resultReg, -1) return ExpressionCodeResult(result, IRDataType.BYTE, resultReg, -1)
} }
private fun funcSqrt(call: PtBuiltinFunctionCall): ExpressionCodeResult { private fun funcSqrt(call: PtBuiltinFunctionCall): ExpressionCodeResult {

View File

@ -3,7 +3,6 @@
%import string %import string
%import syslib %import syslib
%import math %import math
%import test_stack
%zeropage basicsafe %zeropage basicsafe
main { main {
@ -12,8 +11,6 @@ main {
rotations() rotations()
integers() integers()
floatingpoint() floatingpoint()
test_stack.test()
} }
sub rotations() { sub rotations() {
@ -175,7 +172,7 @@ main {
txt.nl() txt.nl()
&ubyte membyte = $c000 &ubyte membyte = $c000
uword addr = $c000 uword @shared addr = $c000
@(addr) = %10110101 @(addr) = %10110101
txt.print_ubbin(@(addr), true) txt.print_ubbin(@(addr), true)
@ -252,9 +249,6 @@ main {
txt.print_ubbin(@(addr), true) txt.print_ubbin(@(addr), true)
txt.nl() txt.nl()
txt.nl() txt.nl()
test_stack.test()
} }
sub integers() { sub integers() {
@ -263,12 +257,12 @@ main {
uword[] uwarr = [100,200,300,400,0,500,400,300,200,100] uword[] uwarr = [100,200,300,400,0,500,400,300,200,100]
word[] warr = [100,200,300,400,500,0,-400,-300,200,100,-99, -4096] word[] warr = [100,200,300,400,500,0,-400,-300,200,100,-99, -4096]
ubyte zero=0 ubyte @shared zero=0
ubyte ub ubyte @shared ub
ubyte ub2 ubyte @shared ub2
byte bb byte @shared bb
uword uw uword @shared uw
word ww word @shared ww
repeat(20) { repeat(20) {
txt.nl() txt.nl()
@ -421,20 +415,17 @@ main {
reverse(barr) reverse(barr)
reverse(uwarr) reverse(uwarr)
reverse(warr) reverse(warr)
test_stack.test()
} }
sub floatingpoint() { sub floatingpoint() {
ubyte[] barr = [1,2,3,4,5,0,4,3,2,1]
float[] flarr = [1.1, 2.2, 3.3, 0.0, -9.9, 5.5, 4.4] float[] flarr = [1.1, 2.2, 3.3, 0.0, -9.9, 5.5, 4.4]
ubyte zero=0 ubyte @shared zero=0
ubyte ub ubyte @shared ub
byte bb byte @shared bb
uword uw uword @shared uw
float fl float @shared fl
float fzero=0.0 float @shared fzero=0.0
fl = -9.9 fl = -9.9
bb = sgn(fl) bb = sgn(fl)
@ -464,7 +455,5 @@ main {
txt.chrout(',') txt.chrout(',')
} }
txt.nl() txt.nl()
test_stack.test()
} }
} }

View File

@ -156,7 +156,7 @@ divmodr reg1, reg2 - unsigned division reg1/reg2, stori
divmod reg1, value - unsigned division reg1/value, storing division and remainder on value stack (so need to be POPped off) divmod reg1, value - unsigned division reg1/value, storing division and remainder on value stack (so need to be POPped off)
sqrt reg1, reg2 - reg1 is the square root of reg2 (reg2 can be .w or .b, result type in reg1 is always .b) you can also use it with floating point types, fpreg1 and fpreg2 (result is also .f) sqrt reg1, reg2 - reg1 is the square root of reg2 (reg2 can be .w or .b, result type in reg1 is always .b) you can also use it with floating point types, fpreg1 and fpreg2 (result is also .f)
square reg1, reg2 - reg1 is the square of reg2 (reg2 can be .w or .b, result type in reg1 is always .b) you can also use it with floating point types, fpreg1 and fpreg2 (result is also .f) square reg1, reg2 - reg1 is the square of reg2 (reg2 can be .w or .b, result type in reg1 is always .b) you can also use it with floating point types, fpreg1 and fpreg2 (result is also .f)
sgn reg1, reg2 - reg1 is the sign of reg2 (0.b, 1.b or -1.b) sgn reg1, reg2 - reg1.b is the sign of reg2 (or fpreg1, if sgn.f) (0.b, 1.b or -1.b)
cmp reg1, reg2 - set processor status bits C, N, Z according to comparison of reg1 with reg2. (semantics taken from 6502/68000 CMP instruction) cmp reg1, reg2 - set processor status bits C, N, Z according to comparison of reg1 with reg2. (semantics taken from 6502/68000 CMP instruction)
cmpi reg1, value - set processor status bits C, N, Z according to comparison of reg1 with immediate value. (semantics taken from 6502/68000 CMP instruction) cmpi reg1, value - set processor status bits C, N, Z according to comparison of reg1 with immediate value. (semantics taken from 6502/68000 CMP instruction)
@ -634,7 +634,7 @@ val instructionFormats = mutableMapOf(
Opcode.DIVSM to InstructionFormat.from("BW,<r1,<>a | F,<fr1,<>a"), Opcode.DIVSM to InstructionFormat.from("BW,<r1,<>a | F,<fr1,<>a"),
Opcode.SQRT to InstructionFormat.from("BW,>r1,<r2 | F,>fr1,<fr2"), Opcode.SQRT to InstructionFormat.from("BW,>r1,<r2 | F,>fr1,<fr2"),
Opcode.SQUARE to InstructionFormat.from("BW,>r1,<r2 | F,>fr1,<fr2"), Opcode.SQUARE to InstructionFormat.from("BW,>r1,<r2 | F,>fr1,<fr2"),
Opcode.SGN to InstructionFormat.from("BW,>r1,<r2 | F,>fr1,<fr2"), Opcode.SGN to InstructionFormat.from("BW,>r1,<r2 | F,>r1,<fr1"),
Opcode.MODR to InstructionFormat.from("BW,<>r1,<r2"), Opcode.MODR to InstructionFormat.from("BW,<>r1,<r2"),
Opcode.MOD to InstructionFormat.from("BW,<>r1,<i"), Opcode.MOD to InstructionFormat.from("BW,<>r1,<i"),
Opcode.DIVMODR to InstructionFormat.from("BW,<>r1,<r2"), Opcode.DIVMODR to InstructionFormat.from("BW,<>r1,<r2"),

View File

@ -1202,8 +1202,8 @@ class VirtualMachine(irProgram: IRProgram) {
private fun InsSGN(i: IRInstruction) { private fun InsSGN(i: IRInstruction) {
when(i.type!!) { when(i.type!!) {
IRDataType.BYTE -> registers.setSB(i.reg1!!, registers.getSB(i.reg2!!).toInt().sign.toByte()) IRDataType.BYTE -> registers.setSB(i.reg1!!, registers.getSB(i.reg2!!).toInt().sign.toByte())
IRDataType.WORD -> registers.setSW(i.reg1!!, registers.getSW(i.reg2!!).toInt().sign.toShort()) IRDataType.WORD -> registers.setSB(i.reg1!!, registers.getSW(i.reg2!!).toInt().sign.toByte())
IRDataType.FLOAT -> registers.setFloat(i.fpReg1!!, registers.getFloat(i.fpReg2!!).sign) IRDataType.FLOAT -> registers.setSB(i.reg1!!, registers.getFloat(i.fpReg1!!).sign.toInt().toByte())
} }
nextPc() nextPc()
} }