Commit 6390d885 authored by Daniel Drake's avatar Daniel Drake Committed by John W. Linville

mwifiex: fix memory corruption when unsetting multicast list

When trying to unset a previously-set multicast list (i.e. the new list
has 0 entries), mwifiex_set_multicast_list() was calling down to
mwifiex_request_set_multicast_list() while leaving
mcast_list.num_multicast_addr as an uninitialized value.

We were arriving at mwifiex_cmd_mac_multicast_adr() which would then
proceed to do an often huge memcpy of
mcast_list.num_multicast_addr*ETH_ALEN bytes, causing memory corruption
and hard to debug crashes.

Fix this by setting mcast_list.num_multicast_addr to 0 when no multicast
list is provided. Similarly, fix up the logic in
mwifiex_request_set_multicast_list() to unset the multicast list that
was previously sent to the hardware in such cases.
Signed-off-by: default avatarDaniel Drake <dsd@laptop.org>
Acked-by: default avatarBing Zhao <bzhao@marvell.com>
Signed-off-by: default avatarJohn W. Linville <linville@tuxdriver.com>
parent 3c68ef5b
...@@ -669,7 +669,6 @@ static void mwifiex_set_multicast_list(struct net_device *dev) ...@@ -669,7 +669,6 @@ static void mwifiex_set_multicast_list(struct net_device *dev)
mcast_list.mode = MWIFIEX_ALL_MULTI_MODE; mcast_list.mode = MWIFIEX_ALL_MULTI_MODE;
} else { } else {
mcast_list.mode = MWIFIEX_MULTICAST_MODE; mcast_list.mode = MWIFIEX_MULTICAST_MODE;
if (netdev_mc_count(dev))
mcast_list.num_multicast_addr = mcast_list.num_multicast_addr =
mwifiex_copy_mcast_addr(&mcast_list, dev); mwifiex_copy_mcast_addr(&mcast_list, dev);
} }
......
...@@ -104,7 +104,6 @@ int mwifiex_request_set_multicast_list(struct mwifiex_private *priv, ...@@ -104,7 +104,6 @@ int mwifiex_request_set_multicast_list(struct mwifiex_private *priv,
} else { } else {
priv->curr_pkt_filter &= priv->curr_pkt_filter &=
~HostCmd_ACT_MAC_ALL_MULTICAST_ENABLE; ~HostCmd_ACT_MAC_ALL_MULTICAST_ENABLE;
if (mcast_list->num_multicast_addr) {
dev_dbg(priv->adapter->dev, dev_dbg(priv->adapter->dev,
"info: Set multicast list=%d\n", "info: Set multicast list=%d\n",
mcast_list->num_multicast_addr); mcast_list->num_multicast_addr);
...@@ -115,7 +114,6 @@ int mwifiex_request_set_multicast_list(struct mwifiex_private *priv, ...@@ -115,7 +114,6 @@ int mwifiex_request_set_multicast_list(struct mwifiex_private *priv,
mcast_list); mcast_list);
} }
} }
}
dev_dbg(priv->adapter->dev, dev_dbg(priv->adapter->dev,
"info: old_pkt_filter=%#x, curr_pkt_filter=%#x\n", "info: old_pkt_filter=%#x, curr_pkt_filter=%#x\n",
old_pkt_filter, priv->curr_pkt_filter); old_pkt_filter, priv->curr_pkt_filter);
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment