Skip to content

Commit

Permalink
Merge pull request #81 from khauersp/memory-access-expansion
Browse files Browse the repository at this point in the history
Memory access error expansion
  • Loading branch information
snideto authored Jun 18, 2024
2 parents 276a89b + 28c10d2 commit 04b4294
Show file tree
Hide file tree
Showing 2 changed files with 106 additions and 19 deletions.
48 changes: 29 additions & 19 deletions j1939/Dm14Server.py
Original file line number Diff line number Diff line change
Expand Up @@ -43,15 +43,24 @@ def _wait_for_data(self) -> None:
Determines whether to send data or wait to receive data based on the command type.
If the command is a read command, then the data requested is sent.
"""
if self.command is j1939.Command.READ.value:
self._send_dm15(
self.length,
self.direct,
self.status,
self.state,
self.object_count,
self.sa,
)
self._ca.subscribe(self._parse_dm16)
self._send_dm15(
self.length,
self.direct,
self.status,
self.state,
self.object_count,
self.sa,
j1939.ParameterGroupNumber.PGN.DM15,
self.error,
self.edcp,
)

if (
self.command is j1939.Command.READ.value
and self.state == ResponseState.SEND_PROCEED
):
self._ca.unsubscribe(self._parse_dm16)
self._send_dm16()
if (len(self.data)) <= 8:
self.proceed = True
Expand All @@ -64,18 +73,19 @@ def _wait_for_data(self) -> None:
self.state,
self.object_count,
self.sa,
j1939.ParameterGroupNumber.PGN.DM15,
self.error,
self.edcp,
)
else:
self._ca.subscribe(self._parse_dm16)
self._send_dm15(
self.length,
self.direct,
self.status,
self.state,
self.object_count,
self.sa,
)
elif (
self.command is j1939.Command.WRITE.value
and self.state == ResponseState.SEND_PROCEED
):
self.state = ResponseState.WAIT_FOR_DM16
else:
self._ca.unsubscribe(self._parse_dm16)
self.state = ResponseState.IDLE
self.sa = None

def parse_dm14(
self, priority: int, pgn: int, sa: int, timestamp: int, data: bytearray
Expand Down
77 changes: 77 additions & 0 deletions test/test_memory_access.py
Original file line number Diff line number Diff line change
Expand Up @@ -125,6 +125,30 @@
(Feeder.MsgType.CANTX, 0x18D8F9D4, [0x01, 0x11, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF], 0.0), # DM15 proceed response
]

read_with_seed_error = [
(Feeder.MsgType.CANTX, 0x18D9D4F9, [0x01, 0x13, 0x03, 0x00, 0x00, 0x92, 0x07, 0x00], 0.0), # DM14 read address 0x92000007
(Feeder.MsgType.CANRX, 0x18D8F9D4, [0x00, 0x11, 0xFF, 0xFF, 0xFF, 0xFF, 0x5A, 0xA5], 0.0), # DM15 seed response
(Feeder.MsgType.CANTX, 0x18D9D4F9, [0x01, 0x13, 0x03, 0x00, 0x00, 0x92, 0xA5, 0x5A], 0.0), # DM14 key response
(Feeder.MsgType.CANRX, 0x18D8F9D4, [0x00, 0x1B, 0x01, 0x00, 0x00, 0x07, 0xFF, 0xFF], 0.0), # DM15 error response
]

read_no_seed_error = [
(Feeder.MsgType.CANTX, 0x18D9D4F9, [0x01, 0x13, 0x03, 0x00, 0x00, 0x92, 0x07, 0x00], 0.0), # DM14 read address 0x92000007
(Feeder.MsgType.CANRX, 0x18D8F9D4, [0x00, 0x1B, 0x01, 0x00, 0x00, 0x07, 0xFF, 0xFF], 0.0), # DM15 error response
]

write_with_seed_error = [
(Feeder.MsgType.CANTX, 0x18D9D4F9, [0x01, 0x15, 0x07, 0x00, 0x00, 0x91, 0x07, 0x00], 0.0), # DM14 write address 0x91000007
(Feeder.MsgType.CANRX, 0x18D8F9D4, [0x00, 0x11, 0xFF, 0xFF, 0xFF, 0xFF, 0x5A, 0xA5], 0.0), # DM15 seed response
(Feeder.MsgType.CANTX, 0x18D9D4F9, [0x01, 0x15, 0x07, 0x00, 0x00, 0x91, 0xA5, 0x5A], 0.0), # DM14 key response
(Feeder.MsgType.CANRX, 0x18D8F9D4, [0x00, 0x1B, 0x01, 0x00, 0x00, 0x07, 0xFF, 0xFF], 0.0), # DM15 error response
]

write_no_seed_error = [
(Feeder.MsgType.CANTX, 0x18D9D4F9, [0x01, 0x15, 0x07, 0x00, 0x00, 0x91, 0x07, 0x00], 0.0), # DM14 write address 0x91000007
(Feeder.MsgType.CANRX, 0x18D8F9D4, [0x00, 0x1B, 0x01, 0x00, 0x00, 0x07, 0xFF, 0xFF], 0.0), # DM15 error response
]

error_codes = [0x10, 0x11, 0x12, 0x100, 0x101, 0x1000, 0x1001, 0x100F, 0x10FE]
# fmt: on

Expand Down Expand Up @@ -654,4 +678,57 @@ def test_dm14_write_error(feeder, error_code):
feeder.process_messages()


@pytest.mark.parametrize(
argnames=["expected_messages"],
argvalues=[[read_with_seed_error], [read_no_seed_error]],
ids=["With seed key", "Without seed key"],
)
def test_dm14_read_error_response(feeder, expected_messages):
"""
Tests that the DM14 read query can react to errors correctly
:param feeder: can message feeder
:param expected_messages: list of expected messages
"""
with pytest.raises(RuntimeError) as excinfo:
feeder.can_messages = expected_messages
feeder.pdus_from_messages()
ca = feeder.accept_all_messages(
device_address_preferred=0xF9, bypass_address_claim=True
)
dm14 = j1939.MemoryAccess(ca)
dm14.set_seed_key_algorithm(key_from_seed)
dm14.read(0xD4, 1, 0x92000003, 1)

assert j1939.ErrorInfo[0x1] in str(excinfo.value)

feeder.process_messages()


@pytest.mark.parametrize(
argnames=["expected_messages"],
argvalues=[[write_with_seed_error], [write_no_seed_error]],
ids=["With seed key", "Without seed key"],
)
def test_dm14_write_error_response(feeder, expected_messages):
"""
Tests that the DM14 read query can react to errors correctly
:param feeder: can message feeder
:param expected_messages: list of expected messages
"""
with pytest.raises(RuntimeError) as excinfo:
feeder.can_messages = expected_messages
feeder.pdus_from_messages()
ca = feeder.accept_all_messages(
device_address_preferred=0xF9, bypass_address_claim=True
)
dm14 = j1939.MemoryAccess(ca)
dm14.set_seed_key_algorithm(key_from_seed)
values = [0x11223344]
dm14.write(0xD4, 1, 0x91000007, values, object_byte_size=4)

assert j1939.ErrorInfo[0x1] in str(excinfo.value)

feeder.process_messages()


# TODO: moar test

0 comments on commit 04b4294

Please sign in to comment.