feat(pm3py): transport layer with NG/MIX frame encoding and async serial I/O
This commit is contained in:
59
tests/test_transport.py
Normal file
59
tests/test_transport.py
Normal file
@@ -0,0 +1,59 @@
|
||||
import struct
|
||||
from pm3py.transport import encode_ng_frame, decode_response_frame, encode_mix_frame
|
||||
from pm3py.protocol import Cmd, CMD_PREAMBLE_MAGIC, RESP_PREAMBLE_MAGIC, crc16_a
|
||||
|
||||
def test_encode_ng_frame_ping_no_payload():
|
||||
frame = encode_ng_frame(Cmd.PING, b"")
|
||||
# 8 byte preamble + 0 payload + 2 postamble = 10 bytes
|
||||
assert len(frame) == 10
|
||||
magic, length_ng, cmd = struct.unpack_from("<IHH", frame, 0)
|
||||
assert magic == CMD_PREAMBLE_MAGIC
|
||||
assert length_ng & 0x8000 # ng bit set
|
||||
assert (length_ng & 0x7FFF) == 0
|
||||
assert cmd == Cmd.PING
|
||||
|
||||
def test_encode_ng_frame_with_payload():
|
||||
payload = bytes(range(32))
|
||||
frame = encode_ng_frame(Cmd.PING, payload)
|
||||
assert len(frame) == 10 + 32
|
||||
_, length_ng, _ = struct.unpack_from("<IHH", frame, 0)
|
||||
assert (length_ng & 0x7FFF) == 32
|
||||
# verify payload in frame
|
||||
assert frame[8:40] == payload
|
||||
# verify CRC
|
||||
crc_expected = crc16_a(frame[:40])
|
||||
crc_actual = struct.unpack_from("<H", frame, 40)[0]
|
||||
assert crc_actual == crc_expected
|
||||
|
||||
def test_encode_mix_frame():
|
||||
frame = encode_mix_frame(Cmd.HF_ISO14443A_READER, 0x107, 0, 0, b"")
|
||||
_, length_ng, _ = struct.unpack_from("<IHH", frame, 0)
|
||||
assert not (length_ng & 0x8000) # ng bit NOT set for MIX
|
||||
assert (length_ng & 0x7FFF) == 24 # 3x uint64 = 24 bytes
|
||||
|
||||
def test_decode_response_frame_success():
|
||||
# Build a fake response frame
|
||||
payload = b"\x01\x02\x03\x04"
|
||||
length_ng = len(payload) | 0x8000
|
||||
preamble = struct.pack("<IHbbH", RESP_PREAMBLE_MAGIC, length_ng, 0, 0, Cmd.PING)
|
||||
body = preamble + payload
|
||||
crc = crc16_a(body)
|
||||
postamble = struct.pack("<H", crc)
|
||||
frame = body + postamble
|
||||
|
||||
resp = decode_response_frame(frame)
|
||||
assert resp["cmd"] == Cmd.PING
|
||||
assert resp["status"] == 0
|
||||
assert resp["data"] == payload
|
||||
assert resp["ng"] is True
|
||||
|
||||
def test_decode_response_frame_error_status():
|
||||
length_ng = 0 | 0x8000
|
||||
preamble = struct.pack("<IHbbH", RESP_PREAMBLE_MAGIC, length_ng, -4, -1, Cmd.STATUS)
|
||||
crc = crc16_a(preamble)
|
||||
postamble = struct.pack("<H", crc)
|
||||
frame = preamble + postamble
|
||||
|
||||
resp = decode_response_frame(frame)
|
||||
assert resp["status"] == -4 # ETIMEOUT
|
||||
assert resp["data"] == b""
|
||||
Reference in New Issue
Block a user