[PATCH] staging: ks7010: removed custom Michael MIC implementation.

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



Changed the driver to use the kernel's own implementation.

Signed-off-by: Jeremy Sowden <jeremy@xxxxxxxxxx>
---
 drivers/staging/ks7010/Makefile      |   2 +-
 drivers/staging/ks7010/TODO          |   2 -
 drivers/staging/ks7010/ks_hostif.c   | 111 +++++++++++++++++++----
 drivers/staging/ks7010/michael_mic.c | 127 ---------------------------
 drivers/staging/ks7010/michael_mic.h |  21 -----
 5 files changed, 93 insertions(+), 170 deletions(-)
 delete mode 100644 drivers/staging/ks7010/michael_mic.c
 delete mode 100644 drivers/staging/ks7010/michael_mic.h

diff --git a/drivers/staging/ks7010/Makefile b/drivers/staging/ks7010/Makefile
index 07dc16cc86f5..412e2105a3a5 100644
--- a/drivers/staging/ks7010/Makefile
+++ b/drivers/staging/ks7010/Makefile
@@ -1,3 +1,3 @@
 obj-$(CONFIG_KS7010) += ks7010.o
 
-ks7010-y	     := michael_mic.o ks_hostif.o ks_wlan_net.o ks7010_sdio.o
+ks7010-y	:= ks_hostif.o ks_wlan_net.o ks7010_sdio.o
diff --git a/drivers/staging/ks7010/TODO b/drivers/staging/ks7010/TODO
index d393ca58e231..87a6dac4890d 100644
--- a/drivers/staging/ks7010/TODO
+++ b/drivers/staging/ks7010/TODO
@@ -27,8 +27,6 @@ Now the TODOs:
 - fix the 'card removal' event when card is inserted when booting
 - check what other upstream wireless mechanisms can be used instead of the
   custom ones here
-- replace custom Michael MIC implementation with the kernel
-  implementation. This task is only required for a *clean* WEXT interface.
 
 Please send any patches to:
 Greg Kroah-Hartman <gregkh@xxxxxxxxxxxxxxxxxxx>
diff --git a/drivers/staging/ks7010/ks_hostif.c b/drivers/staging/ks7010/ks_hostif.c
index e48fc36b6ebd..06ebea0be118 100644
--- a/drivers/staging/ks7010/ks_hostif.c
+++ b/drivers/staging/ks7010/ks_hostif.c
@@ -6,15 +6,18 @@
  *   Copyright (C) 2009 Renesas Technology Corp.
  */
 
+#include <crypto/hash.h>
 #include <linux/circ_buf.h>
 #include <linux/if_arp.h>
 #include <net/iw_handler.h>
 #include <uapi/linux/llc.h>
 #include "eap_packet.h"
 #include "ks_wlan.h"
-#include "michael_mic.h"
 #include "ks_hostif.h"
 
+#define MICHAEL_MIC_KEY_LEN 8
+#define MICHAEL_MIC_LEN     8
+
 static inline void inc_smeqhead(struct ks_wlan_private *priv)
 {
 	priv->sme_i.qhead = (priv->sme_i.qhead + 1) % SME_EVENT_BUFF_SIZE;
@@ -191,6 +194,68 @@ static u8 read_ie(unsigned char *bp, u8 max, u8 *body)
 	return size;
 }
 
