"""Android wire compatibility and complete host-side flashing transactions.""" from dataclasses import replace from types import SimpleNamespace import struct import zlib import pytest from protocan import tms_firmware as tms from protocan.can_boot import CanBootTarget, CanBootTransfer from protocan.protocan import ProtoCanId from protocan.transport import build_frame def reply(command, payload=b"", tail=2): return tms.packet(10, command, payload) + bytes(tail) def test_android_packet_layout_and_crc(): assert tms.crc16_modbus(b"123456789") == 0x4B37 assert tms.init_load(10, 0xA0000, 0x1234)[:10] == bytes.fromhex("0a3a00000a0034120000") assert tms.load_data(10, b"\1\2\3\4")[:6] == bytes.fromhex("0a3301020304") assert tms.tflash(10, 0xA0000, 0x110000, 0x123456)[:14] == bytes.fromhex("0a3700000a000000110056341200") assert tms.extend(10, 0xA0000, 0, 2, 10, 3)[:16] == bytes.fromhex("0a3c00000a0000000000020000000a03") @pytest.mark.parametrize("command,payload,tail", [(58, b"", 2), (52, b"abcdef", 4)]) def test_only_reserved_tail_may_be_missing(command, payload, tail): full = reply(command, payload, tail) for n in range(tail + 1): assert tms.normalize_reply(full[:len(full)-n], 10, command, len(full)) == full assert tms.normalize_reply(full[:len(full)-tail-1], 10, command, len(full)) is None corrupt = bytearray(full) corrupt[2] ^= 1 assert tms.normalize_reply(bytes(corrupt), 10, command, len(full)) is None assert tms.normalize_reply(full, 11, command, len(full)) is None def run_tms(data, target, corrupt=False): plan = tms.programming_steps(data, target) response = None requests = [] while True: try: request, size, timeout, title, percent = plan.send(response) except StopIteration: return requests requests.append(request) command = request[1] if command == 52: address, count = struct.unpack_from("