@@ -537,11 +537,13 @@ struct libipw_txb {
struct libipw_qos_information_element {
u8 elementID;
u8 length;
- u8 qui[QOS_OUI_LEN];
- u8 qui_type;
- u8 qui_subtype;
- u8 version;
- u8 ac_info;
+ struct_group(data,
+ u8 qui[QOS_OUI_LEN];
+ u8 qui_type;
+ u8 qui_subtype;
+ u8 version;
+ u8 ac_info;
+ );
} __packed;
struct libipw_qos_ac_parameter {
@@ -948,13 +948,13 @@ static int libipw_read_qos_param_element(struct libipw_qos_parameter_info
*info_element)
{
int ret = 0;
- u16 size = sizeof(struct libipw_qos_parameter_info) - 2;
+ u16 size = sizeof(element_param->info_element.data);
if ((info_element == NULL) || (element_param == NULL))
return -1;
if (info_element->id == QOS_ELEMENT_ID && info_element->len == size) {
- memcpy(element_param->info_element.qui, info_element->data,
+ memcpy(&element_param->info_element.data, info_element->data,
info_element->len);
element_param->info_element.elementID = info_element->id;
element_param->info_element.length = info_element->len;
@@ -975,7 +975,7 @@ static int libipw_read_qos_info_element(struct
*info_element)
{
int ret = 0;
- u16 size = sizeof(struct libipw_qos_information_element) - 2;
+ u16 size = sizeof(element_info->data);
if (element_info == NULL)
return -1;
@@ -983,7 +983,7 @@ static int libipw_read_qos_info_element(struct
return -1;
if ((info_element->id == QOS_ELEMENT_ID) && (info_element->len == size)) {
- memcpy(element_info->qui, info_element->data,
+ memcpy(&element_info->data, info_element->data,
info_element->len);
element_info->elementID = info_element->id;
element_info->length = info_element->len;
In preparation for FORTIFY_SOURCE performing compile-time and run-time field array bounds checking for memcpy(), memmove(), and memset(), avoid intentionally writing across neighboring fields. Use struct_group() in struct libipw_qos_information_element around members qui, qui_type, qui_subtype, version, and ac_info, so they can be referenced together. This will allow memcpy() and sizeof() to more easily reason about sizes, improve readability, and avoid future warnings about writing beyond the end of qui. "pahole" shows no size nor member offset changes to struct libipw_qos_information_element. Additionally corrects the size in libipw_read_qos_param_element() as it was testing the wrong structure size (it should have been struct libipw_qos_information_element, not struct libipw_qos_parameter_info). Signed-off-by: Kees Cook <keescook@chromium.org> --- drivers/net/wireless/intel/ipw2x00/libipw.h | 12 +++++++----- drivers/net/wireless/intel/ipw2x00/libipw_rx.c | 8 ++++---- 2 files changed, 11 insertions(+), 9 deletions(-)