예제 #1
0
def test_timing_both_lt_128():
    """Follow the routine through, checking the timing comments

    This follows the case where both values are less than 128
    I'm just trying to check that the comments are correct!
    """
    RAM[vars.sysArgs:vars.sysArgs + 2] = 3, 5
    # fmt: off
    cycles = 9  # On entry to SYS, 9 cycles have already elapsed
    cycles += Emulator.run_to("SYS_MultiplyBytes_120")
    assert 14 == cycles  # noqa: E702, E241, E272
    cycles += Emulator.run_to("sys_MultiplyBytes.tableEntry")
    assert 29 == cycles  # noqa: E702, E241, E272
    cycles += Emulator.run_to(
        "sys_MultiplyBytes.high-byte-action.store-inverted")
    assert 35 == cycles  # noqa: E702, E241, E272
    cycles += Emulator.run_to("sys_MultiplyBytes.tableExit")
    assert 40 == cycles  # noqa: E702, E241, E272
    cycles += Emulator.run_to("sys_MultiplyBytes#44")
    assert 43 == cycles  # noqa: E702, E241, E272
    cycles += Emulator.run_to("sys_MultiplyBytes.tableEntry")
    assert 51 == cycles  # noqa: E702, E241, E272
    cycles += Emulator.run_to(
        "sys_MultiplyBytes.high-byte-action.restore-and-add")
    assert 57 == cycles  # noqa: E702, E241, E272
    cycles += Emulator.run_to("sys_MultiplyBytes.tableExit")
    assert 64 == cycles  # noqa: E702, E241, E272
    cycles += Emulator.run_to("sys_MultiplyBytes#68")
    assert 67 == cycles  # noqa: E702, E241, E272
    cycles += Emulator.run_to("NEXTY")
    assert 90 == cycles  # noqa: E702, E241, E272
예제 #2
0
def test_read_initial_state():
    # The following are not necessary, but it was very helpful in debugging
    Emulator.run_to(0x2FF, max_instructions=10_000_000)  # Entry of vCPU
    Emulator.run_vcpu_to(0x200)  # Pass through loading sequence
    buffer = bytearray()
    for _ in range(5):
        value = Emulator.read_serial(bits=8)
        buffer.append(value)
    assert buffer == b"READY"
예제 #3
0
def test_timing_one_lt_128():
    """Follow the routine through, checking the timing comments

    This follows the case where one value is less than 128
    """
    RAM[vars.sysArgs:vars.sysArgs + 2] = 3, 160
    # fmt: off
    cycles = 9  # On entry to SYS, 9 cycles have already elapsed
    cycles += Emulator.run_to("sys_MultiplyBytes#68")
    assert 67 == cycles  # noqa: E702, E241, E272
    cycles += Emulator.run_to("sys_MultiplyBytes.oneMsbSetCase")
    assert 85 == cycles  # noqa: E702, E241, E272
    cycles += Emulator.run_to("sys_MultiplyBytes#92")
    assert 91 == cycles  # noqa: E702, E241, E272
예제 #4
0
def test_timing_neither_lt_128():
    """Follow the routine through, checking the timing comments

    This follows the case where neither value is less than 128
    """
    RAM[vars.sysArgs:vars.sysArgs + 2] = 172, 160
    # fmt: off
    cycles = 9  # On entry to SYS, 9 cycles have already elapsed
    cycles += Emulator.run_to("sys_MultiplyBytes#68")
    assert 67 == cycles  # noqa: E702, E241, E272, E221
    cycles += Emulator.run_to("sys_MultiplyBytes#92")
    assert 91 == cycles  # noqa: E702, E241, E272, E221
    cycles += Emulator.run_to("sys_MultiplyBytes#114")
    assert 113 == cycles  # noqa: E702, E241, E272
    cycles += Emulator.run_to("NEXTY")
    assert 118 == cycles  # noqa: E702, E241, E272
