aboutsummaryrefslogtreecommitdiffstats
path: root/epan/dissectors/packet-epl.c
diff options
context:
space:
mode:
authorChristian Krump <christian.krump@br-automation.com>2020-10-15 14:30:39 +0200
committerWireshark GitLab Utility <gerald+gitlab-utility@wireshark.org>2020-10-15 22:35:29 +0000
commit76e56358c25e43b30b4ef40d441906fc5dff6b2d (patch)
treeba27cc9cc502b92fae2b8cb12f217e8de1a53580 /epan/dissectors/packet-epl.c
parent34626f25966ee875e773c79d8c7af9f9e68a8c11 (diff)
EPL: wrong size detection of last segment
- fixed size detection of last segment in multiple read/write ASNDs
Diffstat (limited to 'epan/dissectors/packet-epl.c')
-rw-r--r--epan/dissectors/packet-epl.c128
1 files changed, 63 insertions, 65 deletions
diff --git a/epan/dissectors/packet-epl.c b/epan/dissectors/packet-epl.c
index a548782d0a..7404611948 100644
--- a/epan/dissectors/packet-epl.c
+++ b/epan/dissectors/packet-epl.c
@@ -4348,6 +4348,7 @@ dissect_epl_sdo_command_write_multiple_by_index(struct epl_convo *convo, proto_t
proto_tree *psf_od_tree;
struct object *obj = NULL;
const struct subobject *subobj = NULL;
+ guint16 segment_restsize = segment_size;
/* Offset is calculated simply by only applying EPL payload offset, not packet offset.
@@ -4378,45 +4379,38 @@ dissect_epl_sdo_command_write_multiple_by_index(struct epl_convo *convo, proto_t
/* the data is aligned in 4-byte increments, therfore maximum padding is 3 */
padding = tvb_get_guint8 ( tvb, offset + 7 ) & 0x03;
- datalength = offsetincrement - ( offset - EPL_SOA_EPLV_OFFSET );
/* An offset increment of zero usually indicates, that we are at the end
* of the payload. But we cannot ignore the end, because packages are
* stacked up until the last byte */
- if ( offsetincrement == 0 )
- datalength = remlength - EPL_SOA_EPLV_OFFSET;
-
- /* Possible guint overflow */
- if ( ( datalength + EPL_SOA_EPLV_OFFSET ) > remlength )
- break;
-
- /* Last frame detected */
- if ( offsetincrement == 0 )
+ if (offsetincrement == 0)
{
- datalength = remlength;
-
- /* guarding size against remaining length */
- if ( remlength < EPL_SOA_EPLV_OFFSET )
- break;
-
- size = remlength - EPL_SOA_EPLV_OFFSET - padding;
+ datalength = segment_restsize;
lastentry = TRUE;
}
else
{
- /* Each entry has a header size of 8, based on the following calculation:
- * - 4 byte for byte position of next data set
- * - 2 byte for index
- * - 1 byte for subindex
- * - 1 byte for reserved and padding */
-
- /* Guarding against readout of padding. Probability is nearly zero, as
- * padding was checked above, but to be sure, this remains here */
- if ( (guint32)( padding + 8 ) >= datalength )
- break;
-
- /* size of data is datalength - ( entry header size and padding ) */
- size = datalength - 8 - padding;
+ datalength = offsetincrement - (offset - EPL_SOA_EPLV_OFFSET);
}
+ /* decrease restsize */
+ segment_restsize -= datalength;
+
+ /* Possible guint overflow */
+ if ( datalength > remlength )
+ break;
+
+ /* Each entry has a header size of 8, based on the following calculation:
+ * - 4 byte for byte position of next data set
+ * - 2 byte for index
+ * - 1 byte for subindex
+ * - 1 byte for reserved and padding */
+
+ /* Guarding against readout of padding. Probability is nearly zero, as
+ * padding was checked above, but to be sure, this remains here */
+ if ((guint32)(padding + 8) >= datalength)
+ break;
+
+ /* size of data is datalength - ( entry header size and padding ) */
+ size = datalength - 8 - padding;
dataoffset = offset + 4;
@@ -4689,6 +4683,7 @@ dissect_epl_sdo_command_read_multiple_by_index(struct epl_convo *convo, proto_tr
struct object *obj = NULL;
const struct subobject *subobj = NULL;
const char *name;
+ guint16 segment_restsize = segment_size;
/* Offset is calculated simply by only applying EPL payload offset, not packet offset.
* The packet offset is 16, as this is the number of bytes trailing the SDO payload.
@@ -4720,45 +4715,38 @@ dissect_epl_sdo_command_read_multiple_by_index(struct epl_convo *convo, proto_tr
if ((tvb_get_guint8 ( tvb, offset + 7 ) & 0x80) == 0x80)
is_abort = TRUE;
- datalength = offsetincrement - ( offset - EPL_SOA_EPLV_OFFSET );
- /* An offset increment of zero usually indicates, that we are at the end
- * of the payload. But we cannot ignore the end, because packages are
- * stacked up until the last byte */
- if ( offsetincrement == 0 )
- datalength = remlength - EPL_SOA_EPLV_OFFSET;
-
- /* Possible guint overflow */
- if ( ( datalength + EPL_SOA_EPLV_OFFSET ) > remlength )
- break;
-
- /* Last frame detected */
- if ( offsetincrement == 0 )
+ /* An offset increment of zero usually indicates, that we are at the end
+ * of the payload. But we cannot ignore the end, because packages are
+ * stacked up until the last byte */
+ if (offsetincrement == 0)
{
- datalength = remlength;
-
- /* guarding size against remaining length */
- if ( remlength < EPL_SOA_EPLV_OFFSET )
- break;
-
- size = remlength - EPL_SOA_EPLV_OFFSET - padding;
+ datalength = segment_restsize;
lastentry = TRUE;
}
else
{
- /* Each entry has a header size of 8, based on the following calculation:
- * - 4 byte for byte position of next data set
- * - 2 byte for index
- * - 1 byte for subindex
- * - 1 byte for reserved and padding */
-
- /* Guarding against readout of padding. Probability is nearly zero, as
- * padding was checked above, but to be sure, this remains here */
- if ( (guint32)( padding + 8 ) >= datalength )
- break;
-
- /* size of data is datalength - ( entry header size and padding ) */
- size = datalength - 8 - padding;
+ datalength = offsetincrement - (offset - EPL_SOA_EPLV_OFFSET);
}
+ /* decrease restsize */
+ segment_restsize -= datalength;
+
+ /* Possible guint overflow */
+ if (datalength > remlength)
+ break;
+
+ /* Each entry has a header size of 8, based on the following calculation:
+ * - 4 byte for byte position of next data set
+ * - 2 byte for index
+ * - 1 byte for subindex
+ * - 1 byte for reserved and padding */
+
+ /* Guarding against readout of padding. Probability is nearly zero, as
+ * padding was checked above, but to be sure, this remains here */
+ if ((guint32)(padding + 8) >= datalength)
+ break;
+
+ /* size of data is datalength - ( entry header size and padding ) */
+ size = datalength - 8 - padding;
dataoffset = offset + 4;
@@ -5059,7 +5047,7 @@ dissect_epl_sdo_command_read_multiple_by_index(struct epl_convo *convo, proto_tr
static gint
dissect_epl_sdo_command_read_by_index(struct epl_convo *convo, proto_tree *epl_tree, tvbuff_t *tvb, packet_info *pinfo, gint offset, guint8 segmented, gboolean response, guint16 segment_size)
{
- gint size, payload_length;
+ gint size, payload_length, rem_size = 0;
guint16 idx = 0x00;
guint8 subindex = 0x00;
guint32 fragmentId, frame;
@@ -5213,7 +5201,17 @@ dissect_epl_sdo_command_read_by_index(struct epl_convo *convo, proto_tree *epl_t
}
- offset = dissect_epl_payload(epl_tree, tvb, pinfo, offset, size, type, EPL_ASND);
+ /* determine remaining SDO payload size (depends on segment size of current command) */
+ if (size > (segment_size - 4))
+ {
+ rem_size = (segment_size - 4);
+ }
+ else
+ {
+ rem_size = size;
+ }
+
+ offset = dissect_epl_payload(epl_tree, tvb, pinfo, offset, rem_size, type, EPL_ASND);
}
return offset;