diff options
author | Aleksander Morgado <aleksander@aleksander.es> | 2019-11-26 21:42:26 +0100 |
---|---|---|
committer | Aleksander Morgado <aleksander@aleksander.es> | 2019-11-26 23:01:19 +0100 |
commit | d498e9323ea133de9993d1fba7f4d548e8ca2152 (patch) | |
tree | dcd44c187aacba4af74c673e4040e600d69586cb | |
parent | 5ddf637c1636c79eaf69dee6fb5223fea9766927 (diff) |
libmbim-glib,message: reading IPv6 array may fail
-rw-r--r-- | build-aux/mbim-codegen/Message.py | 9 | ||||
-rw-r--r-- | src/libmbim-glib/mbim-message-private.h | 9 | ||||
-rw-r--r-- | src/libmbim-glib/mbim-message.c | 43 |
3 files changed, 44 insertions, 17 deletions
diff --git a/build-aux/mbim-codegen/Message.py b/build-aux/mbim-codegen/Message.py index 76b71a9..2488538 100644 --- a/build-aux/mbim-codegen/Message.py +++ b/build-aux/mbim-codegen/Message.py @@ -892,9 +892,10 @@ class Message: ' goto out;\n' ' offset += 4;\n') elif field['format'] == 'ipv6-array': + count_early_outs += 1 inner_template += ( - ' if (out_${field} != NULL)\n' - ' _${field} = _mbim_message_read_ipv6_array (message, _${array_size_field}, offset);\n' + ' if ((out_${field} != NULL) && !_mbim_message_read_ipv6_array (message, _${array_size_field}, offset, &_${field}, error))\n' + ' goto out;\n' ' offset += 4;\n') inner_template += ( @@ -999,6 +1000,7 @@ class Message: field['format'] == 'ipv4-array' or \ field['format'] == 'ipv6' or \ field['format'] == 'ref-ipv6' or \ + field['format'] == 'ipv6-array' or \ field['format'] == 'uuid' or \ field['format'] == 'struct-array' or \ field['format'] == 'ref-struct-array' or \ @@ -1298,7 +1300,8 @@ class Message: elif field['format'] == 'ipv6-array': inner_template += ( ' array_size = _${array_size_field};\n' - ' tmp = _mbim_message_read_ipv6_array (message, _${array_size_field}, offset);\n' + ' if (!_mbim_message_read_ipv6_array (message, _${array_size_field}, offset, &tmp, &inner_error))\n' + ' goto out;\n' ' offset += 4;\n') inner_template += ( diff --git a/src/libmbim-glib/mbim-message-private.h b/src/libmbim-glib/mbim-message-private.h index 341c257..467e356 100644 --- a/src/libmbim-glib/mbim-message-private.h +++ b/src/libmbim-glib/mbim-message-private.h @@ -308,10 +308,11 @@ gboolean _mbim_message_read_ipv6 (const MbimMessage *self, gboolean ref, const MbimIPv6 **ipv6, GError **error); - -MbimIPv6 *_mbim_message_read_ipv6_array (const MbimMessage *self, - guint32 array_size, - guint32 relative_offset_array_start); +gboolean _mbim_message_read_ipv6_array (const MbimMessage *self, + guint32 array_size, + guint32 relative_offset_array_start, + MbimIPv6 **array, + GError **error); G_END_DECLS diff --git a/src/libmbim-glib/mbim-message.c b/src/libmbim-glib/mbim-message.c index a4dcb4c..bda5650 100644 --- a/src/libmbim-glib/mbim-message.c +++ b/src/libmbim-glib/mbim-message.c @@ -712,34 +712,57 @@ _mbim_message_read_ipv6 (const MbimMessage *self, return TRUE; } -MbimIPv6 * -_mbim_message_read_ipv6_array (const MbimMessage *self, - guint32 array_size, - guint32 relative_offset_array_start) +gboolean +_mbim_message_read_ipv6_array (const MbimMessage *self, + guint32 array_size, + guint32 relative_offset_array_start, + MbimIPv6 **array, + GError **error) { - MbimIPv6 *array; + guint32 required_size; guint32 offset; guint32 i; guint32 information_buffer_offset; - if (!array_size) - return NULL; + g_assert (array != NULL); + + if (!array_size) { + *array = NULL; + return TRUE; + } information_buffer_offset = _mbim_message_get_information_buffer_offset (self); - array = g_new (MbimIPv6, array_size); + required_size = information_buffer_offset + relative_offset_array_start + 4; + if (self->len < required_size) { + g_set_error (error, MBIM_CORE_ERROR, MBIM_CORE_ERROR_INVALID_MESSAGE, + "cannot read IPv6 array offset (4 bytes) (%u < %u)", + self->len, required_size); + return FALSE; + } + offset = GUINT32_FROM_LE (G_STRUCT_MEMBER ( guint32, self->data, (information_buffer_offset + relative_offset_array_start))); + + required_size = information_buffer_offset + offset + (16 * array_size); + if (self->len < required_size) { + g_set_error (error, MBIM_CORE_ERROR, MBIM_CORE_ERROR_INVALID_MESSAGE, + "cannot read IPv6 array data (%u bytes) (%u < %u)", + (16 * array_size), self->len, required_size); + return FALSE; + } + + *array = g_new (MbimIPv6, array_size); for (i = 0; i < array_size; i++, offset += 16) { - memcpy (&array[i], + memcpy (&((*array)[i]), G_STRUCT_MEMBER_P (self->data, (information_buffer_offset + offset)), 16); } - return array; + return TRUE; } /*****************************************************************************/ |