+static int
+michael_mic(u8 *key, u8 *data, unsigned int len, u8 priority, u8 *result)
+{
+	u8 pad_data[4] = { priority, 0, 0, 0 };
+	struct crypto_shash *tfm = NULL;
+	struct shash_desc *desc = NULL;
+	int ret;
+
+	tfm = crypto_alloc_shash("michael_mic", 0, 0);
+	if (IS_ERR(tfm)) {
+		ret = PTR_ERR(tfm);
+		goto err;
+	}
+
+	ret = crypto_shash_setkey(tfm, key, MICHAEL_MIC_KEY_LEN);
+	if (ret < 0)
+		goto err_free_tfm;
+
+	desc = kmalloc(sizeof(*desc) + crypto_shash_descsize(tfm), GFP_KERNEL);
+	if (!desc) {
+		ret = -ENOMEM;
+		goto err_free_tfm;
+	}
+
+	desc->tfm = tfm;
+	desc->flags = 0;
+
+	ret = crypto_shash_init(desc);
+	if (ret < 0)
+		goto err_free_desc;
+
+	// Compute the MIC value
+	/*
+	 * IEEE802.11i  page 47
+	 * Figure 43g TKIP MIC processing format
+	 * +--+--+--------+--+----+--+--+--+--+--+--+--+--+
+	 * |6 |6 |1       |3 |M   |1 |1 |1 |1 |1 |1 |1 |1 | Octet
+	 * +--+--+--------+--+----+--+--+--+--+--+--+--+--+
+	 * |DA|SA|Priority|0 |Data|M0|M1|M2|M3|M4|M5|M6|M7|
+	 * +--+--+--------+--+----+--+--+--+--+--+--+--+--+
+	 */
+
+	ret = crypto_shash_update(desc, data, 12);
+	if (ret < 0)
+		goto err_free_desc;
+
+	ret = crypto_shash_update(desc, pad_data, 4);
+	if (ret < 0)
+		goto err_free_desc;
+
+	ret = crypto_shash_finup(desc, data + 12, len - 12, result);
+
+err_free_desc:
+	kzfree(desc);
+
+err_free_tfm:
+	crypto_free_shash(tfm);
+
+err:
+	return ret;
+}
+
 static
 int get_ap_information(struct ks_wlan_private *priv, struct ap_info *ap_info,
 		       struct local_ap *ap)
@@ -273,11 +338,11 @@ int hostif_data_indication_wpa(struct ks_wlan_private *priv,
 {
 	struct ether_hdr *eth_hdr;
 	unsigned short eth_proto;
-	unsigned char recv_mic[8];
+	unsigned char recv_mic[MICHAEL_MIC_LEN];
 	char buf[128];
 	unsigned long now;
 	struct mic_failure *mic_failure;
-	struct michael_mic michael_mic;
+	u8 mic[MICHAEL_MIC_LEN];
 	union iwreq_data wrqu;
 	unsigned int key_index = auth_type - 1;
 	struct wpa_key *key = &priv->wpa.key[key_index];
@@ -300,14 +365,20 @@ int hostif_data_indication_wpa(struct ks_wlan_private *priv,
 		netdev_dbg(priv->net_dev, "TKIP: protocol=%04X: size=%u\n",
 			   eth_proto, priv->rx_size);
 		/* MIC save */
-		memcpy(&recv_mic[0], (priv->rxp) + ((priv->rx_size) - 8), 8);
-		priv->rx_size = priv->rx_size - 8;
+		memcpy(&recv_mic[0],
+		       (priv->rxp) + ((priv->rx_size) - sizeof(recv_mic)),
+		       sizeof(recv_mic));
+		priv->rx_size = priv->rx_size - sizeof(recv_mic);
 		if (auth_type > 0 && auth_type < 4) {	/* auth_type check */
-			michael_mic_function(&michael_mic, key->rx_mic_key,
-					     priv->rxp, priv->rx_size,
-					     0,	michael_mic.result);
+			int ret;
+
+			ret = michael_mic(key->rx_mic_key,
+					  priv->rxp, priv->rx_size,
+					  0, mic);
+			if (ret < 0)
+				return ret;
 		}
-		if (memcmp(michael_mic.result, recv_mic, 8) != 0) {
+		if (memcmp(mic, recv_mic, sizeof(mic)) != 0) {
 			now = jiffies;
 			mic_failure = &priv->wpa.mic_failure;
 			/* MIC FAILURE */
@@ -1002,7 +1073,6 @@ int hostif_data_request(struct ks_wlan_private *priv, struct sk_buff *skb)
 	int result = 0;
 	unsigned short eth_proto;
 	struct ether_hdr *eth_hdr;
-	struct michael_mic michael_mic;
 	unsigned short keyinfo = 0;
 	struct ieee802_1x_hdr *aa1x_hdr;
 	struct wpa_eapol_key *eap_key;
@@ -1109,17 +1179,20 @@ int hostif_data_request(struct ks_wlan_private *priv, struct sk_buff *skb)
 			pp->auth_type = cpu_to_le16(TYPE_AUTH);
 		} else {
 			if (priv->wpa.pairwise_suite == IW_AUTH_CIPHER_TKIP) {
-				michael_mic_function(&michael_mic,
-						     priv->wpa.key[0].tx_mic_key,
-						     &pp->data[0], skb_len,
-						     0,	michael_mic.result);
-				memcpy(p, michael_mic.result, 8);
-				length += 8;
-				skb_len += 8;
-				p += 8;
+				u8 mic[MICHAEL_MIC_LEN];
+
+				ret = michael_mic(priv->wpa.key[0].tx_mic_key,
+						  &pp->data[0], skb_len,
+						  0, mic);
+				if (ret < 0)
+					goto err_kfree;
+
+				memcpy(p, mic, sizeof(mic));
+				length += sizeof(mic);
+				skb_len += sizeof(mic);
+				p += sizeof(mic);
 				pp->auth_type =
 				    cpu_to_le16(TYPE_DATA);
-
 			} else if (priv->wpa.pairwise_suite ==
 				   IW_AUTH_CIPHER_CCMP) {
 				pp->auth_type =
diff --git a/drivers/staging/ks7010/michael_mic.c b/drivers/staging/ks7010/michael_mic.c
deleted file mode 100644
index 3acd79615f98..000000000000
--- a/drivers/staging/ks7010/michael_mic.c
+++ /dev/null
@@ -1,127 +0,0 @@
-// SPDX-License-Identifier: GPL-2.0
-/*
- *   Driver for KeyStream wireless LAN
- *
- *   Copyright (C) 2005-2008 KeyStream Corp.
- *   Copyright (C) 2009 Renesas Technology Corp.
- */
-
-#include <asm/unaligned.h>
-#include <linux/bitops.h>
-#include <linux/string.h>
-#include "michael_mic.h"
-
-// Reset the state to the empty message.
-static inline void michael_clear(struct michael_mic *mic)
-{
-	mic->l = mic->k0;
-	mic->r = mic->k1;
-	mic->m_bytes = 0;
-}
-
-static void michael_init(struct michael_mic *mic, u8 *key)
-{
-	// Set the key
-	mic->k0 = get_unaligned_le32(key);
-	mic->k1 = get_unaligned_le32(key + 4);
-
-	//clear();
-	michael_clear(mic);
-}
-
-static inline void michael_block(struct michael_mic *mic)
-{
-	mic->r ^= rol32(mic->l, 17);
-	mic->l += mic->r;
-	mic->r ^= ((mic->l & 0xff00ff00) >> 8) |
-		  ((mic->l & 0x00ff00ff) << 8);
-	mic->l += mic->r;
-	mic->r ^= rol32(mic->l, 3);
-	mic->l += mic->r;
-	mic->r ^= ror32(mic->l, 2);
-	mic->l += mic->r;
-}
-
-static void michael_append(struct michael_mic *mic, u8 *src, int bytes)
-{
-	int addlen;
-
-	if (mic->m_bytes) {
-		addlen = 4 - mic->m_bytes;
-		if (addlen > bytes)
-			addlen = bytes;
-		memcpy(&mic->m[mic->m_bytes], src, addlen);
-		mic->m_bytes += addlen;
-		src += addlen;
-		bytes -= addlen;
-
-		if (mic->m_bytes < 4)
-			return;
-
-		mic->l ^= get_unaligned_le32(mic->m);
-		michael_block(mic);
-		mic->m_bytes = 0;
-	}
-
-	while (bytes >= 4) {
-		mic->l ^= get_unaligned_le32(src);
-		michael_block(mic);
-		src += 4;
-		bytes -= 4;
-	}
-
-	if (bytes > 0) {
-		mic->m_bytes = bytes;
-		memcpy(mic->m, src, bytes);
-	}
-}
-
-static void michael_get_mic(struct michael_mic *mic, u8 *dst)
-{
-	u8 *data = mic->m;
-
-	switch (mic->m_bytes) {
-	case 0:
-		mic->l ^= 0x5a;
-		break;
-	case 1:
-		mic->l ^= data[0] | 0x5a00;
-		break;
-	case 2:
-		mic->l ^= data[0] | (data[1] << 8) | 0x5a0000;
-		break;
-	case 3:
-		mic->l ^= data[0] | (data[1] << 8) | (data[2] << 16) |
-		    0x5a000000;
-		break;
-	}
-	michael_block(mic);
-	michael_block(mic);
-	// The appendByte function has already computed the result.
-	put_unaligned_le32(mic->l, dst);
-	put_unaligned_le32(mic->r, dst + 4);
-
-	// Reset to the empty message.
-	michael_clear(mic);
-}
-
-void michael_mic_function(struct michael_mic *mic, u8 *key,
-			  u8 *data, unsigned int len, u8 priority, u8 *result)
-{
-	u8 pad_data[4] = { priority, 0, 0, 0 };
-	// Compute the MIC value
-	/*
-	 * IEEE802.11i  page 47
-	 * Figure 43g TKIP MIC processing format
-	 * +--+--+--------+--+----+--+--+--+--+--+--+--+--+
-	 * |6 |6 |1       |3 |M   |1 |1 |1 |1 |1 |1 |1 |1 | Octet
-	 * +--+--+--------+--+----+--+--+--+--+--+--+--+--+
-	 * |DA|SA|Priority|0 |Data|M0|M1|M2|M3|M4|M5|M6|M7|
-	 * +--+--+--------+--+----+--+--+--+--+--+--+--+--+
-	 */
-	michael_init(mic, key);
-	michael_append(mic, data, 12);	/* |DA|SA| */
-	michael_append(mic, pad_data, 4);	/* |Priority|0|0|0| */
-	michael_append(mic, data + 12, len - 12);	/* |Data| */
-	michael_get_mic(mic, result);
-}
diff --git a/drivers/staging/ks7010/michael_mic.h b/drivers/staging/ks7010/michael_mic.h
deleted file mode 100644
index f0ac164b999b..000000000000
--- a/drivers/staging/ks7010/michael_mic.h
+++ /dev/null
@@ -1,21 +0,0 @@
-/* SPDX-License-Identifier: GPL-2.0 */
-/*
- *   Driver for KeyStream wireless LAN
- *
- *   Copyright (C) 2005-2008 KeyStream Corp.
- *   Copyright (C) 2009 Renesas Technology Corp.
- */
-
-/* MichaelMIC routine define */
-struct michael_mic {
-	u32 k0;	// Key
-	u32 k1;	// Key
-	u32 l;	// Current state
-	u32 r;	// Current state
-	u8 m[4];	// Message accumulator (single word)
-	int m_bytes;	// # bytes in M
-	u8 result[8];
-};
-
-void michael_mic_function(struct michael_mic *mic, u8 *key,
-			  u8 *data, unsigned int len, u8 priority, u8 *result);
-- 
2.20.1

_______________________________________________
devel mailing list
devel@xxxxxxxxxxxxxxxxxxxxxx
http://driverdev.linuxdriverproject.org/mailman/listinfo/driverdev-devel



[Index of Archives]     [Linux Driver Backports]     [DMA Engine]     [Linux GPIO]     [Linux SPI]     [Video for Linux]     [Linux USB Devel]     [Linux Coverity]     [Linux Audio Users]     [Linux Kernel]     [Linux SCSI]     [Yosemite Backpacking]
  Powered by Linux