From 6f9f06eb4a2d8989583e35ec0d4b34d7705726d0 Mon Sep 17 00:00:00 2001 From: Carl Ljungholm Date: Sun, 17 Sep 2023 10:26:42 +0200 Subject: [PATCH] Use smaller of response size and size in OD (#395) --- canopen/sdo/client.py | 27 ++++++++++++++------------- 1 file changed, 14 insertions(+), 13 deletions(-) diff --git a/canopen/sdo/client.py b/canopen/sdo/client.py index 21517717..370aab72 100644 --- a/canopen/sdo/client.py +++ b/canopen/sdo/client.py @@ -114,21 +114,22 @@ def upload(self, index: int, subindex: int) -> bytes: When node responds with an error. """ with self.open(index, subindex, buffering=0) as fp: - size = fp.size + response_size = fp.size data = fp.read() - if size is None: - # Node did not specify how many bytes to use - # Try to find out using Object Dictionary - var = self.od.get_variable(index, subindex) - if var is not None: - # Found a matching variable in OD - # If this is a data type (string, domain etc) the size is - # unknown anyway so keep the data as is - if var.data_type not in objectdictionary.DATA_TYPES: - # Get the size in bytes for this variable - size = len(var) // 8 + + # If size is available through variable in OD, then use the smaller of the two sizes. + # Some devices send U32/I32 even if variable is smaller in OD + var = self.od.get_variable(index, subindex) + if var is not None: + # Found a matching variable in OD + # If this is a data type (string, domain etc) the size is + # unknown anyway so keep the data as is + if var.data_type not in objectdictionary.DATA_TYPES: + # Get the size in bytes for this variable + var_size = len(var) // 8 + if response_size is None or var_size < response_size: # Truncate the data to specified size - data = data[0:size] + data = data[0:var_size] return data def download(