@@ -7,12 +7,14 @@ class DMState(Enum):
77 REQUEST_STARTED = 2
88 WAIT_RESPONSE = 3
99 WAIT_QUERY = 4
10+ SERVER_CLEANUP = 5
1011
1112
1213class MemoryAccess :
1314 def __init__ (self , ca : j1939 .ControllerApplication ) -> None :
1415 """
1516 Makes an overarching Memory access class
17+
1618 :param ca: Controller Application
1719 """
1820 self ._ca = ca
@@ -22,14 +24,33 @@ def __init__(self, ca: j1939.ControllerApplication) -> None:
2224 self .state = DMState .IDLE
2325 self .seed_security = False
2426 self ._notify_query_received = None
25- self ._seed_key_valid = None
2627 self ._proceed_function = None
2728
29+ def _handle_error (self , priority : int , pgn : int , sa : int , timestamp : int , data : bytearray , error_code : int ) -> None :
30+ """
31+ Handles errors by resetting the state and unsubscribing from DM14 messages
32+
33+ :param priority: Priority of the message
34+ :param pgn: Parameter Group Number of the message
35+ :param sa: Source Address of the message
36+ :param timestamp: Timestamp of the message
37+ :param data: Data of the PDU
38+ :param error_code: Error code to be set
39+ """
40+ self .server .error = error_code
41+ self .server .set_busy (True )
42+ self .server .parse_dm14 (
43+ priority , pgn , sa , timestamp , data
44+ )
45+ self .server .set_busy (False )
46+ self .reset ()
47+
2848 def _listen_for_dm14 (
2949 self , priority : int , pgn : int , sa : int , timestamp : int , data : bytearray
3050 ) -> None :
3151 """
3252 Listens for dm14 messages and passes them to the appropriate function
53+
3354 :param priority: Priority of the message
3455 :param pgn: Parameter Group Number of the message
3556 :param sa: Source Address of the message
@@ -64,15 +85,7 @@ def _listen_for_dm14(
6485 if self .proceed :
6586 self ._notify_query_received () # notify incoming request
6687 else :
67- self .server .error = 0x100
68- self .server .set_busy (True )
69- self .server .parse_dm14 (
70- priority , pgn , sa , timestamp , data
71- )
72- self .server .set_busy (False )
73- self .server .reset_query ()
74- self .state = DMState .IDLE
75- self .server .error = 0x0
88+ self ._handle_error (priority , pgn , sa , timestamp , data , 0x100 )
7689
7790 case DMState .REQUEST_STARTED :
7891 self .server .parse_dm14 (priority , pgn , sa , timestamp , data )
@@ -101,32 +114,19 @@ def _listen_for_dm14(
101114 if self .proceed :
102115 self ._notify_query_received () # notify incoming request
103116 else :
104- self .server .error = 0x100
105- self .server .set_busy (True )
106- self .server .parse_dm14 (
107- priority , pgn , sa , timestamp , data
108- )
109- self .server .set_busy (False )
110- self .server .reset_query ()
111- self .state = DMState .IDLE
112- self .server .error = 0x0
117+ self ._handle_error (priority , pgn , sa , timestamp , data , 0x100 )
113118 else :
114- self .server .error = 0x1003
115- self .server .set_busy (True )
116- self .server .parse_dm14 (
117- priority , pgn , sa , timestamp , data
118- )
119- self .server .set_busy (False )
120- self .state = DMState .IDLE
121- self .server .error = 0x0
119+ self ._handle_error (priority , pgn , sa , timestamp , data , 0x1003 )
122120
123121 case DMState .WAIT_QUERY :
124122 self .server .set_busy (True )
125123 self .server .parse_dm14 (priority , pgn , sa , timestamp , data )
126124 self .server .set_busy (False )
125+ case DMState .SERVER_CLEANUP :
126+ self .state = DMState .IDLE
127127 case _:
128128 pass
129-
129+
130130 def respond (
131131 self ,
132132 proceed : bool ,
@@ -137,6 +137,7 @@ def respond(
137137 ) -> list :
138138 """
139139 Responds with requested data and error code, if applicable, to a read request
140+
140141 :param bool proceed: whether the operation is good to proceed
141142 :param list data: data to be sent to device
142143 :param int error: error code to be sent to device
@@ -145,14 +146,15 @@ def respond(
145146 """
146147 if data is None :
147148 data = []
148- if self .state is DMState .WAIT_RESPONSE :
149- self ._ca .unsubscribe (self ._listen_for_dm14 )
150- self .state = DMState .IDLE
151- return_data = self .server .respond (proceed , data , error , edcp , max_timeout )
152- self ._ca .subscribe (self ._listen_for_dm14 )
153- return return_data
154- else :
149+
150+ if self .state is not DMState .WAIT_RESPONSE :
155151 return data
152+
153+ self ._ca .unsubscribe (self ._listen_for_dm14 )
154+ return_data = self .server .respond (proceed , data , error , edcp , max_timeout )
155+ self .state = DMState .SERVER_CLEANUP if self .server .state .value != DMState .IDLE .value else DMState .IDLE
156+ self ._ca .subscribe (self ._listen_for_dm14 )
157+ return return_data
156158
157159 def read (
158160 self ,
@@ -167,6 +169,7 @@ def read(
167169 ) -> list :
168170 """
169171 Make a dm14 read Query
172+
170173 :param int dest_address: destination address of the message
171174 :param int direct: direct address of the message
172175 :param int address: address of the message
@@ -189,9 +192,10 @@ def read(
189192 return_raw_bytes ,
190193 max_timeout ,
191194 )
192- self .state = DMState . IDLE
195+ self .reset ()
193196 return data
194197 else :
198+ self .reset ()
195199 raise RuntimeWarning ("Process already Running" )
196200
197201 def write (
@@ -205,6 +209,7 @@ def write(
205209 ) -> None :
206210 """
207211 Send a write query to dest_address, requesting to write values at address
212+
208213 :param int dest_address: destination address of the message
209214 :param int direct: direct address of the message
210215 :param int address: address of the message
@@ -218,7 +223,7 @@ def write(
218223 self .query .write (
219224 dest_address , direct , address , values , object_byte_size , max_timeout
220225 )
221- self .state = DMState . IDLE
226+ self .reset ()
222227
223228 def set_seed_generator (self , seed_generator : callable ) -> None :
224229 """
@@ -229,7 +234,8 @@ def set_seed_generator(self, seed_generator: callable) -> None:
229234
230235 def set_seed_key_algorithm (self , algorithm : callable ) -> None :
231236 """
232- set seed-key algorithm to be used for key generation
237+ Sets seed-key algorithm to be used for key generation
238+
233239 :param callable algorithm: seed-key algorithm
234240 """
235241 self .seed_security = True
@@ -238,28 +244,34 @@ def set_seed_key_algorithm(self, algorithm: callable) -> None:
238244
239245 def set_verify_key (self , verify_key : callable ) -> None :
240246 """
241- set verify key function to be used for verifying the key
247+ Sets verify key function to be used for verifying the key
248+
242249 :param callable verify_key: verify key function
243250 """
244251 self .server .set_verify_key (verify_key )
245252
246253 def set_notify (self , notify : callable ) -> None :
247254 """
248- set notify function to be used for notifying the user of memory accesses
255+ Sets notify function to be used for notifying the user of memory accesses
256+
249257 :param callable notify: notify function
250258 """
251259 self ._notify_query_received = notify
252260
253261 def set_proceed (self , proceed : callable ) -> None :
254262 """
255- set proceed function to determine if a memory query is valid or not
263+ Sets proceed function to determine if a memory query is valid or not
264+
256265 :param callable proceed: proceed function
257266 """
258267 self ._proceed_function = proceed
259268
260- def reset_query (self ) -> None :
269+ def reset (self ) -> None :
261270 """
262- reset query for the server
271+ Resets both server and query to remove transaction specific data
263272 """
273+ self .state = DMState .IDLE
274+ self ._ca .unsubscribe (self ._listen_for_dm14 )
264275 self ._ca .subscribe (self ._listen_for_dm14 )
265- self .server .reset_query ()
276+ self .server .reset_server ()
277+ self .query .reset_query ()
0 commit comments