1/******************************************************************************
2 * rtl871x_security.c
3 *
4 * Copyright(c) 2007 - 2010 Realtek Corporation. All rights reserved.
5 * Linux device driver for RTL8192SU
6 *
7 * This program is free software; you can redistribute it and/or modify it
8 * under the terms of version 2 of the GNU General Public License as
9 * published by the Free Software Foundation.
10 *
11 * This program is distributed in the hope that it will be useful, but WITHOUT
12 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
13 * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License for
14 * more details.
15 *
16 * You should have received a copy of the GNU General Public License along with
17 * this program; if not, write to the Free Software Foundation, Inc.,
18 * 51 Franklin Street, Fifth Floor, Boston, MA 02110, USA
19 *
20 * Modifications for inclusion into the Linux staging tree are
21 * Copyright(c) 2010 Larry Finger. All rights reserved.
22 *
23 * Contact information:
24 * WLAN FAE <wlanfae@realtek.com>
25 * Larry Finger <Larry.Finger@lwfinger.net>
26 *
27 ******************************************************************************/
28
29#define  _RTL871X_SECURITY_C_
30
31#include <linux/compiler.h>
32#include <linux/kernel.h>
33#include <linux/errno.h>
34#include <linux/slab.h>
35#include <linux/module.h>
36#include <linux/kref.h>
37#include <linux/netdevice.h>
38#include <linux/skbuff.h>
39#include <linux/circ_buf.h>
40#include <linux/uaccess.h>
41#include <asm/byteorder.h>
42#include <linux/atomic.h>
43#include <linux/semaphore.h>
44
45#include "osdep_service.h"
46#include "drv_types.h"
47#include "wifi.h"
48#include "osdep_intf.h"
49
50/* =====WEP related===== */
51
52#define CRC32_POLY 0x04c11db7
53
54struct arc4context {
55	u32 x;
56	u32 y;
57	u8 state[256];
58};
59
60static void arcfour_init(struct arc4context *parc4ctx, u8 *key, u32 key_len)
61{
62	u32	t, u;
63	u32	keyindex;
64	u32	stateindex;
65	u8 *state;
66	u32	counter;
67
68	state = parc4ctx->state;
69	parc4ctx->x = 0;
70	parc4ctx->y = 0;
71	for (counter = 0; counter < 256; counter++)
72		state[counter] = (u8)counter;
73	keyindex = 0;
74	stateindex = 0;
75	for (counter = 0; counter < 256; counter++) {
76		t = state[counter];
77		stateindex = (stateindex + key[keyindex] + t) & 0xff;
78		u = state[stateindex];
79		state[stateindex] = (u8)t;
80		state[counter] = (u8)u;
81		if (++keyindex >= key_len)
82			keyindex = 0;
83	}
84}
85
86static u32 arcfour_byte(struct arc4context *parc4ctx)
87{
88	u32 x;
89	u32 y;
90	u32 sx, sy;
91	u8 *state;
92
93	state = parc4ctx->state;
94	x = (parc4ctx->x + 1) & 0xff;
95	sx = state[x];
96	y = (sx + parc4ctx->y) & 0xff;
97	sy = state[y];
98	parc4ctx->x = x;
99	parc4ctx->y = y;
100	state[y] = (u8)sx;
101	state[x] = (u8)sy;
102	return state[(sx + sy) & 0xff];
103}
104
105static void arcfour_encrypt(struct arc4context	*parc4ctx,
106		     u8 *dest, u8 *src, u32 len)
107{
108	u32 i;
109
110	for (i = 0; i < len; i++)
111		dest[i] = src[i] ^ (unsigned char)arcfour_byte(parc4ctx);
112}
113
114static sint bcrc32initialized;
115static u32 crc32_table[256];
116
117static u8 crc32_reverseBit(u8 data)
118{
119	return ((u8)(data << 7) & 0x80) | ((data << 5) & 0x40) | ((data << 3)
120		 & 0x20) | ((data << 1) & 0x10) | ((data >> 1) & 0x08) |
121		 ((data >> 3) & 0x04) | ((data >> 5) & 0x02) | ((data >> 7) &
122		 0x01);
123}
124
125static void crc32_init(void)
126{
127	if (bcrc32initialized == 1)
128		return;
129	else {
130		sint i, j;
131		u32 c;
132		u8 *p = (u8 *)&c, *p1;
133		u8 k;
134
135		c = 0x12340000;
136		for (i = 0; i < 256; ++i) {
137			k = crc32_reverseBit((u8)i);
138			for (c = ((u32)k) << 24, j = 8; j > 0; --j)
139				c = c & 0x80000000 ? (c << 1) ^ CRC32_POLY :
140				    (c << 1);
141			p1 = (u8 *)&crc32_table[i];
142			p1[0] = crc32_reverseBit(p[3]);
143			p1[1] = crc32_reverseBit(p[2]);
144			p1[2] = crc32_reverseBit(p[1]);
145			p1[3] = crc32_reverseBit(p[0]);
146		}
147		bcrc32initialized = 1;
148	}
149}
150
151static u32 getcrc32(u8 *buf, u32 len)
152{
153	u8 *p;
154	u32  crc;
155
156	if (!bcrc32initialized)
157		crc32_init();
158	crc = 0xffffffff; /* preload shift register, per CRC-32 spec */
159	for (p = buf; len > 0; ++p, --len)
160		crc = crc32_table[(crc ^ *p) & 0xff] ^ (crc >> 8);
161	return ~crc;    /* transmit complement, per CRC-32 spec */
162}
163
164/*
165	Need to consider the fragment  situation
166*/
167void r8712_wep_encrypt(struct _adapter *padapter, u8 *pxmitframe)
168{	/* exclude ICV */
169	unsigned char	crc[4];
170	struct arc4context  mycontext;
171	u32 curfragnum, length, keylength;
172	u8 *pframe, *payload, *iv;    /*,*wepkey*/
173	u8 wepkey[16];
174	struct	pkt_attrib  *pattrib = &((struct xmit_frame *)
175				       pxmitframe)->attrib;
176	struct	security_priv *psecuritypriv = &padapter->securitypriv;
177	struct	xmit_priv *pxmitpriv = &padapter->xmitpriv;
178
179	if (((struct xmit_frame *)pxmitframe)->buf_addr == NULL)
180		return;
181	pframe = ((struct xmit_frame *)pxmitframe)->buf_addr+TXDESC_OFFSET;
182	/*start to encrypt each fragment*/
183	if ((pattrib->encrypt == _WEP40_) || (pattrib->encrypt == _WEP104_)) {
184		keylength = psecuritypriv->DefKeylen[psecuritypriv->
185			    PrivacyKeyIndex];
186		for (curfragnum = 0; curfragnum < pattrib->nr_frags;
187		     curfragnum++) {
188			iv = pframe+pattrib->hdrlen;
189			memcpy(&wepkey[0], iv, 3);
190			memcpy(&wepkey[3], &psecuritypriv->DefKey[
191				psecuritypriv->PrivacyKeyIndex].skey[0],
192				keylength);
193			payload = pframe+pattrib->iv_len+pattrib->hdrlen;
194			if ((curfragnum + 1) == pattrib->nr_frags) {
195				length = pattrib->last_txcmdsz-pattrib->
196					 hdrlen-pattrib->iv_len -
197					 pattrib->icv_len;
198				*((u32 *)crc) = cpu_to_le32(getcrc32(
199						payload, length));
200				arcfour_init(&mycontext, wepkey, 3 + keylength);
201				arcfour_encrypt(&mycontext, payload, payload,
202						length);
203				arcfour_encrypt(&mycontext, payload + length,
204						crc, 4);
205			} else {
206				length = pxmitpriv->frag_len-pattrib->hdrlen -
207					 pattrib->iv_len-pattrib->icv_len;
208				*((u32 *)crc) = cpu_to_le32(getcrc32(
209						payload, length));
210				arcfour_init(&mycontext, wepkey, 3 + keylength);
211				arcfour_encrypt(&mycontext, payload, payload,
212						length);
213				arcfour_encrypt(&mycontext, payload+length,
214						crc, 4);
215				pframe += pxmitpriv->frag_len;
216				pframe = (u8 *)RND4((addr_t)(pframe));
217			}
218		}
219	}
220}
221
222void r8712_wep_decrypt(struct _adapter  *padapter, u8 *precvframe)
223{
224	/* exclude ICV */
225	u8 crc[4];
226	struct arc4context  mycontext;
227	u32 length, keylength;
228	u8 *pframe, *payload, *iv, wepkey[16];
229	u8  keyindex;
230	struct rx_pkt_attrib  *prxattrib = &(((union recv_frame *)
231					  precvframe)->u.hdr.attrib);
232	struct security_priv *psecuritypriv = &padapter->securitypriv;
233
234	pframe = (unsigned char *)((union recv_frame *)precvframe)->
235		  u.hdr.rx_data;
236	/* start to decrypt recvframe */
237	if ((prxattrib->encrypt == _WEP40_) || (prxattrib->encrypt ==
238	     _WEP104_)) {
239		iv = pframe + prxattrib->hdrlen;
240		keyindex = (iv[3] & 0x3);
241		keylength = psecuritypriv->DefKeylen[keyindex];
242		memcpy(&wepkey[0], iv, 3);
243		memcpy(&wepkey[3], &psecuritypriv->DefKey[
244			psecuritypriv->PrivacyKeyIndex].skey[0],
245			keylength);
246		length = ((union recv_frame *)precvframe)->
247			   u.hdr.len-prxattrib->hdrlen-prxattrib->iv_len;
248		payload = pframe+prxattrib->iv_len+prxattrib->hdrlen;
249		/* decrypt payload include icv */
250		arcfour_init(&mycontext, wepkey, 3 + keylength);
251		arcfour_encrypt(&mycontext, payload, payload,  length);
252		/* calculate icv and compare the icv */
253		*((u32 *)crc) = cpu_to_le32(getcrc32(payload, length - 4));
254	}
255}
256
257/* 3 =====TKIP related===== */
258
259static u32 secmicgetuint32(u8 *p)
260/* Convert from Byte[] to Us4Byte32 in a portable way */
261{
262	s32 i;
263	u32 res = 0;
264
265	for (i = 0; i < 4; i++)
266		res |= ((u32)(*p++)) << (8 * i);
267	return res;
268}
269
270static void secmicputuint32(u8 *p, u32 val)
271/* Convert from Us4Byte32 to Byte[] in a portable way */
272{
273	long i;
274
275	for (i = 0; i < 4; i++) {
276		*p++ = (u8) (val & 0xff);
277		val >>= 8;
278	}
279}
280
281static void secmicclear(struct mic_data *pmicdata)
282{
283/* Reset the state to the empty message. */
284	pmicdata->L = pmicdata->K0;
285	pmicdata->R = pmicdata->K1;
286	pmicdata->nBytesInM = 0;
287	pmicdata->M = 0;
288}
289
290void r8712_secmicsetkey(struct mic_data *pmicdata, u8 *key)
291{
292	/* Set the key */
293	pmicdata->K0 = secmicgetuint32(key);
294	pmicdata->K1 = secmicgetuint32(key + 4);
295	/* and reset the message */
296	secmicclear(pmicdata);
297}
298
299static void secmicappendbyte(struct mic_data *pmicdata, u8 b)
300{
301	/* Append the byte to our word-sized buffer */
302	pmicdata->M |= ((u32)b) << (8 * pmicdata->nBytesInM);
303	pmicdata->nBytesInM++;
304	/* Process the word if it is full. */
305	if (pmicdata->nBytesInM >= 4) {
306		pmicdata->L ^= pmicdata->M;
307		pmicdata->R ^= ROL32(pmicdata->L, 17);
308		pmicdata->L += pmicdata->R;
309		pmicdata->R ^= ((pmicdata->L & 0xff00ff00) >> 8) |
310			       ((pmicdata->L & 0x00ff00ff) << 8);
311		pmicdata->L += pmicdata->R;
312		pmicdata->R ^= ROL32(pmicdata->L, 3);
313		pmicdata->L += pmicdata->R;
314		pmicdata->R ^= ROR32(pmicdata->L, 2);
315		pmicdata->L += pmicdata->R;
316		/* Clear the buffer */
317		pmicdata->M = 0;
318		pmicdata->nBytesInM = 0;
319	}
320}
321
322void r8712_secmicappend(struct mic_data *pmicdata, u8 *src, u32 nbytes)
323{
324	/* This is simple */
325	while (nbytes > 0) {
326		secmicappendbyte(pmicdata, *src++);
327		nbytes--;
328	}
329}
330
331void r8712_secgetmic(struct mic_data *pmicdata, u8 *dst)
332{
333	/* Append the minimum padding */
334	secmicappendbyte(pmicdata, 0x5a);
335	secmicappendbyte(pmicdata, 0);
336	secmicappendbyte(pmicdata, 0);
337	secmicappendbyte(pmicdata, 0);
338	secmicappendbyte(pmicdata, 0);
339	/* and then zeroes until the length is a multiple of 4 */
340	while (pmicdata->nBytesInM != 0)
341		secmicappendbyte(pmicdata, 0);
342	/* The appendByte function has already computed the result. */
343	secmicputuint32(dst, pmicdata->L);
344	secmicputuint32(dst + 4, pmicdata->R);
345	/* Reset to the empty message. */
346	secmicclear(pmicdata);
347}
348
349void seccalctkipmic(u8 *key, u8 *header, u8 *data, u32 data_len, u8 *mic_code,
350		    u8 pri)
351{
352
353	struct mic_data	micdata;
354	u8 priority[4] = {0x0, 0x0, 0x0, 0x0};
355
356	r8712_secmicsetkey(&micdata, key);
357	priority[0] = pri;
358	/* Michael MIC pseudo header: DA, SA, 3 x 0, Priority */
359	if (header[1] & 1) {   /* ToDS==1 */
360		r8712_secmicappend(&micdata, &header[16], 6);  /* DA */
361		if (header[1] & 2)  /* From Ds==1 */
362			r8712_secmicappend(&micdata, &header[24], 6);
363		else
364			r8712_secmicappend(&micdata, &header[10], 6);
365	} else {	/* ToDS==0 */
366		r8712_secmicappend(&micdata, &header[4], 6);   /* DA */
367		if (header[1] & 2)  /* From Ds==1 */
368			r8712_secmicappend(&micdata, &header[16], 6);
369		else
370			r8712_secmicappend(&micdata, &header[10], 6);
371	}
372	r8712_secmicappend(&micdata, &priority[0], 4);
373	r8712_secmicappend(&micdata, data, data_len);
374	r8712_secgetmic(&micdata, mic_code);
375}
376
377/* macros for extraction/creation of unsigned char/unsigned short values  */
378#define RotR1(v16)   ((((v16) >> 1) & 0x7FFF) ^ (((v16) & 1) << 15))
379#define   Lo8(v16)   ((u8)((v16) & 0x00FF))
380#define   Hi8(v16)   ((u8)(((v16) >> 8) & 0x00FF))
381#define  Lo16(v32)   ((u16)((v32) & 0xFFFF))
382#define  Hi16(v32)   ((u16)(((v32) >> 16) & 0xFFFF))
383#define  Mk16(hi, lo) ((lo) ^ (((u16)(hi)) << 8))
384
385/* select the Nth 16-bit word of the temporal key unsigned char array TK[]   */
386#define  TK16(N)  Mk16(tk[2 * (N) + 1], tk[2 * (N)])
387
388/* S-box lookup: 16 bits --> 16 bits */
389#define _S_(v16)  (Sbox1[0][Lo8(v16)] ^ Sbox1[1][Hi8(v16)])
390
391/* fixed algorithm "parameters" */
392#define PHASE1_LOOP_CNT   8    /* this needs to be "big enough"     */
393#define TA_SIZE           6    /*  48-bit transmitter address       */
394#define TK_SIZE          16    /* 128-bit temporal key              */
395#define P1K_SIZE         10    /*  80-bit Phase1 key                */
396#define RC4_KEY_SIZE     16    /* 128-bit RC4KEY (104 bits unknown) */
397
398
399/* 2-unsigned char by 2-unsigned char subset of the full AES S-box table */
400static const unsigned short Sbox1[2][256] = {/* Sbox for hash (can be in ROM) */
401	{
402	0xC6A5, 0xF884, 0xEE99, 0xF68D, 0xFF0D, 0xD6BD, 0xDEB1, 0x9154,
403	0x6050, 0x0203, 0xCEA9, 0x567D, 0xE719, 0xB562, 0x4DE6, 0xEC9A,
404	0x8F45, 0x1F9D, 0x8940, 0xFA87, 0xEF15, 0xB2EB, 0x8EC9, 0xFB0B,
405	0x41EC, 0xB367, 0x5FFD, 0x45EA, 0x23BF, 0x53F7, 0xE496, 0x9B5B,
406	0x75C2, 0xE11C, 0x3DAE, 0x4C6A, 0x6C5A, 0x7E41, 0xF502, 0x834F,
407	0x685C, 0x51F4, 0xD134, 0xF908, 0xE293, 0xAB73, 0x6253, 0x2A3F,
408	0x080C, 0x9552, 0x4665, 0x9D5E, 0x3028, 0x37A1, 0x0A0F, 0x2FB5,
409	0x0E09, 0x2436, 0x1B9B, 0xDF3D, 0xCD26, 0x4E69, 0x7FCD, 0xEA9F,
410	0x121B, 0x1D9E, 0x5874, 0x342E, 0x362D, 0xDCB2, 0xB4EE, 0x5BFB,
411	0xA4F6, 0x764D, 0xB761, 0x7DCE, 0x527B, 0xDD3E, 0x5E71, 0x1397,
412	0xA6F5, 0xB968, 0x0000, 0xC12C, 0x4060, 0xE31F, 0x79C8, 0xB6ED,
413	0xD4BE, 0x8D46, 0x67D9, 0x724B, 0x94DE, 0x98D4, 0xB0E8, 0x854A,
414	0xBB6B, 0xC52A, 0x4FE5, 0xED16, 0x86C5, 0x9AD7, 0x6655, 0x1194,
415	0x8ACF, 0xE910, 0x0406, 0xFE81, 0xA0F0, 0x7844, 0x25BA, 0x4BE3,
416	0xA2F3, 0x5DFE, 0x80C0, 0x058A, 0x3FAD, 0x21BC, 0x7048, 0xF104,
417	0x63DF, 0x77C1, 0xAF75, 0x4263, 0x2030, 0xE51A, 0xFD0E, 0xBF6D,
418	0x814C, 0x1814, 0x2635, 0xC32F, 0xBEE1, 0x35A2, 0x88CC, 0x2E39,
419	0x9357, 0x55F2, 0xFC82, 0x7A47, 0xC8AC, 0xBAE7, 0x322B, 0xE695,
420	0xC0A0, 0x1998, 0x9ED1, 0xA37F, 0x4466, 0x547E, 0x3BAB, 0x0B83,
421	0x8CCA, 0xC729, 0x6BD3, 0x283C, 0xA779, 0xBCE2, 0x161D, 0xAD76,
422	0xDB3B, 0x6456, 0x744E, 0x141E, 0x92DB, 0x0C0A, 0x486C, 0xB8E4,
423	0x9F5D, 0xBD6E, 0x43EF, 0xC4A6, 0x39A8, 0x31A4, 0xD337, 0xF28B,
424	0xD532, 0x8B43, 0x6E59, 0xDAB7, 0x018C, 0xB164, 0x9CD2, 0x49E0,
425	0xD8B4, 0xACFA, 0xF307, 0xCF25, 0xCAAF, 0xF48E, 0x47E9, 0x1018,
426	0x6FD5, 0xF088, 0x4A6F, 0x5C72, 0x3824, 0x57F1, 0x73C7, 0x9751,
427	0xCB23, 0xA17C, 0xE89C, 0x3E21, 0x96DD, 0x61DC, 0x0D86, 0x0F85,
428	0xE090, 0x7C42, 0x71C4, 0xCCAA, 0x90D8, 0x0605, 0xF701, 0x1C12,
429	0xC2A3, 0x6A5F, 0xAEF9, 0x69D0, 0x1791, 0x9958, 0x3A27, 0x27B9,
430	0xD938, 0xEB13, 0x2BB3, 0x2233, 0xD2BB, 0xA970, 0x0789, 0x33A7,
431	0x2DB6, 0x3C22, 0x1592, 0xC920, 0x8749, 0xAAFF, 0x5078, 0xA57A,
432	0x038F, 0x59F8, 0x0980, 0x1A17, 0x65DA, 0xD731, 0x84C6, 0xD0B8,
433	0x82C3, 0x29B0, 0x5A77, 0x1E11, 0x7BCB, 0xA8FC, 0x6DD6, 0x2C3A,
434	},
435	{  /* second half is unsigned char-reversed version of first! */
436	0xA5C6, 0x84F8, 0x99EE, 0x8DF6, 0x0DFF, 0xBDD6, 0xB1DE, 0x5491,
437	0x5060, 0x0302, 0xA9CE, 0x7D56, 0x19E7, 0x62B5, 0xE64D, 0x9AEC,
438	0x458F, 0x9D1F, 0x4089, 0x87FA, 0x15EF, 0xEBB2, 0xC98E, 0x0BFB,
439	0xEC41, 0x67B3, 0xFD5F, 0xEA45, 0xBF23, 0xF753, 0x96E4, 0x5B9B,
440	0xC275, 0x1CE1, 0xAE3D, 0x6A4C, 0x5A6C, 0x417E, 0x02F5, 0x4F83,
441	0x5C68, 0xF451, 0x34D1, 0x08F9, 0x93E2, 0x73AB, 0x5362, 0x3F2A,
442	0x0C08, 0x5295, 0x6546, 0x5E9D, 0x2830, 0xA137, 0x0F0A, 0xB52F,
443	0x090E, 0x3624, 0x9B1B, 0x3DDF, 0x26CD, 0x694E, 0xCD7F, 0x9FEA,
444	0x1B12, 0x9E1D, 0x7458, 0x2E34, 0x2D36, 0xB2DC, 0xEEB4, 0xFB5B,
445	0xF6A4, 0x4D76, 0x61B7, 0xCE7D, 0x7B52, 0x3EDD, 0x715E, 0x9713,
446	0xF5A6, 0x68B9, 0x0000, 0x2CC1, 0x6040, 0x1FE3, 0xC879, 0xEDB6,
447	0xBED4, 0x468D, 0xD967, 0x4B72, 0xDE94, 0xD498, 0xE8B0, 0x4A85,
448	0x6BBB, 0x2AC5, 0xE54F, 0x16ED, 0xC586, 0xD79A, 0x5566, 0x9411,
449	0xCF8A, 0x10E9, 0x0604, 0x81FE, 0xF0A0, 0x4478, 0xBA25, 0xE34B,
450	0xF3A2, 0xFE5D, 0xC080, 0x8A05, 0xAD3F, 0xBC21, 0x4870, 0x04F1,
451	0xDF63, 0xC177, 0x75AF, 0x6342, 0x3020, 0x1AE5, 0x0EFD, 0x6DBF,
452	0x4C81, 0x1418, 0x3526, 0x2FC3, 0xE1BE, 0xA235, 0xCC88, 0x392E,
453	0x5793, 0xF255, 0x82FC, 0x477A, 0xACC8, 0xE7BA, 0x2B32, 0x95E6,
454	0xA0C0, 0x9819, 0xD19E, 0x7FA3, 0x6644, 0x7E54, 0xAB3B, 0x830B,
455	0xCA8C, 0x29C7, 0xD36B, 0x3C28, 0x79A7, 0xE2BC, 0x1D16, 0x76AD,
456	0x3BDB, 0x5664, 0x4E74, 0x1E14, 0xDB92, 0x0A0C, 0x6C48, 0xE4B8,
457	0x5D9F, 0x6EBD, 0xEF43, 0xA6C4, 0xA839, 0xA431, 0x37D3, 0x8BF2,
458	0x32D5, 0x438B, 0x596E, 0xB7DA, 0x8C01, 0x64B1, 0xD29C, 0xE049,
459	0xB4D8, 0xFAAC, 0x07F3, 0x25CF, 0xAFCA, 0x8EF4, 0xE947, 0x1810,
460	0xD56F, 0x88F0, 0x6F4A, 0x725C, 0x2438, 0xF157, 0xC773, 0x5197,
461	0x23CB, 0x7CA1, 0x9CE8, 0x213E, 0xDD96, 0xDC61, 0x860D, 0x850F,
462	0x90E0, 0x427C, 0xC471, 0xAACC, 0xD890, 0x0506, 0x01F7, 0x121C,
463	0xA3C2, 0x5F6A, 0xF9AE, 0xD069, 0x9117, 0x5899, 0x273A, 0xB927,
464	0x38D9, 0x13EB, 0xB32B, 0x3322, 0xBBD2, 0x70A9, 0x8907, 0xA733,
465	0xB62D, 0x223C, 0x9215, 0x20C9, 0x4987, 0xFFAA, 0x7850, 0x7AA5,
466	0x8F03, 0xF859, 0x8009, 0x171A, 0xDA65, 0x31D7, 0xC684, 0xB8D0,
467	0xC382, 0xB029, 0x775A, 0x111E, 0xCB7B, 0xFCA8, 0xD66D, 0x3A2C,
468	}
469};
470
471/*
472**********************************************************************
473* Routine: Phase 1 -- generate P1K, given TA, TK, IV32
474*
475* Inputs:
476*     tk[]      = temporal key                         [128 bits]
477*     ta[]      = transmitter's MAC address            [ 48 bits]
478*     iv32      = upper 32 bits of IV                  [ 32 bits]
479* Output:
480*     p1k[]     = Phase 1 key                          [ 80 bits]
481*
482* Note:
483*     This function only needs to be called every 2**16 packets,
484*     although in theory it could be called every packet.
485*
486**********************************************************************
487*/
488static void phase1(u16 *p1k, const u8 *tk, const u8 *ta, u32 iv32)
489{
490	sint  i;
491
492	/* Initialize the 80 bits of P1K[] from IV32 and TA[0..5]     */
493	p1k[0] = Lo16(iv32);
494	p1k[1] = Hi16(iv32);
495	p1k[2] = Mk16(ta[1], ta[0]); /* use TA[] as little-endian */
496	p1k[3] = Mk16(ta[3], ta[2]);
497	p1k[4] = Mk16(ta[5], ta[4]);
498	/* Now compute an unbalanced Feistel cipher with 80-bit block */
499	/* size on the 80-bit block P1K[], using the 128-bit key TK[] */
500	for (i = 0; i < PHASE1_LOOP_CNT; i++) {  /* Each add is mod 2**16 */
501		p1k[0] += _S_(p1k[4] ^ TK16((i&1) + 0));
502		p1k[1] += _S_(p1k[0] ^ TK16((i&1) + 2));
503		p1k[2] += _S_(p1k[1] ^ TK16((i&1) + 4));
504		p1k[3] += _S_(p1k[2] ^ TK16((i&1) + 6));
505		p1k[4] += _S_(p1k[3] ^ TK16((i&1) + 0));
506		p1k[4] +=  (unsigned short)i;	/* avoid "slide attacks" */
507	}
508}
509
510/*
511**********************************************************************
512* Routine: Phase 2 -- generate RC4KEY, given TK, P1K, IV16
513*
514* Inputs:
515*     tk[]      = Temporal key                         [128 bits]
516*     p1k[]     = Phase 1 output key                   [ 80 bits]
517*     iv16      = low 16 bits of IV counter            [ 16 bits]
518* Output:
519*     rc4key[]  = the key used to encrypt the packet   [128 bits]
520*
521* Note:
522*     The value {TA,IV32,IV16} for Phase1/Phase2 must be unique
523*     across all packets using the same key TK value. Then, for a
524*     given value of TK[], this TKIP48 construction guarantees that
525*     the final RC4KEY value is unique across all packets.
526*
527* Suggested implementation optimization: if PPK[] is "overlaid"
528*     appropriately on RC4KEY[], there is no need for the final
529*     for loop below that copies the PPK[] result into RC4KEY[].
530*
531**********************************************************************
532*/
533static void phase2(u8 *rc4key, const u8 *tk, const u16 *p1k, u16 iv16)
534{
535	sint  i;
536	u16 PPK[6];			/* temporary key for mixing    */
537
538	/* Note: all adds in the PPK[] equations below are mod 2**16 */
539	for (i = 0; i < 5; i++)
540		PPK[i] = p1k[i]; /* first, copy P1K to PPK */
541	PPK[5]  =  p1k[4] + iv16; /* next,  add in IV16 */
542	/* Bijective non-linear mixing of the 96 bits of PPK[0..5] */
543	PPK[0] += _S_(PPK[5] ^ TK16(0));   /* Mix key in each "round" */
544	PPK[1] += _S_(PPK[0] ^ TK16(1));
545	PPK[2] += _S_(PPK[1] ^ TK16(2));
546	PPK[3] += _S_(PPK[2] ^ TK16(3));
547	PPK[4] += _S_(PPK[3] ^ TK16(4));
548	PPK[5] += _S_(PPK[4] ^ TK16(5));   /* Total # S-box lookups == 6  */
549	/* Final sweep: bijective, "linear". Rotates kill LSB correlations   */
550	PPK[0] +=  RotR1(PPK[5] ^ TK16(6));
551	PPK[1] +=  RotR1(PPK[0] ^ TK16(7));   /* Use all of TK[] in Phase2   */
552	PPK[2] +=  RotR1(PPK[1]);
553	PPK[3] +=  RotR1(PPK[2]);
554	PPK[4] +=  RotR1(PPK[3]);
555	PPK[5] +=  RotR1(PPK[4]);
556	/* Note: At this point, for a given key TK[0..15], the 96-bit output */
557	/* value PPK[0..5] is guaranteed to be unique, as a function   */
558	/* of the 96-bit "input" value   {TA,IV32,IV16}. That is, P1K  */
559	/* is now a keyed permutation of {TA,IV32,IV16}. */
560	/* Set RC4KEY[0..3], which includes "cleartext" portion of RC4 key   */
561	rc4key[0] = Hi8(iv16); /* RC4KEY[0..2] is the WEP IV  */
562	rc4key[1] = (Hi8(iv16) | 0x20) & 0x7F; /* Help avoid weak (FMS) keys  */
563	rc4key[2] = Lo8(iv16);
564	rc4key[3] = Lo8((PPK[5] ^ TK16(0)) >> 1);
565	/* Copy 96 bits of PPK[0..5] to RC4KEY[4..15]  (little-endian) */
566	for (i = 0; i < 6; i++) {
567		rc4key[4 + 2 * i] = Lo8(PPK[i]);
568		rc4key[5 + 2 * i] = Hi8(PPK[i]);
569	}
570}
571
572/*The hlen isn't include the IV*/
573u32 r8712_tkip_encrypt(struct _adapter *padapter, u8 *pxmitframe)
574{	/*  exclude ICV */
575	u16 pnl;
576	u32 pnh;
577	u8 rc4key[16];
578	u8 ttkey[16];
579	u8 crc[4];
580	struct arc4context mycontext;
581	u32 curfragnum, length;
582
583	u8 *pframe, *payload, *iv, *prwskey;
584	union pn48 txpn;
585	struct sta_info *stainfo;
586	struct pkt_attrib *pattrib = &((struct xmit_frame *)pxmitframe)->attrib;
587	struct xmit_priv *pxmitpriv = &padapter->xmitpriv;
588	u32 res = _SUCCESS;
589
590	if (((struct xmit_frame *)pxmitframe)->buf_addr == NULL)
591		return _FAIL;
592
593	pframe = ((struct xmit_frame *)pxmitframe)->buf_addr+TXDESC_OFFSET;
594	/* 4 start to encrypt each fragment */
595	if (pattrib->encrypt == _TKIP_) {
596		if (pattrib->psta)
597			stainfo = pattrib->psta;
598		else
599			stainfo = r8712_get_stainfo(&padapter->stapriv,
600				  &pattrib->ra[0]);
601		if (stainfo != NULL) {
602			prwskey = &stainfo->x_UncstKey.skey[0];
603			for (curfragnum = 0; curfragnum < pattrib->nr_frags;
604			     curfragnum++) {
605				iv = pframe + pattrib->hdrlen;
606				payload = pframe+pattrib->iv_len +
607					  pattrib->hdrlen;
608				GET_TKIP_PN(iv, txpn);
609				pnl = (u16)(txpn.val);
610				pnh = (u32)(txpn.val >> 16);
611				phase1((u16 *)&ttkey[0], prwskey, &pattrib->
612				       ta[0], pnh);
613				phase2(&rc4key[0], prwskey, (u16 *)&ttkey[0],
614				       pnl);
615				if ((curfragnum + 1) == pattrib->nr_frags) {
616					/* 4 the last fragment */
617					length = pattrib->last_txcmdsz -
618					     pattrib->hdrlen-pattrib->iv_len -
619					     pattrib->icv_len;
620					*((u32 *)crc) = cpu_to_le32(
621						getcrc32(payload, length));
622					arcfour_init(&mycontext, rc4key, 16);
623					arcfour_encrypt(&mycontext, payload,
624							payload, length);
625					arcfour_encrypt(&mycontext, payload +
626							length, crc, 4);
627				} else {
628					length = pxmitpriv->frag_len-pattrib->
629						 hdrlen-pattrib->
630						 iv_len-pattrib->icv_len;
631					*((u32 *)crc) = cpu_to_le32(getcrc32(
632							payload, length));
633					arcfour_init(&mycontext, rc4key, 16);
634					arcfour_encrypt(&mycontext, payload,
635							 payload, length);
636					arcfour_encrypt(&mycontext,
637							payload+length, crc, 4);
638					pframe += pxmitpriv->frag_len;
639					pframe = (u8 *)RND4((addr_t)(pframe));
640				}
641			}
642		} else
643			res = _FAIL;
644	}
645	return res;
646}
647
648/* The hlen doesn't include the IV */
649u32 r8712_tkip_decrypt(struct _adapter *padapter, u8 *precvframe)
650{	/* exclude ICV */
651	u16 pnl;
652	u32 pnh;
653	u8 rc4key[16];
654	u8 ttkey[16];
655	u8 crc[4];
656	struct arc4context mycontext;
657	u32 length;
658	u8 *pframe, *payload, *iv, *prwskey, idx = 0;
659	union pn48 txpn;
660	struct	sta_info *stainfo;
661	struct	rx_pkt_attrib *prxattrib = &((union recv_frame *)
662					   precvframe)->u.hdr.attrib;
663	struct	security_priv	*psecuritypriv = &padapter->securitypriv;
664
665	pframe = (unsigned char *)((union recv_frame *)
666				   precvframe)->u.hdr.rx_data;
667	/* 4 start to decrypt recvframe */
668	if (prxattrib->encrypt == _TKIP_) {
669		stainfo = r8712_get_stainfo(&padapter->stapriv,
670					    &prxattrib->ta[0]);
671		if (stainfo != NULL) {
672			iv = pframe+prxattrib->hdrlen;
673			payload = pframe+prxattrib->iv_len + prxattrib->hdrlen;
674			length = ((union recv_frame *)precvframe)->
675				 u.hdr.len - prxattrib->hdrlen -
676				 prxattrib->iv_len;
677			if (IS_MCAST(prxattrib->ra)) {
678				idx = iv[3];
679				prwskey = &psecuritypriv->XGrpKey[
680					 ((idx >> 6) & 0x3) - 1].skey[0];
681				if (psecuritypriv->binstallGrpkey == false)
682					return _FAIL;
683			} else
684				prwskey = &stainfo->x_UncstKey.skey[0];
685			GET_TKIP_PN(iv, txpn);
686			pnl = (u16)(txpn.val);
687			pnh = (u32)(txpn.val >> 16);
688			phase1((u16 *)&ttkey[0], prwskey, &prxattrib->ta[0],
689				pnh);
690			phase2(&rc4key[0], prwskey, (unsigned short *)
691			       &ttkey[0], pnl);
692			/* 4 decrypt payload include icv */
693			arcfour_init(&mycontext, rc4key, 16);
694			arcfour_encrypt(&mycontext, payload, payload, length);
695			*((u32 *)crc) = cpu_to_le32(getcrc32(payload,
696					length - 4));
697			if (crc[3] != payload[length - 1] ||
698			    crc[2] != payload[length - 2] ||
699			    crc[1] != payload[length - 3] ||
700			    crc[0] != payload[length - 4])
701				return _FAIL;
702		} else
703			return _FAIL;
704	}
705	return _SUCCESS;
706}
707
708/* 3 =====AES related===== */
709
710#define MAX_MSG_SIZE	2048
711/*****************************/
712/******** SBOX Table *********/
713/*****************************/
714
715static const u8 sbox_table[256] = {
716	0x63, 0x7c, 0x77, 0x7b, 0xf2, 0x6b, 0x6f, 0xc5,
717	0x30, 0x01, 0x67, 0x2b, 0xfe, 0xd7, 0xab, 0x76,
718	0xca, 0x82, 0xc9, 0x7d, 0xfa, 0x59, 0x47, 0xf0,
719	0xad, 0xd4, 0xa2, 0xaf, 0x9c, 0xa4, 0x72, 0xc0,
720	0xb7, 0xfd, 0x93, 0x26, 0x36, 0x3f, 0xf7, 0xcc,
721	0x34, 0xa5, 0xe5, 0xf1, 0x71, 0xd8, 0x31, 0x15,
722	0x04, 0xc7, 0x23, 0xc3, 0x18, 0x96, 0x05, 0x9a,
723	0x07, 0x12, 0x80, 0xe2, 0xeb, 0x27, 0xb2, 0x75,
724	0x09, 0x83, 0x2c, 0x1a, 0x1b, 0x6e, 0x5a, 0xa0,
725	0x52, 0x3b, 0xd6, 0xb3, 0x29, 0xe3, 0x2f, 0x84,
726	0x53, 0xd1, 0x00, 0xed, 0x20, 0xfc, 0xb1, 0x5b,
727	0x6a, 0xcb, 0xbe, 0x39, 0x4a, 0x4c, 0x58, 0xcf,
728	0xd0, 0xef, 0xaa, 0xfb, 0x43, 0x4d, 0x33, 0x85,
729	0x45, 0xf9, 0x02, 0x7f, 0x50, 0x3c, 0x9f, 0xa8,
730	0x51, 0xa3, 0x40, 0x8f, 0x92, 0x9d, 0x38, 0xf5,
731	0xbc, 0xb6, 0xda, 0x21, 0x10, 0xff, 0xf3, 0xd2,
732	0xcd, 0x0c, 0x13, 0xec, 0x5f, 0x97, 0x44, 0x17,
733	0xc4, 0xa7, 0x7e, 0x3d, 0x64, 0x5d, 0x19, 0x73,
734	0x60, 0x81, 0x4f, 0xdc, 0x22, 0x2a, 0x90, 0x88,
735	0x46, 0xee, 0xb8, 0x14, 0xde, 0x5e, 0x0b, 0xdb,
736	0xe0, 0x32, 0x3a, 0x0a, 0x49, 0x06, 0x24, 0x5c,
737	0xc2, 0xd3, 0xac, 0x62, 0x91, 0x95, 0xe4, 0x79,
738	0xe7, 0xc8, 0x37, 0x6d, 0x8d, 0xd5, 0x4e, 0xa9,
739	0x6c, 0x56, 0xf4, 0xea, 0x65, 0x7a, 0xae, 0x08,
740	0xba, 0x78, 0x25, 0x2e, 0x1c, 0xa6, 0xb4, 0xc6,
741	0xe8, 0xdd, 0x74, 0x1f, 0x4b, 0xbd, 0x8b, 0x8a,
742	0x70, 0x3e, 0xb5, 0x66, 0x48, 0x03, 0xf6, 0x0e,
743	0x61, 0x35, 0x57, 0xb9, 0x86, 0xc1, 0x1d, 0x9e,
744	0xe1, 0xf8, 0x98, 0x11, 0x69, 0xd9, 0x8e, 0x94,
745	0x9b, 0x1e, 0x87, 0xe9, 0xce, 0x55, 0x28, 0xdf,
746	0x8c, 0xa1, 0x89, 0x0d, 0xbf, 0xe6, 0x42, 0x68,
747	0x41, 0x99, 0x2d, 0x0f, 0xb0, 0x54, 0xbb, 0x16
748};
749
750/****************************************/
751/* aes128k128d()                        */
752/* Performs a 128 bit AES encrypt with  */
753/* 128 bit data.                        */
754/****************************************/
755static void xor_128(u8 *a, u8 *b, u8 *out)
756{
757	sint i;
758
759	for (i = 0; i < 16; i++)
760		out[i] = a[i] ^ b[i];
761}
762
763static void xor_32(u8 *a, u8 *b, u8 *out)
764{
765	sint i;
766
767	for (i = 0; i < 4; i++)
768		out[i] = a[i] ^ b[i];
769}
770
771static u8 sbox(u8 a)
772{
773	return sbox_table[(sint)a];
774}
775
776static void next_key(u8 *key, sint round)
777{
778	u8 rcon;
779	u8 sbox_key[4];
780	u8 rcon_table[12] = {
781		0x01, 0x02, 0x04, 0x08, 0x10, 0x20, 0x40, 0x80,
782		0x1b, 0x36, 0x36, 0x36
783	};
784
785	sbox_key[0] = sbox(key[13]);
786	sbox_key[1] = sbox(key[14]);
787	sbox_key[2] = sbox(key[15]);
788	sbox_key[3] = sbox(key[12]);
789	rcon = rcon_table[round];
790	xor_32(&key[0], sbox_key, &key[0]);
791	key[0] = key[0] ^ rcon;
792	xor_32(&key[4], &key[0], &key[4]);
793	xor_32(&key[8], &key[4], &key[8]);
794	xor_32(&key[12], &key[8], &key[12]);
795}
796
797static void byte_sub(u8 *in, u8 *out)
798{
799	sint i;
800
801	for (i = 0; i < 16; i++)
802		out[i] = sbox(in[i]);
803}
804
805static void shift_row(u8 *in, u8 *out)
806{
807	out[0] =  in[0];
808	out[1] =  in[5];
809	out[2] =  in[10];
810	out[3] =  in[15];
811	out[4] =  in[4];
812	out[5] =  in[9];
813	out[6] =  in[14];
814	out[7] =  in[3];
815	out[8] =  in[8];
816	out[9] =  in[13];
817	out[10] = in[2];
818	out[11] = in[7];
819	out[12] = in[12];
820	out[13] = in[1];
821	out[14] = in[6];
822	out[15] = in[11];
823}
824
825static void mix_column(u8 *in, u8 *out)
826{
827	sint i;
828	u8 add1b[4];
829	u8 add1bf7[4];
830	u8 rotl[4];
831	u8 swap_halfs[4];
832	u8 andf7[4];
833	u8 rotr[4];
834	u8 temp[4];
835	u8 tempb[4];
836
837	for (i = 0; i < 4; i++) {
838		if ((in[i] & 0x80) == 0x80)
839			add1b[i] = 0x1b;
840		else
841			add1b[i] = 0x00;
842	}
843	swap_halfs[0] = in[2];    /* Swap halves */
844	swap_halfs[1] = in[3];
845	swap_halfs[2] = in[0];
846	swap_halfs[3] = in[1];
847	rotl[0] = in[3];        /* Rotate left 8 bits */
848	rotl[1] = in[0];
849	rotl[2] = in[1];
850	rotl[3] = in[2];
851	andf7[0] = in[0] & 0x7f;
852	andf7[1] = in[1] & 0x7f;
853	andf7[2] = in[2] & 0x7f;
854	andf7[3] = in[3] & 0x7f;
855	for (i = 3; i > 0; i--) {   /* logical shift left 1 bit */
856		andf7[i] = andf7[i] << 1;
857		if ((andf7[i-1] & 0x80) == 0x80)
858			andf7[i] = (andf7[i] | 0x01);
859	}
860	andf7[0] = andf7[0] << 1;
861	andf7[0] = andf7[0] & 0xfe;
862	xor_32(add1b, andf7, add1bf7);
863	xor_32(in, add1bf7, rotr);
864	temp[0] = rotr[0];         /* Rotate right 8 bits */
865	rotr[0] = rotr[1];
866	rotr[1] = rotr[2];
867	rotr[2] = rotr[3];
868	rotr[3] = temp[0];
869	xor_32(add1bf7, rotr, temp);
870	xor_32(swap_halfs, rotl, tempb);
871	xor_32(temp, tempb, out);
872}
873
874static void aes128k128d(u8 *key, u8 *data, u8 *ciphertext)
875{
876	sint round;
877	sint i;
878	u8 intermediatea[16];
879	u8 intermediateb[16];
880	u8 round_key[16];
881
882	for (i = 0; i < 16; i++)
883		round_key[i] = key[i];
884	for (round = 0; round < 11; round++) {
885		if (round == 0) {
886			xor_128(round_key, data, ciphertext);
887			next_key(round_key, round);
888		} else if (round == 10) {
889			byte_sub(ciphertext, intermediatea);
890			shift_row(intermediatea, intermediateb);
891			xor_128(intermediateb, round_key, ciphertext);
892		} else {   /* 1 - 9 */
893			byte_sub(ciphertext, intermediatea);
894			shift_row(intermediatea, intermediateb);
895			mix_column(&intermediateb[0], &intermediatea[0]);
896			mix_column(&intermediateb[4], &intermediatea[4]);
897			mix_column(&intermediateb[8], &intermediatea[8]);
898			mix_column(&intermediateb[12], &intermediatea[12]);
899			xor_128(intermediatea, round_key, ciphertext);
900			next_key(round_key, round);
901		}
902	}
903}
904
905/************************************************/
906/* construct_mic_iv()                           */
907/* Builds the MIC IV from header fields and PN  */
908/************************************************/
909static void construct_mic_iv(u8 *mic_iv, sint qc_exists, sint a4_exists,
910			     u8 *mpdu, uint payload_length, u8 *pn_vector)
911{
912	sint i;
913
914	mic_iv[0] = 0x59;
915	if (qc_exists && a4_exists)
916		mic_iv[1] = mpdu[30] & 0x0f;    /* QoS_TC           */
917	if (qc_exists && !a4_exists)
918		mic_iv[1] = mpdu[24] & 0x0f;   /* mute bits 7-4    */
919	if (!qc_exists)
920		mic_iv[1] = 0x00;
921	for (i = 2; i < 8; i++)
922		mic_iv[i] = mpdu[i + 8];
923	for (i = 8; i < 14; i++)
924		mic_iv[i] = pn_vector[13 - i]; /* mic_iv[8:13] = PN[5:0] */
925	mic_iv[14] = (unsigned char) (payload_length / 256);
926	mic_iv[15] = (unsigned char) (payload_length % 256);
927}
928
929/************************************************/
930/* construct_mic_header1()                      */
931/* Builds the first MIC header block from       */
932/* header fields.                               */
933/************************************************/
934static void construct_mic_header1(u8 *mic_header1, sint header_length, u8 *mpdu)
935{
936	mic_header1[0] = (u8)((header_length - 2) / 256);
937	mic_header1[1] = (u8)((header_length - 2) % 256);
938	mic_header1[2] = mpdu[0] & 0xcf;    /* Mute CF poll & CF ack bits */
939	/* Mute retry, more data and pwr mgt bits */
940	mic_header1[3] = mpdu[1] & 0xc7;
941	mic_header1[4] = mpdu[4];       /* A1 */
942	mic_header1[5] = mpdu[5];
943	mic_header1[6] = mpdu[6];
944	mic_header1[7] = mpdu[7];
945	mic_header1[8] = mpdu[8];
946	mic_header1[9] = mpdu[9];
947	mic_header1[10] = mpdu[10];     /* A2 */
948	mic_header1[11] = mpdu[11];
949	mic_header1[12] = mpdu[12];
950	mic_header1[13] = mpdu[13];
951	mic_header1[14] = mpdu[14];
952	mic_header1[15] = mpdu[15];
953}
954
955/************************************************/
956/* construct_mic_header2()                      */
957/* Builds the last MIC header block from        */
958/* header fields.                               */
959/************************************************/
960static void construct_mic_header2(u8 *mic_header2, u8 *mpdu, sint a4_exists,
961			   sint qc_exists)
962{
963	sint i;
964
965	for (i = 0; i < 16; i++)
966		mic_header2[i] = 0x00;
967	mic_header2[0] = mpdu[16];    /* A3 */
968	mic_header2[1] = mpdu[17];
969	mic_header2[2] = mpdu[18];
970	mic_header2[3] = mpdu[19];
971	mic_header2[4] = mpdu[20];
972	mic_header2[5] = mpdu[21];
973	mic_header2[6] = 0x00;
974	mic_header2[7] = 0x00; /* mpdu[23]; */
975	if (!qc_exists && a4_exists)
976		for (i = 0; i < 6; i++)
977			mic_header2[8 + i] = mpdu[24 + i];   /* A4 */
978	if (qc_exists && !a4_exists) {
979		mic_header2[8] = mpdu[24] & 0x0f; /* mute bits 15 - 4 */
980		mic_header2[9] = mpdu[25] & 0x00;
981	}
982	if (qc_exists && a4_exists) {
983		for (i = 0; i < 6; i++)
984			mic_header2[8 + i] = mpdu[24 + i];   /* A4 */
985		mic_header2[14] = mpdu[30] & 0x0f;
986		mic_header2[15] = mpdu[31] & 0x00;
987	}
988}
989
990/************************************************/
991/* construct_mic_header2()                      */
992/* Builds the last MIC header block from        */
993/* header fields.                               */
994/************************************************/
995static void construct_ctr_preload(u8 *ctr_preload, sint a4_exists, sint qc_exists,
996			   u8 *mpdu, u8 *pn_vector, sint c)
997{
998	sint i;
999
1000	for (i = 0; i < 16; i++)
1001		ctr_preload[i] = 0x00;
1002	i = 0;
1003	ctr_preload[0] = 0x01;    /* flag */
1004	if (qc_exists && a4_exists)
1005		ctr_preload[1] = mpdu[30] & 0x0f;
1006	if (qc_exists && !a4_exists)
1007		ctr_preload[1] = mpdu[24] & 0x0f;
1008	for (i = 2; i < 8; i++)
1009		ctr_preload[i] = mpdu[i + 8];
1010	for (i = 8; i < 14; i++)
1011		ctr_preload[i] = pn_vector[13 - i];
1012	ctr_preload[14] = (unsigned char) (c / 256); /* Ctr */
1013	ctr_preload[15] = (unsigned char) (c % 256);
1014}
1015
1016/************************************/
1017/* bitwise_xor()                    */
1018/* A 128 bit, bitwise exclusive or  */
1019/************************************/
1020static void bitwise_xor(u8 *ina, u8 *inb, u8 *out)
1021{
1022	sint i;
1023
1024	for (i = 0; i < 16; i++)
1025		out[i] = ina[i] ^ inb[i];
1026}
1027
1028static sint aes_cipher(u8 *key, uint	hdrlen,
1029			u8 *pframe, uint plen)
1030{
1031	uint qc_exists, a4_exists, i, j, payload_remainder;
1032	uint num_blocks, payload_index;
1033
1034	u8 pn_vector[6];
1035	u8 mic_iv[16];
1036	u8 mic_header1[16];
1037	u8 mic_header2[16];
1038	u8 ctr_preload[16];
1039
1040	/* Intermediate Buffers */
1041	u8 chain_buffer[16];
1042	u8 aes_out[16];
1043	u8 padded_buffer[16];
1044	u8 mic[8];
1045	uint	frtype  = GetFrameType(pframe);
1046	uint	frsubtype  = GetFrameSubType(pframe);
1047
1048	frsubtype >>= 4;
1049	memset((void *)mic_iv, 0, 16);
1050	memset((void *)mic_header1, 0, 16);
1051	memset((void *)mic_header2, 0, 16);
1052	memset((void *)ctr_preload, 0, 16);
1053	memset((void *)chain_buffer, 0, 16);
1054	memset((void *)aes_out, 0, 16);
1055	memset((void *)padded_buffer, 0, 16);
1056
1057	if ((hdrlen == WLAN_HDR_A3_LEN) || (hdrlen ==  WLAN_HDR_A3_QOS_LEN))
1058		a4_exists = 0;
1059	else
1060		a4_exists = 1;
1061
1062	if ((frtype == WIFI_DATA_CFACK) ||
1063	     (frtype == WIFI_DATA_CFPOLL) ||
1064	     (frtype == WIFI_DATA_CFACKPOLL)) {
1065			qc_exists = 1;
1066			if (hdrlen !=  WLAN_HDR_A3_QOS_LEN)
1067				hdrlen += 2;
1068	} else if ((frsubtype == 0x08) ||
1069		   (frsubtype == 0x09) ||
1070		   (frsubtype == 0x0a) ||
1071		   (frsubtype == 0x0b)) {
1072			if (hdrlen !=  WLAN_HDR_A3_QOS_LEN)
1073				hdrlen += 2;
1074			qc_exists = 1;
1075	} else
1076		qc_exists = 0;
1077	pn_vector[0] = pframe[hdrlen];
1078	pn_vector[1] = pframe[hdrlen+1];
1079	pn_vector[2] = pframe[hdrlen+4];
1080	pn_vector[3] = pframe[hdrlen+5];
1081	pn_vector[4] = pframe[hdrlen+6];
1082	pn_vector[5] = pframe[hdrlen+7];
1083	construct_mic_iv(mic_iv, qc_exists, a4_exists, pframe, plen, pn_vector);
1084	construct_mic_header1(mic_header1, hdrlen, pframe);
1085	construct_mic_header2(mic_header2, pframe, a4_exists, qc_exists);
1086	payload_remainder = plen % 16;
1087	num_blocks = plen / 16;
1088	/* Find start of payload */
1089	payload_index = hdrlen + 8;
1090	/* Calculate MIC */
1091	aes128k128d(key, mic_iv, aes_out);
1092	bitwise_xor(aes_out, mic_header1, chain_buffer);
1093	aes128k128d(key, chain_buffer, aes_out);
1094	bitwise_xor(aes_out, mic_header2, chain_buffer);
1095	aes128k128d(key, chain_buffer, aes_out);
1096	for (i = 0; i < num_blocks; i++) {
1097		bitwise_xor(aes_out, &pframe[payload_index], chain_buffer);
1098		payload_index += 16;
1099		aes128k128d(key, chain_buffer, aes_out);
1100	}
1101	/* Add on the final payload block if it needs padding */
1102	if (payload_remainder > 0) {
1103		for (j = 0; j < 16; j++)
1104			padded_buffer[j] = 0x00;
1105		for (j = 0; j < payload_remainder; j++)
1106			padded_buffer[j] = pframe[payload_index++];
1107		bitwise_xor(aes_out, padded_buffer, chain_buffer);
1108		aes128k128d(key, chain_buffer, aes_out);
1109	}
1110	for (j = 0; j < 8; j++)
1111		mic[j] = aes_out[j];
1112	/* Insert MIC into payload */
1113	for (j = 0; j < 8; j++)
1114		pframe[payload_index+j] = mic[j];
1115	payload_index = hdrlen + 8;
1116	for (i = 0; i < num_blocks; i++) {
1117		construct_ctr_preload(ctr_preload, a4_exists, qc_exists,
1118				      pframe, pn_vector, i + 1);
1119		aes128k128d(key, ctr_preload, aes_out);
1120		bitwise_xor(aes_out, &pframe[payload_index], chain_buffer);
1121		for (j = 0; j < 16; j++)
1122			pframe[payload_index++] = chain_buffer[j];
1123	}
1124	if (payload_remainder > 0) {  /* If short final block, then pad it,*/
1125				      /* encrypt and copy unpadded part back */
1126		construct_ctr_preload(ctr_preload, a4_exists, qc_exists,
1127				      pframe, pn_vector, num_blocks+1);
1128		for (j = 0; j < 16; j++)
1129			padded_buffer[j] = 0x00;
1130		for (j = 0; j < payload_remainder; j++)
1131			padded_buffer[j] = pframe[payload_index+j];
1132		aes128k128d(key, ctr_preload, aes_out);
1133		bitwise_xor(aes_out, padded_buffer, chain_buffer);
1134		for (j = 0; j < payload_remainder; j++)
1135			pframe[payload_index++] = chain_buffer[j];
1136	}
1137	/* Encrypt the MIC */
1138	construct_ctr_preload(ctr_preload, a4_exists, qc_exists,
1139			      pframe, pn_vector, 0);
1140	for (j = 0; j < 16; j++)
1141		padded_buffer[j] = 0x00;
1142	for (j = 0; j < 8; j++)
1143		padded_buffer[j] = pframe[j+hdrlen+8+plen];
1144	aes128k128d(key, ctr_preload, aes_out);
1145	bitwise_xor(aes_out, padded_buffer, chain_buffer);
1146	for (j = 0; j < 8; j++)
1147		pframe[payload_index++] = chain_buffer[j];
1148	return _SUCCESS;
1149}
1150
1151u32 r8712_aes_encrypt(struct _adapter *padapter, u8 *pxmitframe)
1152{	/* exclude ICV */
1153	/* Intermediate Buffers */
1154	sint	curfragnum, length;
1155	u8	*pframe, *prwskey;
1156	struct	sta_info *stainfo;
1157	struct	pkt_attrib  *pattrib = &((struct xmit_frame *)
1158				       pxmitframe)->attrib;
1159	struct	xmit_priv *pxmitpriv = &padapter->xmitpriv;
1160	u32 res = _SUCCESS;
1161
1162	if (((struct xmit_frame *)pxmitframe)->buf_addr == NULL)
1163		return _FAIL;
1164	pframe = ((struct xmit_frame *)pxmitframe)->buf_addr + TXDESC_OFFSET;
1165	/* 4 start to encrypt each fragment */
1166	if (pattrib->encrypt == _AES_) {
1167		if (pattrib->psta)
1168			stainfo = pattrib->psta;
1169		else
1170			stainfo = r8712_get_stainfo(&padapter->stapriv,
1171				  &pattrib->ra[0]);
1172		if (stainfo != NULL) {
1173			prwskey = &stainfo->x_UncstKey.skey[0];
1174			for (curfragnum = 0; curfragnum < pattrib->nr_frags;
1175			     curfragnum++) {
1176				if ((curfragnum + 1) == pattrib->nr_frags) {
1177					length = pattrib->last_txcmdsz -
1178						 pattrib->hdrlen -
1179						 pattrib->iv_len -
1180						 pattrib->icv_len;
1181					aes_cipher(prwskey, pattrib->
1182						  hdrlen, pframe, length);
1183				} else {
1184					length = pxmitpriv->frag_len -
1185						 pattrib->hdrlen -
1186						 pattrib->iv_len -
1187						 pattrib->icv_len;
1188					aes_cipher(prwskey, pattrib->
1189						   hdrlen, pframe, length);
1190					pframe += pxmitpriv->frag_len;
1191					pframe = (u8 *)RND4((addr_t)(pframe));
1192				}
1193			}
1194		} else
1195			res = _FAIL;
1196	}
1197	return res;
1198}
1199
1200static sint aes_decipher(u8 *key, uint	hdrlen,
1201			u8 *pframe, uint plen)
1202{
1203	static u8 message[MAX_MSG_SIZE];
1204	uint qc_exists, a4_exists, i, j, payload_remainder;
1205	uint num_blocks, payload_index;
1206	u8 pn_vector[6];
1207	u8 mic_iv[16];
1208	u8 mic_header1[16];
1209	u8 mic_header2[16];
1210	u8 ctr_preload[16];
1211	/* Intermediate Buffers */
1212	u8 chain_buffer[16];
1213	u8 aes_out[16];
1214	u8 padded_buffer[16];
1215	u8 mic[8];
1216	uint frtype  = GetFrameType(pframe);
1217	uint frsubtype  = GetFrameSubType(pframe);
1218
1219	frsubtype >>= 4;
1220	memset((void *)mic_iv, 0, 16);
1221	memset((void *)mic_header1, 0, 16);
1222	memset((void *)mic_header2, 0, 16);
1223	memset((void *)ctr_preload, 0, 16);
1224	memset((void *)chain_buffer, 0, 16);
1225	memset((void *)aes_out, 0, 16);
1226	memset((void *)padded_buffer, 0, 16);
1227	/* start to decrypt the payload */
1228	/*(plen including llc, payload and mic) */
1229	num_blocks = (plen - 8) / 16;
1230	payload_remainder = (plen-8) % 16;
1231	pn_vector[0] = pframe[hdrlen];
1232	pn_vector[1] = pframe[hdrlen+1];
1233	pn_vector[2] = pframe[hdrlen+4];
1234	pn_vector[3] = pframe[hdrlen+5];
1235	pn_vector[4] = pframe[hdrlen+6];
1236	pn_vector[5] = pframe[hdrlen+7];
1237	if ((hdrlen == WLAN_HDR_A3_LEN) || (hdrlen ==  WLAN_HDR_A3_QOS_LEN))
1238		a4_exists = 0;
1239	else
1240		a4_exists = 1;
1241	if ((frtype == WIFI_DATA_CFACK) ||
1242	    (frtype == WIFI_DATA_CFPOLL) ||
1243	    (frtype == WIFI_DATA_CFACKPOLL)) {
1244		qc_exists = 1;
1245		if (hdrlen != WLAN_HDR_A3_QOS_LEN)
1246			hdrlen += 2;
1247	} else if ((frsubtype == 0x08) ||
1248		   (frsubtype == 0x09) ||
1249		   (frsubtype == 0x0a) ||
1250		   (frsubtype == 0x0b)) {
1251		if (hdrlen != WLAN_HDR_A3_QOS_LEN)
1252			hdrlen += 2;
1253		qc_exists = 1;
1254	} else {
1255		qc_exists = 0;
1256	}
1257	/* now, decrypt pframe with hdrlen offset and plen long */
1258	payload_index = hdrlen + 8; /* 8 is for extiv */
1259	for (i = 0; i < num_blocks; i++) {
1260		construct_ctr_preload(ctr_preload, a4_exists, qc_exists,
1261				      pframe, pn_vector, i + 1);
1262		aes128k128d(key, ctr_preload, aes_out);
1263		bitwise_xor(aes_out, &pframe[payload_index], chain_buffer);
1264		for (j = 0; j < 16; j++)
1265			pframe[payload_index++] = chain_buffer[j];
1266	}
1267	if (payload_remainder > 0) {  /* If short final block, pad it,*/
1268		/* encrypt it and copy the unpadded part back   */
1269		construct_ctr_preload(ctr_preload, a4_exists, qc_exists,
1270				      pframe, pn_vector, num_blocks+1);
1271		for (j = 0; j < 16; j++)
1272			padded_buffer[j] = 0x00;
1273		for (j = 0; j < payload_remainder; j++)
1274			padded_buffer[j] = pframe[payload_index + j];
1275		aes128k128d(key, ctr_preload, aes_out);
1276		bitwise_xor(aes_out, padded_buffer, chain_buffer);
1277		for (j = 0; j < payload_remainder; j++)
1278			pframe[payload_index++] = chain_buffer[j];
1279	}
1280	/* start to calculate the mic */
1281	memcpy((void *)message, pframe, (hdrlen + plen + 8));
1282	pn_vector[0] = pframe[hdrlen];
1283	pn_vector[1] = pframe[hdrlen+1];
1284	pn_vector[2] = pframe[hdrlen+4];
1285	pn_vector[3] = pframe[hdrlen+5];
1286	pn_vector[4] = pframe[hdrlen+6];
1287	pn_vector[5] = pframe[hdrlen+7];
1288	construct_mic_iv(mic_iv, qc_exists, a4_exists, message, plen-8,
1289			 pn_vector);
1290	construct_mic_header1(mic_header1, hdrlen, message);
1291	construct_mic_header2(mic_header2, message, a4_exists, qc_exists);
1292	payload_remainder = (plen - 8) % 16;
1293	num_blocks = (plen - 8) / 16;
1294	/* Find start of payload */
1295	payload_index = hdrlen + 8;
1296	/* Calculate MIC */
1297	aes128k128d(key, mic_iv, aes_out);
1298	bitwise_xor(aes_out, mic_header1, chain_buffer);
1299	aes128k128d(key, chain_buffer, aes_out);
1300	bitwise_xor(aes_out, mic_header2, chain_buffer);
1301	aes128k128d(key, chain_buffer, aes_out);
1302	for (i = 0; i < num_blocks; i++) {
1303		bitwise_xor(aes_out, &message[payload_index], chain_buffer);
1304		payload_index += 16;
1305		aes128k128d(key, chain_buffer, aes_out);
1306	}
1307	/* Add on the final payload block if it needs padding */
1308	if (payload_remainder > 0) {
1309		for (j = 0; j < 16; j++)
1310			padded_buffer[j] = 0x00;
1311		for (j = 0; j < payload_remainder; j++)
1312			padded_buffer[j] = message[payload_index++];
1313		bitwise_xor(aes_out, padded_buffer, chain_buffer);
1314		aes128k128d(key, chain_buffer, aes_out);
1315	}
1316	for (j = 0; j < 8; j++)
1317		mic[j] = aes_out[j];
1318	/* Insert MIC into payload */
1319	for (j = 0; j < 8; j++)
1320		message[payload_index+j] = mic[j];
1321	payload_index = hdrlen + 8;
1322	for (i = 0; i < num_blocks; i++) {
1323		construct_ctr_preload(ctr_preload, a4_exists, qc_exists,
1324				      message, pn_vector, i + 1);
1325		aes128k128d(key, ctr_preload, aes_out);
1326		bitwise_xor(aes_out, &message[payload_index], chain_buffer);
1327		for (j = 0; j < 16; j++)
1328			message[payload_index++] = chain_buffer[j];
1329	}
1330	if (payload_remainder > 0) { /* If short final block, pad it,*/
1331				     /* encrypt and copy unpadded part back */
1332		construct_ctr_preload(ctr_preload, a4_exists, qc_exists,
1333				      message, pn_vector, num_blocks+1);
1334		for (j = 0; j < 16; j++)
1335			padded_buffer[j] = 0x00;
1336		for (j = 0; j < payload_remainder; j++)
1337			padded_buffer[j] = message[payload_index + j];
1338		aes128k128d(key, ctr_preload, aes_out);
1339		bitwise_xor(aes_out, padded_buffer, chain_buffer);
1340		for (j = 0; j < payload_remainder; j++)
1341			message[payload_index++] = chain_buffer[j];
1342	}
1343	/* Encrypt the MIC */
1344	construct_ctr_preload(ctr_preload, a4_exists, qc_exists, message,
1345			      pn_vector, 0);
1346	for (j = 0; j < 16; j++)
1347		padded_buffer[j] = 0x00;
1348	for (j = 0; j < 8; j++)
1349		padded_buffer[j] = message[j + hdrlen + plen];
1350	aes128k128d(key, ctr_preload, aes_out);
1351	bitwise_xor(aes_out, padded_buffer, chain_buffer);
1352	for (j = 0; j < 8; j++)
1353		message[payload_index++] = chain_buffer[j];
1354	/* compare the mic */
1355	return _SUCCESS;
1356}
1357
1358u32 r8712_aes_decrypt(struct _adapter *padapter, u8 *precvframe)
1359{	/* exclude ICV */
1360	/* Intermediate Buffers */
1361	sint		length;
1362	u8	*pframe, *prwskey, *iv, idx;
1363	struct	sta_info *stainfo;
1364	struct	rx_pkt_attrib *prxattrib = &((union recv_frame *)
1365					   precvframe)->u.hdr.attrib;
1366	struct	security_priv *psecuritypriv = &padapter->securitypriv;
1367
1368	pframe = (unsigned char *)((union recv_frame *)precvframe)->
1369		 u.hdr.rx_data;
1370	/* 4 start to encrypt each fragment */
1371	if (prxattrib->encrypt == _AES_) {
1372		stainfo = r8712_get_stainfo(&padapter->stapriv,
1373					    &prxattrib->ta[0]);
1374		if (stainfo != NULL) {
1375			if (IS_MCAST(prxattrib->ra)) {
1376				iv = pframe+prxattrib->hdrlen;
1377				idx = iv[3];
1378				prwskey = &psecuritypriv->XGrpKey[
1379					  ((idx >> 6) & 0x3) - 1].skey[0];
1380				if (psecuritypriv->binstallGrpkey == false)
1381					return _FAIL;
1382
1383			} else
1384				prwskey = &stainfo->x_UncstKey.skey[0];
1385			length = ((union recv_frame *)precvframe)->
1386				 u.hdr.len-prxattrib->hdrlen-prxattrib->iv_len;
1387			aes_decipher(prwskey, prxattrib->hdrlen, pframe,
1388				     length);
1389		} else
1390			return _FAIL;
1391	}
1392	return _SUCCESS;
1393}
1394
1395void r8712_use_tkipkey_handler(unsigned long data)
1396{
1397	struct _adapter *padapter = (struct _adapter *)data;
1398
1399	padapter->securitypriv.busetkipkey = true;
1400}
1401