예제 #5
0
def test_multiply_bytes(a, b):
    setup_function()
    RAM[vars.sysArgs:vars.sysArgs + 2] = a, b

    cycles = 10  # Because Next is marked as zero
    cycles += Emulator.run_to("NEXT")

    assert cycles <= MAX_CYCLES
    assert cycles == _sign_extend(Emulator.AC) * -2
    assert a * b == Emulator.vAC
예제 #6
0
def test_low_byte_lookup(value):
    """Lookup of the low-byte of a quarter square should work"""
    Emulator.Y = asm.symbol("Quarter-squares lookup table") >> 8
    Emulator.AC = value
    Emulator.next_instruction = "low-byte table entry"

    cycles = Emulator.run_to("low-byte return point")

    assert int(math.floor((value**2) / 4)) & 0xFF == Emulator.AC
    assert vars.cost_of_low_byte_table_entry == cycles
예제 #7
0
def test_high_byte_lookup(value):
    """Lookup of the high-byte of a quarter square should work"""
    RAM[vars.high_byte_action] = asm.symbol("high-byte action.store")
    Emulator.AC = value
    Emulator.Y = asm.symbol("Quarter-squares lookup table") >> 8
    Emulator.next_instruction = "table entry"

    cycles = Emulator.run_to("high-byte action.store")

    assert int(math.floor((value**2) / 4)) >> 8 == Emulator.AC
    assert vars.cost_of_high_byte_table_entry == cycles
예제 #8
0
def test_multiplication_7(a, b):
    """Multiplication of two seven-bit integers should work"""
    RAM[vars.a] = a
    RAM[vars.b] = b
    Emulator.next_instruction = "multiply 7x7"

    cycles = Emulator.run_to("done")

    result = int.from_bytes(RAM[vars.result:vars.result + 2],
                            "little",
                            signed=False)
    assert a * b == result
    assert vars.cost_of_7bit_multiply == cycles
예제 #9
0
def test_multiplication_8(a, b):
    """Multiplication of two eight-bit integers should work"""
    Emulator.reset()
    RAM[vars.a] = a
    RAM[vars.b] = b
    Emulator.next_instruction = "multiply 8x8"
    expected_saving = (vars.no_msb_cost_saving if a < 128 and b < 128 else
                       vars.one_msb_cost_saving if a < 128 or b < 128 else 0)

    cycles = Emulator.run_to("done")

    result = int.from_bytes(RAM[vars.result:vars.result + 2],
                            "little",
                            signed=False)
    assert a * b == result
    assert vars.cost_of_8bit_multiply - expected_saving == cycles
예제 #10
0
def test_subtract_quarter_square(a, b, previous_value):
    """to done should subtract the"""
    RAM[vars.a] = a
    RAM[vars.b] = b
    RAM[vars.result:vars.result + 2] = (previous_value + 1).to_bytes(
        2, "little", signed=False)
    Emulator.Y = asm.symbol("Quarter-squares lookup table") >> 8
    Emulator.next_instruction = asm.symbol(".after-first-lookup") + 2
    expected = (previous_value - math.floor((a - b)**2 / 4)) & 0xFFFF

    cycles = Emulator.run_to(asm.symbol("done"))

    assert expected == int.from_bytes(RAM[vars.result:vars.result + 2],
                                      "little",
                                      signed=False)
    assert asm.symbol("Quarter-squares lookup table") >> 8 == Emulator.Y
    assert vars.cost_of_7bit_multiply - vars.cost_after_first_lookup - 2 == cycles
예제 #11
0
def test_both_byte_lookup(a, b):
    """Lookup of both bytes of a quarter square should work

    The multiplication routine actually adds 1 to the result,
    so storing it, so check for that.
    """
    RAM[vars.a] = a
    RAM[vars.b] = b
    Emulator.next_instruction = "multiply 7x7"
    expected = int(math.floor(((a + b)**2) / 4)) + 1

    cycles = Emulator.run_to(asm.symbol(".after-first-lookup") + 2)

    assert expected == int.from_bytes(RAM[vars.result:vars.result + 2],
                                      "little",
                                      signed=False)
    assert cycles == vars.cost_after_first_lookup + 2
    assert asm.symbol("Quarter-squares lookup table") >> 8 == Emulator.Y