aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorDan Carpenter <dan.carpenter@oracle.com>2012-03-01 02:02:08 -0500
committerJohn W. Linville <linville@tuxdriver.com>2012-03-05 15:23:15 -0500
commit41eedf39dfb145fb8fa04cd5b799f7bdc7679696 (patch)
tree359897e247fc8112046abae3540759eea33213e2
parent5533513784a88049e19dd2ab380a452b61e5171e (diff)
rndis_wlan: integer overflows in rndis_wlan_do_link_up_work()
If "offset" is negative then we can get past this check: if (offset > CONTROL_BUFFER_SIZE) Or if we pick a very high "req_ie_len" then we can get around the check: if (offset + req_ie_len > CONTROL_BUFFER_SIZE) I made "resp_ie_len" and "req_ie_len" unsigned. I don't know if it was intentional that they were signed in the original. Signed-off-by: Dan Carpenter <dan.carpenter@oracle.com> Acked-by: Jussi Kivilinna <jussi.kivilinna@mbnet.fi> Signed-off-by: John W. Linville <linville@tuxdriver.com>
-rw-r--r--drivers/net/wireless/rndis_wlan.c13
1 files changed, 9 insertions, 4 deletions
diff --git a/drivers/net/wireless/rndis_wlan.c b/drivers/net/wireless/rndis_wlan.c
index a330c69583d6..dde45effef14 100644
--- a/drivers/net/wireless/rndis_wlan.c
+++ b/drivers/net/wireless/rndis_wlan.c
@@ -2755,9 +2755,10 @@ static void rndis_wlan_do_link_up_work(struct usbnet *usbdev)
2755 struct rndis_wlan_private *priv = get_rndis_wlan_priv(usbdev); 2755 struct rndis_wlan_private *priv = get_rndis_wlan_priv(usbdev);
2756 struct ndis_80211_assoc_info *info = NULL; 2756 struct ndis_80211_assoc_info *info = NULL;
2757 u8 bssid[ETH_ALEN]; 2757 u8 bssid[ETH_ALEN];
2758 int resp_ie_len, req_ie_len; 2758 unsigned int resp_ie_len, req_ie_len;
2759 unsigned int offset;
2759 u8 *req_ie, *resp_ie; 2760 u8 *req_ie, *resp_ie;
2760 int ret, offset; 2761 int ret;
2761 bool roamed = false; 2762 bool roamed = false;
2762 bool match_bss; 2763 bool match_bss;
2763 2764
@@ -2785,7 +2786,9 @@ static void rndis_wlan_do_link_up_work(struct usbnet *usbdev)
2785 ret = get_association_info(usbdev, info, CONTROL_BUFFER_SIZE); 2786 ret = get_association_info(usbdev, info, CONTROL_BUFFER_SIZE);
2786 if (!ret) { 2787 if (!ret) {
2787 req_ie_len = le32_to_cpu(info->req_ie_length); 2788 req_ie_len = le32_to_cpu(info->req_ie_length);
2788 if (req_ie_len > 0) { 2789 if (req_ie_len > CONTROL_BUFFER_SIZE)
2790 req_ie_len = CONTROL_BUFFER_SIZE;
2791 if (req_ie_len != 0) {
2789 offset = le32_to_cpu(info->offset_req_ies); 2792 offset = le32_to_cpu(info->offset_req_ies);
2790 2793
2791 if (offset > CONTROL_BUFFER_SIZE) 2794 if (offset > CONTROL_BUFFER_SIZE)
@@ -2799,7 +2802,9 @@ static void rndis_wlan_do_link_up_work(struct usbnet *usbdev)
2799 } 2802 }
2800 2803
2801 resp_ie_len = le32_to_cpu(info->resp_ie_length); 2804 resp_ie_len = le32_to_cpu(info->resp_ie_length);
2802 if (resp_ie_len > 0) { 2805 if (resp_ie_len > CONTROL_BUFFER_SIZE)
2806 resp_ie_len = CONTROL_BUFFER_SIZE;
2807 if (resp_ie_len != 0) {
2803 offset = le32_to_cpu(info->offset_resp_ies); 2808 offset = le32_to_cpu(info->offset_resp_ies);
2804 2809
2805 if (offset > CONTROL_BUFFER_SIZE) 2810 if (offset > CONTROL_BUFFER_SIZE)