mirror of
https://github.com/KarolS/millfork.git
synced 2025-01-06 09:33:22 +00:00
Z80: The >>>> operator
This commit is contained in:
parent
a39064cf76
commit
85243c96a7
@ -322,7 +322,7 @@ object Z80ExpressionCompiler extends AbstractExpressionCompiler[ZLine] {
|
||||
}
|
||||
case ">>>>" =>
|
||||
val (l, r, 2) = assertArithmeticBinary(ctx, params)
|
||||
???
|
||||
targetifyA(target, compileToHL(ctx, l) ++ Z80Shifting.compileNonetShiftRight(ctx, r), isSigned = false)
|
||||
case "<<" =>
|
||||
val (l, r, size) = assertArithmeticBinary(ctx, params)
|
||||
size match {
|
||||
|
@ -4,6 +4,7 @@ import millfork.CompilationFlag
|
||||
import millfork.assembly.z80.{NoRegisters, ZLine, ZOpcode}
|
||||
import millfork.compiler.CompilationContext
|
||||
import millfork.env.NumericConstant
|
||||
import millfork.error.ErrorReporting
|
||||
import millfork.node.{Expression, LhsExpression, ZRegister}
|
||||
|
||||
import scala.collection.GenTraversableOnce
|
||||
@ -185,4 +186,28 @@ object Z80Shifting {
|
||||
}
|
||||
}
|
||||
|
||||
def compileNonetShiftRight(ctx: CompilationContext, rhs: Expression): List[ZLine] = {
|
||||
import ZOpcode._
|
||||
import ZRegister._
|
||||
ctx.env.eval(rhs) match {
|
||||
case Some(NumericConstant(0, _)) =>
|
||||
List(ZLine.ld8(A, L))
|
||||
case Some(NumericConstant(n, _)) if n < 0 =>
|
||||
ErrorReporting.error("Negative shift amount", rhs.position) // TODO
|
||||
Nil
|
||||
case Some(NumericConstant(n, _)) if n >= 9 =>
|
||||
List(ZLine.ldImm8(A, 0))
|
||||
case Some(NumericConstant(1, _)) =>
|
||||
List(ZLine.register(SRL, H), ZLine.ld8(A, L), ZLine.register(RR, A))
|
||||
case Some(NumericConstant(2, _)) =>
|
||||
List(ZLine.register(SRL, H), ZLine.ld8(A, L), ZLine.register(RR, A), ZLine.register(SRL, A))
|
||||
case Some(NumericConstant(n, _)) =>
|
||||
List(ZLine.register(SRL, H), ZLine.ld8(A, L)) ++ (List.fill(n.toInt)(ZLine.register(RR, A)) :+ ZLine.imm8(AND, 0x1ff >> n))
|
||||
|
||||
case _ =>
|
||||
ErrorReporting.error("Non-constant shift amount", rhs.position) // TODO
|
||||
Nil
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
@ -140,6 +140,9 @@ class Z80Assembler(program: Program,
|
||||
val o = oneRegister(op)
|
||||
writeByte(bank, index, o.opcode + internalRegisterIndex(reg) * o.multiplier)
|
||||
index + 1
|
||||
case ZLine(op@(RR|RRC|RL|RLC), OneRegister(A), _, _) =>
|
||||
writeByte(bank, index, cbOneRegister(op).opcode + 7)
|
||||
index + 1
|
||||
case ZLine(op, OneRegister(reg), _, _) if cbOneRegister.contains(op) =>
|
||||
val o = cbOneRegister(op)
|
||||
writeByte(bank, index, 0xcb)
|
||||
|
@ -1,7 +1,7 @@
|
||||
package millfork.test
|
||||
|
||||
import millfork.Cpu
|
||||
import millfork.test.emu.{EmuBenchmarkRun, EmuCrossPlatformBenchmarkRun, EmuUnoptimizedRun}
|
||||
import millfork.test.emu.{EmuBenchmarkRun, EmuCrossPlatformBenchmarkRun, EmuUnoptimizedCrossPlatformRun}
|
||||
import org.scalatest.{FunSuite, Matchers}
|
||||
|
||||
/**
|
||||
@ -10,22 +10,23 @@ import org.scalatest.{FunSuite, Matchers}
|
||||
class NonetSuite extends FunSuite with Matchers {
|
||||
|
||||
test("Nonet operations") {
|
||||
val m = EmuUnoptimizedRun(
|
||||
EmuUnoptimizedCrossPlatformRun(Cpu.Mos, Cpu.Z80)(
|
||||
"""
|
||||
| array output [3] @$c000
|
||||
| array input = [5,6,7]
|
||||
| array output [5] @$c000
|
||||
| void main () {
|
||||
| word a
|
||||
| a = $110
|
||||
| output[1] = a >>>> 1
|
||||
| output[2] = a >>>> 2
|
||||
| output[3] = a >>>> 3
|
||||
| output[4] = a >>>> 4
|
||||
| }
|
||||
| void copyEntry(byte index) {
|
||||
| output[index] = input[index]
|
||||
| }
|
||||
""".stripMargin)
|
||||
""".stripMargin) { m =>
|
||||
m.readByte(0xc001) should equal(0x88)
|
||||
m.readByte(0xc002) should equal(0x44)
|
||||
m.readByte(0xc003) should equal(0x22)
|
||||
m.readByte(0xc004) should equal(0x11)
|
||||
}
|
||||
}
|
||||
|
||||
test("Nonet left shift") {
|
||||
|
Loading…
Reference in New Issue
Block a user