[PATCH 3.16 191/233] mac80211/wpa: use constant time memory comparison for MACs

2017-09-09 Thread Ben Hutchings
3.16.48-rc1 review patch.  If anyone has any objections, please let me know.

--

From: "Jason A. Donenfeld" 

commit 98c67d187db7808b1f3c95f2110dd4392d034182 upstream.

Otherwise, we enable all sorts of forgeries via timing attack.

Signed-off-by: Jason A. Donenfeld 
Cc: Johannes Berg 
Cc: linux-wireless@vger.kernel.org
Signed-off-by: Johannes Berg 
[bwh: Backported to 3.16: drop changes in
 ieee80211_crypto_aes_{cmac_256,mac}_decrypt()]
Signed-off-by: Ben Hutchings 
---
 net/mac80211/wpa.c | 9 +
 1 file changed, 5 insertions(+), 4 deletions(-)

--- a/net/mac80211/wpa.c
+++ b/net/mac80211/wpa.c
@@ -16,6 +16,7 @@
 #include 
 #include 
 #include 
+#include 
 
 #include "ieee80211_i.h"
 #include "michael.h"
@@ -147,7 +148,7 @@ ieee80211_rx_h_michael_mic_verify(struct
data_len = skb->len - hdrlen - MICHAEL_MIC_LEN;
key = &rx->key->conf.key[NL80211_TKIP_DATA_OFFSET_RX_MIC_KEY];
michael_mic(key, hdr, data, data_len, mic);
-   if (memcmp(mic, data + data_len, MICHAEL_MIC_LEN) != 0)
+   if (crypto_memneq(mic, data + data_len, MICHAEL_MIC_LEN))
goto mic_fail;
 
/* remove Michael MIC from payload */
@@ -768,7 +769,7 @@ ieee80211_crypto_aes_cmac_decrypt(struct
bip_aad(skb, aad);
ieee80211_aes_cmac(key->u.aes_cmac.tfm, aad,
   skb->data + 24, skb->len - 24, mic);
-   if (memcmp(mic, mmie->mic, sizeof(mmie->mic)) != 0) {
+   if (crypto_memneq(mic, mmie->mic, sizeof(mmie->mic))) {
key->u.aes_cmac.icverrors++;
return RX_DROP_UNUSABLE;
}



[PATCH V2 2/3] brcmfmac: Delete redundant length check

2017-09-09 Thread Kevin Cernekee
brcmf_fweh_process_event() sets event->datalen to the
endian-swapped value of event_packet->msg.datalen, which is the
same as emsg.datalen.  This length is already validated in
brcmf_fweh_process_event(), so there is no need to check it
again upon dequeuing the event.

Suggested-by: Arend van Spriel 
Signed-off-by: Kevin Cernekee 
---
 drivers/net/wireless/broadcom/brcm80211/brcmfmac/fweh.c | 5 -
 1 file changed, 5 deletions(-)


V1->V2: Delete the check instead of moving it.


diff --git a/drivers/net/wireless/broadcom/brcm80211/brcmfmac/fweh.c 
b/drivers/net/wireless/broadcom/brcm80211/brcmfmac/fweh.c
index 4eb1e1ce9ace..27e661fa356f 100644
--- a/drivers/net/wireless/broadcom/brcm80211/brcmfmac/fweh.c
+++ b/drivers/net/wireless/broadcom/brcm80211/brcmfmac/fweh.c
@@ -257,11 +257,6 @@ static void brcmf_fweh_event_worker(struct work_struct 
*work)
brcmf_dbg_hex_dump(BRCMF_EVENT_ON(), event->data,
   min_t(u32, emsg.datalen, 64),
   "event payload, len=%d\n", emsg.datalen);
-   if (emsg.datalen > event->datalen) {
-   brcmf_err("event invalid length header=%d, msg=%d\n",
- event->datalen, emsg.datalen);
-   goto event_free;
-   }
 
/* special handling of interface event */
if (event->code == BRCMF_E_IF) {
-- 
2.14.1.581.gf28d330327-goog



[PATCH V2 1/3] brcmfmac: Avoid possible out-of-bounds read

2017-09-09 Thread Kevin Cernekee
In brcmf_p2p_notify_rx_mgmt_p2p_probereq(), chanspec is assigned before
the length of rxframe is validated.  This could lead to uninitialized
data being accessed (but not printed).  Since we already have a
perfectly good endian-swapped copy of rxframe->chanspec in ch.chspec,
and ch.chspec is not modified by decchspec(), avoid the extra
assignment and use ch.chspec in the debug print.

Suggested-by: Mattias Nissler 
Signed-off-by: Kevin Cernekee 
Reviewed-by: Arend van Spriel 
---
 drivers/net/wireless/broadcom/brcm80211/brcmfmac/p2p.c | 3 +--
 1 file changed, 1 insertion(+), 2 deletions(-)


V1->V2: Clarify changelog re: whether the uninitialized data is printed.


diff --git a/drivers/net/wireless/broadcom/brcm80211/brcmfmac/p2p.c 
b/drivers/net/wireless/broadcom/brcm80211/brcmfmac/p2p.c
index 2ce675ab40ef..1c450c0727cb 100644
--- a/drivers/net/wireless/broadcom/brcm80211/brcmfmac/p2p.c
+++ b/drivers/net/wireless/broadcom/brcm80211/brcmfmac/p2p.c
@@ -1853,7 +1853,6 @@ s32 brcmf_p2p_notify_rx_mgmt_p2p_probereq(struct brcmf_if 
*ifp,
struct afx_hdl *afx_hdl = &p2p->afx_hdl;
struct brcmf_cfg80211_vif *vif = ifp->vif;
struct brcmf_rx_mgmt_data *rxframe = (struct brcmf_rx_mgmt_data *)data;
-   u16 chanspec = be16_to_cpu(rxframe->chanspec);
struct brcmu_chan ch;
u8 *mgmt_frame;
u32 mgmt_frame_len;
@@ -1906,7 +1905,7 @@ s32 brcmf_p2p_notify_rx_mgmt_p2p_probereq(struct brcmf_if 
*ifp,
cfg80211_rx_mgmt(&vif->wdev, freq, 0, mgmt_frame, mgmt_frame_len, 0);
 
brcmf_dbg(INFO, "mgmt_frame_len (%d) , e->datalen (%d), chanspec 
(%04x), freq (%d)\n",
- mgmt_frame_len, e->datalen, chanspec, freq);
+ mgmt_frame_len, e->datalen, ch.chspec, freq);
 
return 0;
 }
-- 
2.14.1.581.gf28d330327-goog



[PATCH V2 3/3] brcmfmac: Add check for short event packets

2017-09-09 Thread Kevin Cernekee
The length of the data in the received skb is currently passed into
brcmf_fweh_process_event() as packet_len, but this value is not checked.
event_packet should be followed by DATALEN bytes of additional event
data.  Ensure that the received packet actually contains at least
DATALEN bytes of additional data, to avoid copying uninitialized memory
into event->data.

Suggested-by: Mattias Nissler 
Signed-off-by: Kevin Cernekee 
Reviewed-by: Arend van Spriel 
---
 drivers/net/wireless/broadcom/brcm80211/brcmfmac/fweh.c | 3 ++-
 1 file changed, 2 insertions(+), 1 deletion(-)


V1->V2: No change.


diff --git a/drivers/net/wireless/broadcom/brcm80211/brcmfmac/fweh.c 
b/drivers/net/wireless/broadcom/brcm80211/brcmfmac/fweh.c
index 27e661fa356f..28361bb865f3 100644
--- a/drivers/net/wireless/broadcom/brcm80211/brcmfmac/fweh.c
+++ b/drivers/net/wireless/broadcom/brcm80211/brcmfmac/fweh.c
@@ -424,7 +424,8 @@ void brcmf_fweh_process_event(struct brcmf_pub *drvr,
if (code != BRCMF_E_IF && !fweh->evt_handler[code])
return;
 
-   if (datalen > BRCMF_DCMD_MAXLEN)
+   if (datalen > BRCMF_DCMD_MAXLEN ||
+   datalen + sizeof(*event_packet) < packet_len)
return;
 
if (in_interrupt())
-- 
2.14.1.581.gf28d330327-goog



Re: [PATCH 3/3] brcmfmac: Add check for short event packets

2017-09-09 Thread Arend van Spriel

On 08-09-17 21:13, Kevin Cernekee wrote:

The length of the data in the received skb is currently passed into
brcmf_fweh_process_event() as packet_len, but this value is not checked.
event_packet should be followed by DATALEN bytes of additional event
data.  Ensure that the received packet actually contains at least
DATALEN bytes of additional data, to avoid copying uninitialized memory
into event->data.


Franky made an almost identical change which I had queued up for 
submission. So you beat us to it ;-)


Reviewed-by: Arend van Spriel 

Suggested-by: Mattias Nissler 
Signed-off-by: Kevin Cernekee 
---
  drivers/net/wireless/broadcom/brcm80211/brcmfmac/fweh.c | 3 ++-
  1 file changed, 2 insertions(+), 1 deletion(-)


Re: [PATCH 2/3] brcmfmac: Don't print out-of-bounds event data

2017-09-09 Thread Arend van Spriel

On 08-09-17 21:13, Kevin Cernekee wrote:

The debug print that dumps out newly-dequeued events uses emsg.datalen
before that field has been validated, which may lead to an out-of-bounds
read.  Assume that any properly-formed event message has a valid length
field, and move the debug print below the length check.


The length check is a bit redundant as event->datalen is assigned to 
emsg.datalen upon queuing the event which also does validation. So I 
would propose to just remove the length check here.


Regards,
Arend


Suggested-by: Mattias Nissler 
Signed-off-by: Kevin Cernekee 
---
  drivers/net/wireless/broadcom/brcm80211/brcmfmac/fweh.c | 10 +-
  1 file changed, 5 insertions(+), 5 deletions(-)


Re: [PATCH 1/3] brcmfmac: Avoid possible out-of-bounds read

2017-09-09 Thread Arend van Spriel

On 08-09-17 21:13, Kevin Cernekee wrote:

In brcmf_p2p_notify_rx_mgmt_p2p_probereq(), chanspec is assigned before
the length of rxframe is validated.  This could lead to uninitialized
data being printed in a debug message.  Since we already have a


The debug message is after the length validation so there is not 
unintialized data being printed.



perfectly good endian-swapped copy of rxframe->chanspec in ch.chspec,
and ch.chspec is not modified by decchspec(), avoid the extra
assignment and use ch.chspec in the debug print.


However, there is no real for the chanspec variable for the given reason 
so...


Reviewed-by: Arend van Spriel 

Suggested-by: Mattias Nissler 
Signed-off-by: Kevin Cernekee 
---
  drivers/net/wireless/broadcom/brcm80211/brcmfmac/p2p.c | 3 +--
  1 file changed, 1 insertion(+), 2 deletions(-)