xref: /openbmc/linux/drivers/staging/vt6655/rxtx.c (revision 160b8e75)
1 // SPDX-License-Identifier: GPL-2.0+
2 /*
3  * Copyright (c) 1996, 2003 VIA Networking Technologies, Inc.
4  * All rights reserved.
5  *
6  * File: rxtx.c
7  *
8  * Purpose: handle WMAC/802.3/802.11 rx & tx functions
9  *
10  * Author: Lyndon Chen
11  *
12  * Date: May 20, 2003
13  *
14  * Functions:
15  *      s_vGenerateTxParameter - Generate tx dma required parameter.
16  *      vGenerateMACHeader - Translate 802.3 to 802.11 header
17  *      cbGetFragCount - Calculate fragment number count
18  *      csBeacon_xmit - beacon tx function
19  *      csMgmt_xmit - management tx function
20  *      s_cbFillTxBufHead - fulfill tx dma buffer header
21  *      s_uGetDataDuration - get tx data required duration
22  *      s_uFillDataHead- fulfill tx data duration header
23  *      s_uGetRTSCTSDuration- get rtx/cts required duration
24  *      s_uGetRTSCTSRsvTime- get rts/cts reserved time
25  *      s_uGetTxRsvTime- get frame reserved time
26  *      s_vFillCTSHead- fulfill CTS ctl header
27  *      s_vFillFragParameter- Set fragment ctl parameter.
28  *      s_vFillRTSHead- fulfill RTS ctl header
29  *      s_vFillTxKey- fulfill tx encrypt key
30  *      s_vSWencryption- Software encrypt header
31  *      vDMA0_tx_80211- tx 802.11 frame via dma0
32  *      vGenerateFIFOHeader- Generate tx FIFO ctl header
33  *
34  * Revision History:
35  *
36  */
37 
38 #include "device.h"
39 #include "rxtx.h"
40 #include "card.h"
41 #include "mac.h"
42 #include "baseband.h"
43 #include "rf.h"
44 
45 /*---------------------  Static Definitions -------------------------*/
46 
47 /*---------------------  Static Classes  ----------------------------*/
48 
49 /*---------------------  Static Variables  --------------------------*/
50 
51 /*---------------------  Static Functions  --------------------------*/
52 
53 /*---------------------  Static Definitions -------------------------*/
54 /* if packet size < 256 -> in-direct send
55  * vpacket size >= 256 -> direct send
56  */
57 #define CRITICAL_PACKET_LEN      256
58 
59 static const unsigned short wTimeStampOff[2][MAX_RATE] = {
60 	{384, 288, 226, 209, 54, 43, 37, 31, 28, 25, 24, 23}, /* Long Preamble */
61 	{384, 192, 130, 113, 54, 43, 37, 31, 28, 25, 24, 23}, /* Short Preamble */
62 };
63 
64 static const unsigned short wFB_Opt0[2][5] = {
65 	{RATE_12M, RATE_18M, RATE_24M, RATE_36M, RATE_48M}, /* fallback_rate0 */
66 	{RATE_12M, RATE_12M, RATE_18M, RATE_24M, RATE_36M}, /* fallback_rate1 */
67 };
68 static const unsigned short wFB_Opt1[2][5] = {
69 	{RATE_12M, RATE_18M, RATE_24M, RATE_24M, RATE_36M}, /* fallback_rate0 */
70 	{RATE_6M,  RATE_6M,  RATE_12M, RATE_12M, RATE_18M}, /* fallback_rate1 */
71 };
72 
73 #define RTSDUR_BB       0
74 #define RTSDUR_BA       1
75 #define RTSDUR_AA       2
76 #define CTSDUR_BA       3
77 #define RTSDUR_BA_F0    4
78 #define RTSDUR_AA_F0    5
79 #define RTSDUR_BA_F1    6
80 #define RTSDUR_AA_F1    7
81 #define CTSDUR_BA_F0    8
82 #define CTSDUR_BA_F1    9
83 #define DATADUR_B       10
84 #define DATADUR_A       11
85 #define DATADUR_A_F0    12
86 #define DATADUR_A_F1    13
87 
88 /*---------------------  Static Functions  --------------------------*/
89 static
90 void
91 s_vFillRTSHead(
92 	struct vnt_private *pDevice,
93 	unsigned char byPktType,
94 	void *pvRTS,
95 	unsigned int	cbFrameLength,
96 	bool bNeedAck,
97 	bool bDisCRC,
98 	struct ieee80211_hdr *hdr,
99 	unsigned short wCurrentRate,
100 	unsigned char byFBOption
101 );
102 
103 static
104 void
105 s_vGenerateTxParameter(
106 	struct vnt_private *pDevice,
107 	unsigned char byPktType,
108 	struct vnt_tx_fifo_head *,
109 	void *pvRrvTime,
110 	void *pvRTS,
111 	void *pvCTS,
112 	unsigned int	cbFrameSize,
113 	bool bNeedACK,
114 	unsigned int	uDMAIdx,
115 	void *psEthHeader,
116 	unsigned short wCurrentRate
117 );
118 
119 static unsigned int
120 s_cbFillTxBufHead(struct vnt_private *pDevice, unsigned char byPktType,
121 		  unsigned char *pbyTxBufferAddr,
122 		  unsigned int uDMAIdx, struct vnt_tx_desc *pHeadTD,
123 		  unsigned int uNodeIndex);
124 
125 static
126 __le16
127 s_uFillDataHead(
128 	struct vnt_private *pDevice,
129 	unsigned char byPktType,
130 	void *pTxDataHead,
131 	unsigned int cbFrameLength,
132 	unsigned int uDMAIdx,
133 	bool bNeedAck,
134 	unsigned int uFragIdx,
135 	unsigned int cbLastFragmentSize,
136 	unsigned int uMACfragNum,
137 	unsigned char byFBOption,
138 	unsigned short wCurrentRate,
139 	bool is_pspoll
140 );
141 
142 /*---------------------  Export Variables  --------------------------*/
143 
144 static __le16 vnt_time_stamp_off(struct vnt_private *priv, u16 rate)
145 {
146 	return cpu_to_le16(wTimeStampOff[priv->byPreambleType % 2]
147 							[rate % MAX_RATE]);
148 }
149 
150 /* byPktType : PK_TYPE_11A     0
151  * PK_TYPE_11B     1
152  * PK_TYPE_11GB    2
153  * PK_TYPE_11GA    3
154  */
155 static
156 unsigned int
157 s_uGetTxRsvTime(
158 	struct vnt_private *pDevice,
159 	unsigned char byPktType,
160 	unsigned int cbFrameLength,
161 	unsigned short wRate,
162 	bool bNeedAck
163 )
164 {
165 	unsigned int uDataTime, uAckTime;
166 
167 	uDataTime = BBuGetFrameTime(pDevice->byPreambleType, byPktType, cbFrameLength, wRate);
168 	if (byPktType == PK_TYPE_11B) /* llb,CCK mode */
169 		uAckTime = BBuGetFrameTime(pDevice->byPreambleType, byPktType, 14, (unsigned short)pDevice->byTopCCKBasicRate);
170 	else /* 11g 2.4G OFDM mode & 11a 5G OFDM mode */
171 		uAckTime = BBuGetFrameTime(pDevice->byPreambleType, byPktType, 14, (unsigned short)pDevice->byTopOFDMBasicRate);
172 
173 	if (bNeedAck)
174 		return uDataTime + pDevice->uSIFS + uAckTime;
175 	else
176 		return uDataTime;
177 }
178 
179 static __le16 vnt_rxtx_rsvtime_le16(struct vnt_private *priv, u8 pkt_type,
180 				    u32 frame_length, u16 rate, bool need_ack)
181 {
182 	return cpu_to_le16((u16)s_uGetTxRsvTime(priv, pkt_type,
183 						frame_length, rate, need_ack));
184 }
185 
186 /* byFreqType: 0=>5GHZ 1=>2.4GHZ */
187 static
188 __le16
189 s_uGetRTSCTSRsvTime(
190 	struct vnt_private *pDevice,
191 	unsigned char byRTSRsvType,
192 	unsigned char byPktType,
193 	unsigned int cbFrameLength,
194 	unsigned short wCurrentRate
195 )
196 {
197 	unsigned int uRrvTime, uRTSTime, uCTSTime, uAckTime, uDataTime;
198 
199 	uRrvTime = uRTSTime = uCTSTime = uAckTime = uDataTime = 0;
200 
201 	uDataTime = BBuGetFrameTime(pDevice->byPreambleType, byPktType, cbFrameLength, wCurrentRate);
202 	if (byRTSRsvType == 0) { /* RTSTxRrvTime_bb */
203 		uRTSTime = BBuGetFrameTime(pDevice->byPreambleType, byPktType, 20, pDevice->byTopCCKBasicRate);
204 		uCTSTime = uAckTime = BBuGetFrameTime(pDevice->byPreambleType, byPktType, 14, pDevice->byTopCCKBasicRate);
205 	} else if (byRTSRsvType == 1) { /* RTSTxRrvTime_ba, only in 2.4GHZ */
206 		uRTSTime = BBuGetFrameTime(pDevice->byPreambleType, byPktType, 20, pDevice->byTopCCKBasicRate);
207 		uCTSTime = BBuGetFrameTime(pDevice->byPreambleType, byPktType, 14, pDevice->byTopCCKBasicRate);
208 		uAckTime = BBuGetFrameTime(pDevice->byPreambleType, byPktType, 14, pDevice->byTopOFDMBasicRate);
209 	} else if (byRTSRsvType == 2) { /* RTSTxRrvTime_aa */
210 		uRTSTime = BBuGetFrameTime(pDevice->byPreambleType, byPktType, 20, pDevice->byTopOFDMBasicRate);
211 		uCTSTime = uAckTime = BBuGetFrameTime(pDevice->byPreambleType, byPktType, 14, pDevice->byTopOFDMBasicRate);
212 	} else if (byRTSRsvType == 3) { /* CTSTxRrvTime_ba, only in 2.4GHZ */
213 		uCTSTime = BBuGetFrameTime(pDevice->byPreambleType, byPktType, 14, pDevice->byTopCCKBasicRate);
214 		uAckTime = BBuGetFrameTime(pDevice->byPreambleType, byPktType, 14, pDevice->byTopOFDMBasicRate);
215 		uRrvTime = uCTSTime + uAckTime + uDataTime + 2*pDevice->uSIFS;
216 		return cpu_to_le16((u16)uRrvTime);
217 	}
218 
219 	/* RTSRrvTime */
220 	uRrvTime = uRTSTime + uCTSTime + uAckTime + uDataTime + 3*pDevice->uSIFS;
221 	return cpu_to_le16((u16)uRrvTime);
222 }
223 
224 /* byFreqType 0: 5GHz, 1:2.4Ghz */
225 static
226 unsigned int
227 s_uGetDataDuration(
228 	struct vnt_private *pDevice,
229 	unsigned char byDurType,
230 	unsigned int cbFrameLength,
231 	unsigned char byPktType,
232 	unsigned short wRate,
233 	bool bNeedAck,
234 	unsigned int uFragIdx,
235 	unsigned int cbLastFragmentSize,
236 	unsigned int uMACfragNum,
237 	unsigned char byFBOption
238 )
239 {
240 	bool bLastFrag = false;
241 	unsigned int uAckTime = 0, uNextPktTime = 0;
242 
243 	if (uFragIdx == (uMACfragNum-1))
244 		bLastFrag = true;
245 
246 	switch (byDurType) {
247 	case DATADUR_B:    /* DATADUR_B */
248 		if (((uMACfragNum == 1)) || bLastFrag) {/* Non Frag or Last Frag */
249 			if (bNeedAck) {
250 				uAckTime = BBuGetFrameTime(pDevice->byPreambleType, byPktType, 14, pDevice->byTopCCKBasicRate);
251 				return pDevice->uSIFS + uAckTime;
252 			} else {
253 				return 0;
254 			}
255 		} else {/* First Frag or Mid Frag */
256 			if (uFragIdx == (uMACfragNum-2))
257 				uNextPktTime = s_uGetTxRsvTime(pDevice, byPktType, cbLastFragmentSize, wRate, bNeedAck);
258 			else
259 				uNextPktTime = s_uGetTxRsvTime(pDevice, byPktType, cbFrameLength, wRate, bNeedAck);
260 
261 			if (bNeedAck) {
262 				uAckTime = BBuGetFrameTime(pDevice->byPreambleType, byPktType, 14, pDevice->byTopCCKBasicRate);
263 				return pDevice->uSIFS + uAckTime + uNextPktTime;
264 			} else {
265 				return pDevice->uSIFS + uNextPktTime;
266 			}
267 		}
268 		break;
269 
270 	case DATADUR_A:    /* DATADUR_A */
271 		if (((uMACfragNum == 1)) || bLastFrag) {/* Non Frag or Last Frag */
272 			if (bNeedAck) {
273 				uAckTime = BBuGetFrameTime(pDevice->byPreambleType, byPktType, 14, pDevice->byTopOFDMBasicRate);
274 				return pDevice->uSIFS + uAckTime;
275 			} else {
276 				return 0;
277 			}
278 		} else {/* First Frag or Mid Frag */
279 			if (uFragIdx == (uMACfragNum-2))
280 				uNextPktTime = s_uGetTxRsvTime(pDevice, byPktType, cbLastFragmentSize, wRate, bNeedAck);
281 			else
282 				uNextPktTime = s_uGetTxRsvTime(pDevice, byPktType, cbFrameLength, wRate, bNeedAck);
283 
284 			if (bNeedAck) {
285 				uAckTime = BBuGetFrameTime(pDevice->byPreambleType, byPktType, 14, pDevice->byTopOFDMBasicRate);
286 				return pDevice->uSIFS + uAckTime + uNextPktTime;
287 			} else {
288 				return pDevice->uSIFS + uNextPktTime;
289 			}
290 		}
291 		break;
292 
293 	case DATADUR_A_F0:    /* DATADUR_A_F0 */
294 		if (((uMACfragNum == 1)) || bLastFrag) {/* Non Frag or Last Frag */
295 			if (bNeedAck) {
296 				uAckTime = BBuGetFrameTime(pDevice->byPreambleType, byPktType, 14, pDevice->byTopOFDMBasicRate);
297 				return pDevice->uSIFS + uAckTime;
298 			} else {
299 				return 0;
300 			}
301 		} else { /* First Frag or Mid Frag */
302 			if (byFBOption == AUTO_FB_0) {
303 				if (wRate < RATE_18M)
304 					wRate = RATE_18M;
305 				else if (wRate > RATE_54M)
306 					wRate = RATE_54M;
307 
308 				if (uFragIdx == (uMACfragNum-2))
309 					uNextPktTime = s_uGetTxRsvTime(pDevice, byPktType, cbLastFragmentSize, wFB_Opt0[FB_RATE0][wRate-RATE_18M], bNeedAck);
310 				else
311 					uNextPktTime = s_uGetTxRsvTime(pDevice, byPktType, cbFrameLength, wFB_Opt0[FB_RATE0][wRate-RATE_18M], bNeedAck);
312 
313 			} else { /* (byFBOption == AUTO_FB_1) */
314 				if (wRate < RATE_18M)
315 					wRate = RATE_18M;
316 				else if (wRate > RATE_54M)
317 					wRate = RATE_54M;
318 
319 				if (uFragIdx == (uMACfragNum-2))
320 					uNextPktTime = s_uGetTxRsvTime(pDevice, byPktType, cbLastFragmentSize, wFB_Opt1[FB_RATE0][wRate-RATE_18M], bNeedAck);
321 				else
322 					uNextPktTime = s_uGetTxRsvTime(pDevice, byPktType, cbFrameLength, wFB_Opt1[FB_RATE0][wRate-RATE_18M], bNeedAck);
323 
324 			}
325 
326 			if (bNeedAck) {
327 				uAckTime = BBuGetFrameTime(pDevice->byPreambleType, byPktType, 14, pDevice->byTopOFDMBasicRate);
328 				return pDevice->uSIFS + uAckTime + uNextPktTime;
329 			} else {
330 				return pDevice->uSIFS + uNextPktTime;
331 			}
332 		}
333 		break;
334 
335 	case DATADUR_A_F1:    /* DATADUR_A_F1 */
336 		if (((uMACfragNum == 1)) || bLastFrag) { /* Non Frag or Last Frag */
337 			if (bNeedAck) {
338 				uAckTime = BBuGetFrameTime(pDevice->byPreambleType, byPktType, 14, pDevice->byTopOFDMBasicRate);
339 				return pDevice->uSIFS + uAckTime;
340 			} else {
341 				return 0;
342 			}
343 		} else { /* First Frag or Mid Frag */
344 			if (byFBOption == AUTO_FB_0) {
345 				if (wRate < RATE_18M)
346 					wRate = RATE_18M;
347 				else if (wRate > RATE_54M)
348 					wRate = RATE_54M;
349 
350 				if (uFragIdx == (uMACfragNum-2))
351 					uNextPktTime = s_uGetTxRsvTime(pDevice, byPktType, cbLastFragmentSize, wFB_Opt0[FB_RATE1][wRate-RATE_18M], bNeedAck);
352 				else
353 					uNextPktTime = s_uGetTxRsvTime(pDevice, byPktType, cbFrameLength, wFB_Opt0[FB_RATE1][wRate-RATE_18M], bNeedAck);
354 
355 			} else { /* (byFBOption == AUTO_FB_1) */
356 				if (wRate < RATE_18M)
357 					wRate = RATE_18M;
358 				else if (wRate > RATE_54M)
359 					wRate = RATE_54M;
360 
361 				if (uFragIdx == (uMACfragNum-2))
362 					uNextPktTime = s_uGetTxRsvTime(pDevice, byPktType, cbLastFragmentSize, wFB_Opt1[FB_RATE1][wRate-RATE_18M], bNeedAck);
363 				else
364 					uNextPktTime = s_uGetTxRsvTime(pDevice, byPktType, cbFrameLength, wFB_Opt1[FB_RATE1][wRate-RATE_18M], bNeedAck);
365 			}
366 			if (bNeedAck) {
367 				uAckTime = BBuGetFrameTime(pDevice->byPreambleType, byPktType, 14, pDevice->byTopOFDMBasicRate);
368 				return pDevice->uSIFS + uAckTime + uNextPktTime;
369 			} else {
370 				return pDevice->uSIFS + uNextPktTime;
371 			}
372 		}
373 		break;
374 
375 	default:
376 		break;
377 	}
378 
379 	return 0;
380 }
381 
382 /* byFreqType: 0=>5GHZ 1=>2.4GHZ */
383 static
384 __le16
385 s_uGetRTSCTSDuration(
386 	struct vnt_private *pDevice,
387 	unsigned char byDurType,
388 	unsigned int cbFrameLength,
389 	unsigned char byPktType,
390 	unsigned short wRate,
391 	bool bNeedAck,
392 	unsigned char byFBOption
393 )
394 {
395 	unsigned int uCTSTime = 0, uDurTime = 0;
396 
397 	switch (byDurType) {
398 	case RTSDUR_BB:    /* RTSDuration_bb */
399 		uCTSTime = BBuGetFrameTime(pDevice->byPreambleType, byPktType, 14, pDevice->byTopCCKBasicRate);
400 		uDurTime = uCTSTime + 2*pDevice->uSIFS + s_uGetTxRsvTime(pDevice, byPktType, cbFrameLength, wRate, bNeedAck);
401 		break;
402 
403 	case RTSDUR_BA:    /* RTSDuration_ba */
404 		uCTSTime = BBuGetFrameTime(pDevice->byPreambleType, byPktType, 14, pDevice->byTopCCKBasicRate);
405 		uDurTime = uCTSTime + 2*pDevice->uSIFS + s_uGetTxRsvTime(pDevice, byPktType, cbFrameLength, wRate, bNeedAck);
406 		break;
407 
408 	case RTSDUR_AA:    /* RTSDuration_aa */
409 		uCTSTime = BBuGetFrameTime(pDevice->byPreambleType, byPktType, 14, pDevice->byTopOFDMBasicRate);
410 		uDurTime = uCTSTime + 2*pDevice->uSIFS + s_uGetTxRsvTime(pDevice, byPktType, cbFrameLength, wRate, bNeedAck);
411 		break;
412 
413 	case CTSDUR_BA:    /* CTSDuration_ba */
414 		uDurTime = pDevice->uSIFS + s_uGetTxRsvTime(pDevice, byPktType, cbFrameLength, wRate, bNeedAck);
415 		break;
416 
417 	case RTSDUR_BA_F0: /* RTSDuration_ba_f0 */
418 		uCTSTime = BBuGetFrameTime(pDevice->byPreambleType, byPktType, 14, pDevice->byTopCCKBasicRate);
419 		if ((byFBOption == AUTO_FB_0) && (wRate >= RATE_18M) && (wRate <= RATE_54M))
420 			uDurTime = uCTSTime + 2 * pDevice->uSIFS + s_uGetTxRsvTime(pDevice, byPktType, cbFrameLength, wFB_Opt0[FB_RATE0][wRate-RATE_18M], bNeedAck);
421 		else if ((byFBOption == AUTO_FB_1) && (wRate >= RATE_18M) && (wRate <= RATE_54M))
422 			uDurTime = uCTSTime + 2 * pDevice->uSIFS + s_uGetTxRsvTime(pDevice, byPktType, cbFrameLength, wFB_Opt1[FB_RATE0][wRate-RATE_18M], bNeedAck);
423 
424 		break;
425 
426 	case RTSDUR_AA_F0: /* RTSDuration_aa_f0 */
427 		uCTSTime = BBuGetFrameTime(pDevice->byPreambleType, byPktType, 14, pDevice->byTopOFDMBasicRate);
428 		if ((byFBOption == AUTO_FB_0) && (wRate >= RATE_18M) && (wRate <= RATE_54M))
429 			uDurTime = uCTSTime + 2*pDevice->uSIFS + s_uGetTxRsvTime(pDevice, byPktType, cbFrameLength, wFB_Opt0[FB_RATE0][wRate-RATE_18M], bNeedAck);
430 		else if ((byFBOption == AUTO_FB_1) && (wRate >= RATE_18M) && (wRate <= RATE_54M))
431 			uDurTime = uCTSTime + 2*pDevice->uSIFS + s_uGetTxRsvTime(pDevice, byPktType, cbFrameLength, wFB_Opt1[FB_RATE0][wRate-RATE_18M], bNeedAck);
432 
433 		break;
434 
435 	case RTSDUR_BA_F1: /* RTSDuration_ba_f1 */
436 		uCTSTime = BBuGetFrameTime(pDevice->byPreambleType, byPktType, 14, pDevice->byTopCCKBasicRate);
437 		if ((byFBOption == AUTO_FB_0) && (wRate >= RATE_18M) && (wRate <= RATE_54M))
438 			uDurTime = uCTSTime + 2*pDevice->uSIFS + s_uGetTxRsvTime(pDevice, byPktType, cbFrameLength, wFB_Opt0[FB_RATE1][wRate-RATE_18M], bNeedAck);
439 		else if ((byFBOption == AUTO_FB_1) && (wRate >= RATE_18M) && (wRate <= RATE_54M))
440 			uDurTime = uCTSTime + 2*pDevice->uSIFS + s_uGetTxRsvTime(pDevice, byPktType, cbFrameLength, wFB_Opt1[FB_RATE1][wRate-RATE_18M], bNeedAck);
441 
442 		break;
443 
444 	case RTSDUR_AA_F1: /* RTSDuration_aa_f1 */
445 		uCTSTime = BBuGetFrameTime(pDevice->byPreambleType, byPktType, 14, pDevice->byTopOFDMBasicRate);
446 		if ((byFBOption == AUTO_FB_0) && (wRate >= RATE_18M) && (wRate <= RATE_54M))
447 			uDurTime = uCTSTime + 2*pDevice->uSIFS + s_uGetTxRsvTime(pDevice, byPktType, cbFrameLength, wFB_Opt0[FB_RATE1][wRate-RATE_18M], bNeedAck);
448 		else if ((byFBOption == AUTO_FB_1) && (wRate >= RATE_18M) && (wRate <= RATE_54M))
449 			uDurTime = uCTSTime + 2*pDevice->uSIFS + s_uGetTxRsvTime(pDevice, byPktType, cbFrameLength, wFB_Opt1[FB_RATE1][wRate-RATE_18M], bNeedAck);
450 
451 		break;
452 
453 	case CTSDUR_BA_F0: /* CTSDuration_ba_f0 */
454 		if ((byFBOption == AUTO_FB_0) && (wRate >= RATE_18M) && (wRate <= RATE_54M))
455 			uDurTime = pDevice->uSIFS + s_uGetTxRsvTime(pDevice, byPktType, cbFrameLength, wFB_Opt0[FB_RATE0][wRate-RATE_18M], bNeedAck);
456 		else if ((byFBOption == AUTO_FB_1) && (wRate >= RATE_18M) && (wRate <= RATE_54M))
457 			uDurTime = pDevice->uSIFS + s_uGetTxRsvTime(pDevice, byPktType, cbFrameLength, wFB_Opt1[FB_RATE0][wRate-RATE_18M], bNeedAck);
458 
459 		break;
460 
461 	case CTSDUR_BA_F1: /* CTSDuration_ba_f1 */
462 		if ((byFBOption == AUTO_FB_0) && (wRate >= RATE_18M) && (wRate <= RATE_54M))
463 			uDurTime = pDevice->uSIFS + s_uGetTxRsvTime(pDevice, byPktType, cbFrameLength, wFB_Opt0[FB_RATE1][wRate-RATE_18M], bNeedAck);
464 		else if ((byFBOption == AUTO_FB_1) && (wRate >= RATE_18M) && (wRate <= RATE_54M))
465 			uDurTime = pDevice->uSIFS + s_uGetTxRsvTime(pDevice, byPktType, cbFrameLength, wFB_Opt1[FB_RATE1][wRate-RATE_18M], bNeedAck);
466 
467 		break;
468 
469 	default:
470 		break;
471 	}
472 
473 	return cpu_to_le16((u16)uDurTime);
474 }
475 
476 static
477 __le16
478 s_uFillDataHead(
479 	struct vnt_private *pDevice,
480 	unsigned char byPktType,
481 	void *pTxDataHead,
482 	unsigned int cbFrameLength,
483 	unsigned int uDMAIdx,
484 	bool bNeedAck,
485 	unsigned int uFragIdx,
486 	unsigned int cbLastFragmentSize,
487 	unsigned int uMACfragNum,
488 	unsigned char byFBOption,
489 	unsigned short wCurrentRate,
490 	bool is_pspoll
491 )
492 {
493 
494 	if (!pTxDataHead)
495 		return 0;
496 
497 
498 	if (byPktType == PK_TYPE_11GB || byPktType == PK_TYPE_11GA) {
499 		if (byFBOption == AUTO_FB_NONE) {
500 			struct vnt_tx_datahead_g *buf = pTxDataHead;
501 			/* Get SignalField, ServiceField & Length */
502 			vnt_get_phy_field(pDevice, cbFrameLength, wCurrentRate,
503 					  byPktType, &buf->a);
504 
505 			vnt_get_phy_field(pDevice, cbFrameLength,
506 					  pDevice->byTopCCKBasicRate,
507 					  PK_TYPE_11B, &buf->b);
508 
509 			if (is_pspoll) {
510 				__le16 dur = cpu_to_le16(pDevice->current_aid | BIT(14) | BIT(15));
511 
512 				buf->duration_a = dur;
513 				buf->duration_b = dur;
514 			} else {
515 				/* Get Duration and TimeStamp */
516 				buf->duration_a =
517 					cpu_to_le16((u16)s_uGetDataDuration(pDevice, DATADUR_A, cbFrameLength,
518 									    byPktType, wCurrentRate, bNeedAck, uFragIdx,
519 									    cbLastFragmentSize, uMACfragNum,
520 									    byFBOption));
521 				buf->duration_b =
522 					cpu_to_le16((u16)s_uGetDataDuration(pDevice, DATADUR_B, cbFrameLength,
523 									    PK_TYPE_11B, pDevice->byTopCCKBasicRate,
524 									    bNeedAck, uFragIdx, cbLastFragmentSize,
525 									    uMACfragNum, byFBOption));
526 			}
527 
528 			buf->time_stamp_off_a = vnt_time_stamp_off(pDevice, wCurrentRate);
529 			buf->time_stamp_off_b = vnt_time_stamp_off(pDevice, pDevice->byTopCCKBasicRate);
530 
531 			return buf->duration_a;
532 		} else {
533 			/* Auto Fallback */
534 			struct vnt_tx_datahead_g_fb *buf = pTxDataHead;
535 			/* Get SignalField, ServiceField & Length */
536 			vnt_get_phy_field(pDevice, cbFrameLength, wCurrentRate,
537 					  byPktType, &buf->a);
538 
539 			vnt_get_phy_field(pDevice, cbFrameLength,
540 					  pDevice->byTopCCKBasicRate,
541 					  PK_TYPE_11B, &buf->b);
542 			/* Get Duration and TimeStamp */
543 			buf->duration_a = cpu_to_le16((u16)s_uGetDataDuration(pDevice, DATADUR_A, cbFrameLength, byPktType,
544 									      wCurrentRate, bNeedAck, uFragIdx, cbLastFragmentSize, uMACfragNum, byFBOption));
545 			buf->duration_b = cpu_to_le16((u16)s_uGetDataDuration(pDevice, DATADUR_B, cbFrameLength, PK_TYPE_11B,
546 									       pDevice->byTopCCKBasicRate, bNeedAck, uFragIdx, cbLastFragmentSize, uMACfragNum, byFBOption));
547 			buf->duration_a_f0 = cpu_to_le16((u16)s_uGetDataDuration(pDevice, DATADUR_A_F0, cbFrameLength, byPktType,
548 										  wCurrentRate, bNeedAck, uFragIdx, cbLastFragmentSize, uMACfragNum, byFBOption));
549 			buf->duration_a_f1 = cpu_to_le16((u16)s_uGetDataDuration(pDevice, DATADUR_A_F1, cbFrameLength, byPktType,
550 										 wCurrentRate, bNeedAck, uFragIdx, cbLastFragmentSize, uMACfragNum, byFBOption));
551 
552 			buf->time_stamp_off_a = vnt_time_stamp_off(pDevice, wCurrentRate);
553 			buf->time_stamp_off_b = vnt_time_stamp_off(pDevice, pDevice->byTopCCKBasicRate);
554 
555 			return buf->duration_a;
556 		} /* if (byFBOption == AUTO_FB_NONE) */
557 	} else if (byPktType == PK_TYPE_11A) {
558 		if (byFBOption != AUTO_FB_NONE) {
559 			/* Auto Fallback */
560 			struct vnt_tx_datahead_a_fb *buf = pTxDataHead;
561 			/* Get SignalField, ServiceField & Length */
562 			vnt_get_phy_field(pDevice, cbFrameLength, wCurrentRate,
563 					  byPktType, &buf->a);
564 
565 			/* Get Duration and TimeStampOff */
566 			buf->duration = cpu_to_le16((u16)s_uGetDataDuration(pDevice, DATADUR_A, cbFrameLength, byPktType,
567 									    wCurrentRate, bNeedAck, uFragIdx, cbLastFragmentSize, uMACfragNum, byFBOption));
568 			buf->duration_f0 = cpu_to_le16((u16)s_uGetDataDuration(pDevice, DATADUR_A_F0, cbFrameLength, byPktType,
569 									       wCurrentRate, bNeedAck, uFragIdx, cbLastFragmentSize, uMACfragNum, byFBOption));
570 			buf->duration_f1 = cpu_to_le16((u16)s_uGetDataDuration(pDevice, DATADUR_A_F1, cbFrameLength, byPktType,
571 										wCurrentRate, bNeedAck, uFragIdx, cbLastFragmentSize, uMACfragNum, byFBOption));
572 			buf->time_stamp_off = vnt_time_stamp_off(pDevice, wCurrentRate);
573 			return buf->duration;
574 		} else {
575 			struct vnt_tx_datahead_ab *buf = pTxDataHead;
576 			/* Get SignalField, ServiceField & Length */
577 			vnt_get_phy_field(pDevice, cbFrameLength, wCurrentRate,
578 					  byPktType, &buf->ab);
579 
580 			if (is_pspoll) {
581 				__le16 dur = cpu_to_le16(pDevice->current_aid | BIT(14) | BIT(15));
582 
583 				buf->duration = dur;
584 			} else {
585 				/* Get Duration and TimeStampOff */
586 				buf->duration =
587 					cpu_to_le16((u16)s_uGetDataDuration(pDevice, DATADUR_A, cbFrameLength, byPktType,
588 									    wCurrentRate, bNeedAck, uFragIdx,
589 									    cbLastFragmentSize, uMACfragNum,
590 									    byFBOption));
591 			}
592 
593 			buf->time_stamp_off = vnt_time_stamp_off(pDevice, wCurrentRate);
594 			return buf->duration;
595 		}
596 	} else {
597 		struct vnt_tx_datahead_ab *buf = pTxDataHead;
598 		/* Get SignalField, ServiceField & Length */
599 		vnt_get_phy_field(pDevice, cbFrameLength, wCurrentRate,
600 				  byPktType, &buf->ab);
601 
602 		if (is_pspoll) {
603 			__le16 dur = cpu_to_le16(pDevice->current_aid | BIT(14) | BIT(15));
604 
605 			buf->duration = dur;
606 		} else {
607 			/* Get Duration and TimeStampOff */
608 			buf->duration =
609 				cpu_to_le16((u16)s_uGetDataDuration(pDevice, DATADUR_B, cbFrameLength, byPktType,
610 								    wCurrentRate, bNeedAck, uFragIdx,
611 								    cbLastFragmentSize, uMACfragNum,
612 								    byFBOption));
613 		}
614 
615 		buf->time_stamp_off = vnt_time_stamp_off(pDevice, wCurrentRate);
616 		return buf->duration;
617 	}
618 	return 0;
619 }
620 
621 
622 static
623 void
624 s_vFillRTSHead(
625 	struct vnt_private *pDevice,
626 	unsigned char byPktType,
627 	void *pvRTS,
628 	unsigned int cbFrameLength,
629 	bool bNeedAck,
630 	bool bDisCRC,
631 	struct ieee80211_hdr *hdr,
632 	unsigned short wCurrentRate,
633 	unsigned char byFBOption
634 )
635 {
636 	unsigned int uRTSFrameLen = 20;
637 
638 	if (!pvRTS)
639 		return;
640 
641 	if (bDisCRC) {
642 		/* When CRCDIS bit is on, H/W forgot to generate FCS for
643 		 * RTS frame, in this case we need to decrease its length by 4.
644 		 */
645 		uRTSFrameLen -= 4;
646 	}
647 
648 	/* Note: So far RTSHead doesn't appear in ATIM & Beacom DMA,
649 	 * so we don't need to take them into account.
650 	 * Otherwise, we need to modify codes for them.
651 	 */
652 	if (byPktType == PK_TYPE_11GB || byPktType == PK_TYPE_11GA) {
653 		if (byFBOption == AUTO_FB_NONE) {
654 			struct vnt_rts_g *buf = pvRTS;
655 			/* Get SignalField, ServiceField & Length */
656 			vnt_get_phy_field(pDevice, uRTSFrameLen,
657 					  pDevice->byTopCCKBasicRate,
658 					  PK_TYPE_11B, &buf->b);
659 
660 			vnt_get_phy_field(pDevice, uRTSFrameLen,
661 					  pDevice->byTopOFDMBasicRate,
662 					  byPktType, &buf->a);
663 			/* Get Duration */
664 			buf->duration_bb =
665 				s_uGetRTSCTSDuration(pDevice, RTSDUR_BB,
666 						     cbFrameLength, PK_TYPE_11B,
667 						     pDevice->byTopCCKBasicRate,
668 						     bNeedAck, byFBOption);
669 			buf->duration_aa =
670 				s_uGetRTSCTSDuration(pDevice, RTSDUR_AA,
671 						     cbFrameLength, byPktType,
672 						     wCurrentRate, bNeedAck,
673 						     byFBOption);
674 			buf->duration_ba =
675 				s_uGetRTSCTSDuration(pDevice, RTSDUR_BA,
676 						     cbFrameLength, byPktType,
677 						     wCurrentRate, bNeedAck,
678 						     byFBOption);
679 
680 			buf->data.duration = buf->duration_aa;
681 			/* Get RTS Frame body */
682 			buf->data.frame_control =
683 					cpu_to_le16(IEEE80211_FTYPE_CTL |
684 						    IEEE80211_STYPE_RTS);
685 
686 			ether_addr_copy(buf->data.ra, hdr->addr1);
687 			ether_addr_copy(buf->data.ta, hdr->addr2);
688 		} else {
689 			struct vnt_rts_g_fb *buf = pvRTS;
690 			/* Get SignalField, ServiceField & Length */
691 			vnt_get_phy_field(pDevice, uRTSFrameLen,
692 					  pDevice->byTopCCKBasicRate,
693 					  PK_TYPE_11B, &buf->b);
694 
695 			vnt_get_phy_field(pDevice, uRTSFrameLen,
696 					  pDevice->byTopOFDMBasicRate,
697 					  byPktType, &buf->a);
698 			/* Get Duration */
699 			buf->duration_bb =
700 				s_uGetRTSCTSDuration(pDevice, RTSDUR_BB,
701 						     cbFrameLength, PK_TYPE_11B,
702 						     pDevice->byTopCCKBasicRate,
703 						     bNeedAck, byFBOption);
704 			buf->duration_aa =
705 				s_uGetRTSCTSDuration(pDevice, RTSDUR_AA,
706 						     cbFrameLength, byPktType,
707 						     wCurrentRate, bNeedAck,
708 						     byFBOption);
709 			buf->duration_ba =
710 				s_uGetRTSCTSDuration(pDevice, RTSDUR_BA,
711 						     cbFrameLength, byPktType,
712 						     wCurrentRate, bNeedAck,
713 						     byFBOption);
714 			buf->rts_duration_ba_f0 =
715 				s_uGetRTSCTSDuration(pDevice, RTSDUR_BA_F0,
716 						     cbFrameLength, byPktType,
717 						     wCurrentRate, bNeedAck,
718 						     byFBOption);
719 			buf->rts_duration_aa_f0 =
720 				s_uGetRTSCTSDuration(pDevice, RTSDUR_AA_F0,
721 						     cbFrameLength, byPktType,
722 						     wCurrentRate, bNeedAck,
723 						     byFBOption);
724 			buf->rts_duration_ba_f1 =
725 				s_uGetRTSCTSDuration(pDevice, RTSDUR_BA_F1,
726 						     cbFrameLength, byPktType,
727 						     wCurrentRate, bNeedAck,
728 						     byFBOption);
729 			buf->rts_duration_aa_f1 =
730 				s_uGetRTSCTSDuration(pDevice, RTSDUR_AA_F1,
731 						     cbFrameLength, byPktType,
732 						     wCurrentRate, bNeedAck,
733 						     byFBOption);
734 			buf->data.duration = buf->duration_aa;
735 			/* Get RTS Frame body */
736 			buf->data.frame_control =
737 					cpu_to_le16(IEEE80211_FTYPE_CTL |
738 						    IEEE80211_STYPE_RTS);
739 
740 			ether_addr_copy(buf->data.ra, hdr->addr1);
741 			ether_addr_copy(buf->data.ta, hdr->addr2);
742 		} /* if (byFBOption == AUTO_FB_NONE) */
743 	} else if (byPktType == PK_TYPE_11A) {
744 		if (byFBOption == AUTO_FB_NONE) {
745 			struct vnt_rts_ab *buf = pvRTS;
746 			/* Get SignalField, ServiceField & Length */
747 			vnt_get_phy_field(pDevice, uRTSFrameLen,
748 					  pDevice->byTopOFDMBasicRate,
749 					  byPktType, &buf->ab);
750 			/* Get Duration */
751 			buf->duration =
752 				s_uGetRTSCTSDuration(pDevice, RTSDUR_AA,
753 						     cbFrameLength, byPktType,
754 						     wCurrentRate, bNeedAck,
755 						     byFBOption);
756 			buf->data.duration = buf->duration;
757 			/* Get RTS Frame body */
758 			buf->data.frame_control =
759 					cpu_to_le16(IEEE80211_FTYPE_CTL |
760 						    IEEE80211_STYPE_RTS);
761 
762 			ether_addr_copy(buf->data.ra, hdr->addr1);
763 			ether_addr_copy(buf->data.ta, hdr->addr2);
764 		} else {
765 			struct vnt_rts_a_fb *buf = pvRTS;
766 			/* Get SignalField, ServiceField & Length */
767 			vnt_get_phy_field(pDevice, uRTSFrameLen,
768 					  pDevice->byTopOFDMBasicRate,
769 					  byPktType, &buf->a);
770 			/* Get Duration */
771 			buf->duration =
772 				s_uGetRTSCTSDuration(pDevice, RTSDUR_AA,
773 						     cbFrameLength, byPktType,
774 						     wCurrentRate, bNeedAck,
775 						     byFBOption);
776 			buf->rts_duration_f0 =
777 				s_uGetRTSCTSDuration(pDevice, RTSDUR_AA_F0,
778 						     cbFrameLength, byPktType,
779 						     wCurrentRate, bNeedAck,
780 						     byFBOption);
781 			buf->rts_duration_f1 =
782 				s_uGetRTSCTSDuration(pDevice, RTSDUR_AA_F1,
783 						     cbFrameLength, byPktType,
784 						     wCurrentRate, bNeedAck,
785 						     byFBOption);
786 			buf->data.duration = buf->duration;
787 			/* Get RTS Frame body */
788 			buf->data.frame_control =
789 					cpu_to_le16(IEEE80211_FTYPE_CTL |
790 						    IEEE80211_STYPE_RTS);
791 
792 			ether_addr_copy(buf->data.ra, hdr->addr1);
793 			ether_addr_copy(buf->data.ta, hdr->addr2);
794 		}
795 	} else if (byPktType == PK_TYPE_11B) {
796 		struct vnt_rts_ab *buf = pvRTS;
797 		/* Get SignalField, ServiceField & Length */
798 		vnt_get_phy_field(pDevice, uRTSFrameLen,
799 				  pDevice->byTopCCKBasicRate,
800 				  PK_TYPE_11B, &buf->ab);
801 		/* Get Duration */
802 		buf->duration =
803 			s_uGetRTSCTSDuration(pDevice, RTSDUR_BB, cbFrameLength,
804 					     byPktType, wCurrentRate, bNeedAck,
805 					     byFBOption);
806 
807 		buf->data.duration = buf->duration;
808 		/* Get RTS Frame body */
809 		buf->data.frame_control =
810 			cpu_to_le16(IEEE80211_FTYPE_CTL | IEEE80211_STYPE_RTS);
811 
812 		ether_addr_copy(buf->data.ra, hdr->addr1);
813 		ether_addr_copy(buf->data.ta, hdr->addr2);
814 	}
815 }
816 
817 static
818 void
819 s_vFillCTSHead(
820 	struct vnt_private *pDevice,
821 	unsigned int uDMAIdx,
822 	unsigned char byPktType,
823 	void *pvCTS,
824 	unsigned int cbFrameLength,
825 	bool bNeedAck,
826 	bool bDisCRC,
827 	unsigned short wCurrentRate,
828 	unsigned char byFBOption
829 )
830 {
831 	unsigned int uCTSFrameLen = 14;
832 
833 	if (!pvCTS)
834 		return;
835 
836 	if (bDisCRC) {
837 		/* When CRCDIS bit is on, H/W forgot to generate FCS for
838 		 * CTS frame, in this case we need to decrease its length by 4.
839 		 */
840 		uCTSFrameLen -= 4;
841 	}
842 
843 	if (byPktType == PK_TYPE_11GB || byPktType == PK_TYPE_11GA) {
844 		if (byFBOption != AUTO_FB_NONE && uDMAIdx != TYPE_ATIMDMA && uDMAIdx != TYPE_BEACONDMA) {
845 			/* Auto Fall back */
846 			struct vnt_cts_fb *buf = pvCTS;
847 			/* Get SignalField, ServiceField & Length */
848 			vnt_get_phy_field(pDevice, uCTSFrameLen,
849 					  pDevice->byTopCCKBasicRate,
850 					  PK_TYPE_11B, &buf->b);
851 
852 			buf->duration_ba =
853 				s_uGetRTSCTSDuration(pDevice, CTSDUR_BA,
854 						     cbFrameLength, byPktType,
855 						     wCurrentRate, bNeedAck,
856 						     byFBOption);
857 
858 			/* Get CTSDuration_ba_f0 */
859 			buf->cts_duration_ba_f0 =
860 				s_uGetRTSCTSDuration(pDevice, CTSDUR_BA_F0,
861 						     cbFrameLength, byPktType,
862 						     wCurrentRate, bNeedAck,
863 						     byFBOption);
864 
865 			/* Get CTSDuration_ba_f1 */
866 			buf->cts_duration_ba_f1 =
867 				s_uGetRTSCTSDuration(pDevice, CTSDUR_BA_F1,
868 						     cbFrameLength, byPktType,
869 						     wCurrentRate, bNeedAck,
870 						     byFBOption);
871 
872 			/* Get CTS Frame body */
873 			buf->data.duration = buf->duration_ba;
874 
875 			buf->data.frame_control =
876 				cpu_to_le16(IEEE80211_FTYPE_CTL |
877 					    IEEE80211_STYPE_CTS);
878 
879 			buf->reserved2 = 0x0;
880 
881 			ether_addr_copy(buf->data.ra,
882 					pDevice->abyCurrentNetAddr);
883 		} else { /* if (byFBOption != AUTO_FB_NONE && uDMAIdx != TYPE_ATIMDMA && uDMAIdx != TYPE_BEACONDMA) */
884 			struct vnt_cts *buf = pvCTS;
885 			/* Get SignalField, ServiceField & Length */
886 			vnt_get_phy_field(pDevice, uCTSFrameLen,
887 					  pDevice->byTopCCKBasicRate,
888 					  PK_TYPE_11B, &buf->b);
889 
890 			/* Get CTSDuration_ba */
891 			buf->duration_ba =
892 				s_uGetRTSCTSDuration(pDevice, CTSDUR_BA,
893 						     cbFrameLength, byPktType,
894 						     wCurrentRate, bNeedAck,
895 						     byFBOption);
896 
897 			/* Get CTS Frame body */
898 			buf->data.duration = buf->duration_ba;
899 
900 			buf->data.frame_control =
901 				cpu_to_le16(IEEE80211_FTYPE_CTL |
902 					    IEEE80211_STYPE_CTS);
903 
904 			buf->reserved2 = 0x0;
905 			ether_addr_copy(buf->data.ra,
906 					pDevice->abyCurrentNetAddr);
907 		}
908 	}
909 }
910 
911 /*
912  *
913  * Description:
914  *      Generate FIFO control for MAC & Baseband controller
915  *
916  * Parameters:
917  *  In:
918  *      pDevice         - Pointer to adapter
919  *      pTxDataHead     - Transmit Data Buffer
920  *      pTxBufHead      - pTxBufHead
921  *      pvRrvTime        - pvRrvTime
922  *      pvRTS            - RTS Buffer
923  *      pCTS            - CTS Buffer
924  *      cbFrameSize     - Transmit Data Length (Hdr+Payload+FCS)
925  *      bNeedACK        - If need ACK
926  *      uDescIdx        - Desc Index
927  *  Out:
928  *      none
929  *
930  * Return Value: none
931  *
932  -
933  * unsigned int cbFrameSize, Hdr+Payload+FCS
934  */
935 static
936 void
937 s_vGenerateTxParameter(
938 	struct vnt_private *pDevice,
939 	unsigned char byPktType,
940 	struct vnt_tx_fifo_head *tx_buffer_head,
941 	void *pvRrvTime,
942 	void *pvRTS,
943 	void *pvCTS,
944 	unsigned int cbFrameSize,
945 	bool bNeedACK,
946 	unsigned int uDMAIdx,
947 	void *psEthHeader,
948 	unsigned short wCurrentRate
949 )
950 {
951 	u16 fifo_ctl = le16_to_cpu(tx_buffer_head->fifo_ctl);
952 	bool bDisCRC = false;
953 	unsigned char byFBOption = AUTO_FB_NONE;
954 
955 	tx_buffer_head->current_rate = cpu_to_le16(wCurrentRate);
956 
957 	if (fifo_ctl & FIFOCTL_CRCDIS)
958 		bDisCRC = true;
959 
960 	if (fifo_ctl & FIFOCTL_AUTO_FB_0)
961 		byFBOption = AUTO_FB_0;
962 	else if (fifo_ctl & FIFOCTL_AUTO_FB_1)
963 		byFBOption = AUTO_FB_1;
964 
965 	if (!pvRrvTime)
966 		return;
967 
968 	if (byPktType == PK_TYPE_11GB || byPktType == PK_TYPE_11GA) {
969 		if (pvRTS != NULL) { /* RTS_need */
970 			/* Fill RsvTime */
971 			struct vnt_rrv_time_rts *buf = pvRrvTime;
972 
973 			buf->rts_rrv_time_aa = s_uGetRTSCTSRsvTime(pDevice, 2, byPktType, cbFrameSize, wCurrentRate);
974 			buf->rts_rrv_time_ba = s_uGetRTSCTSRsvTime(pDevice, 1, byPktType, cbFrameSize, wCurrentRate);
975 			buf->rts_rrv_time_bb = s_uGetRTSCTSRsvTime(pDevice, 0, byPktType, cbFrameSize, wCurrentRate);
976 			buf->rrv_time_a = vnt_rxtx_rsvtime_le16(pDevice, byPktType, cbFrameSize, wCurrentRate, bNeedACK);
977 			buf->rrv_time_b = vnt_rxtx_rsvtime_le16(pDevice, PK_TYPE_11B, cbFrameSize, pDevice->byTopCCKBasicRate, bNeedACK);
978 
979 			s_vFillRTSHead(pDevice, byPktType, pvRTS, cbFrameSize, bNeedACK, bDisCRC, psEthHeader, wCurrentRate, byFBOption);
980 		} else {/* RTS_needless, PCF mode */
981 			struct vnt_rrv_time_cts *buf = pvRrvTime;
982 
983 			buf->rrv_time_a = vnt_rxtx_rsvtime_le16(pDevice, byPktType, cbFrameSize, wCurrentRate, bNeedACK);
984 			buf->rrv_time_b = vnt_rxtx_rsvtime_le16(pDevice, PK_TYPE_11B, cbFrameSize, pDevice->byTopCCKBasicRate, bNeedACK);
985 			buf->cts_rrv_time_ba = s_uGetRTSCTSRsvTime(pDevice, 3, byPktType, cbFrameSize, wCurrentRate);
986 
987 			/* Fill CTS */
988 			s_vFillCTSHead(pDevice, uDMAIdx, byPktType, pvCTS, cbFrameSize, bNeedACK, bDisCRC, wCurrentRate, byFBOption);
989 		}
990 	} else if (byPktType == PK_TYPE_11A) {
991 		if (pvRTS != NULL) {/* RTS_need, non PCF mode */
992 			struct vnt_rrv_time_ab *buf = pvRrvTime;
993 
994 			buf->rts_rrv_time = s_uGetRTSCTSRsvTime(pDevice, 2, byPktType, cbFrameSize, wCurrentRate);
995 			buf->rrv_time = vnt_rxtx_rsvtime_le16(pDevice, byPktType, cbFrameSize, wCurrentRate, bNeedACK);
996 
997 			/* Fill RTS */
998 			s_vFillRTSHead(pDevice, byPktType, pvRTS, cbFrameSize, bNeedACK, bDisCRC, psEthHeader, wCurrentRate, byFBOption);
999 		} else if (!pvRTS) {/* RTS_needless, non PCF mode */
1000 			struct vnt_rrv_time_ab *buf = pvRrvTime;
1001 
1002 			buf->rrv_time = vnt_rxtx_rsvtime_le16(pDevice, PK_TYPE_11A, cbFrameSize, wCurrentRate, bNeedACK);
1003 		}
1004 	} else if (byPktType == PK_TYPE_11B) {
1005 		if (pvRTS != NULL) {/* RTS_need, non PCF mode */
1006 			struct vnt_rrv_time_ab *buf = pvRrvTime;
1007 
1008 			buf->rts_rrv_time = s_uGetRTSCTSRsvTime(pDevice, 0, byPktType, cbFrameSize, wCurrentRate);
1009 			buf->rrv_time = vnt_rxtx_rsvtime_le16(pDevice, PK_TYPE_11B, cbFrameSize, wCurrentRate, bNeedACK);
1010 
1011 			/* Fill RTS */
1012 			s_vFillRTSHead(pDevice, byPktType, pvRTS, cbFrameSize, bNeedACK, bDisCRC, psEthHeader, wCurrentRate, byFBOption);
1013 		} else { /* RTS_needless, non PCF mode */
1014 			struct vnt_rrv_time_ab *buf = pvRrvTime;
1015 
1016 			buf->rrv_time = vnt_rxtx_rsvtime_le16(pDevice, PK_TYPE_11B, cbFrameSize, wCurrentRate, bNeedACK);
1017 		}
1018 	}
1019 }
1020 
1021 static unsigned int
1022 s_cbFillTxBufHead(struct vnt_private *pDevice, unsigned char byPktType,
1023 		  unsigned char *pbyTxBufferAddr,
1024 		  unsigned int uDMAIdx, struct vnt_tx_desc *pHeadTD,
1025 		  unsigned int is_pspoll)
1026 {
1027 	struct vnt_td_info *td_info = pHeadTD->td_info;
1028 	struct sk_buff *skb = td_info->skb;
1029 	struct ieee80211_tx_info *info = IEEE80211_SKB_CB(skb);
1030 	struct ieee80211_hdr *hdr = (struct ieee80211_hdr *)skb->data;
1031 	struct vnt_tx_fifo_head *tx_buffer_head =
1032 			(struct vnt_tx_fifo_head *)td_info->buf;
1033 	u16 fifo_ctl = le16_to_cpu(tx_buffer_head->fifo_ctl);
1034 	unsigned int cbFrameSize;
1035 	__le16 uDuration;
1036 	unsigned char *pbyBuffer;
1037 	unsigned int uLength = 0;
1038 	unsigned int cbMICHDR = 0;
1039 	unsigned int uMACfragNum = 1;
1040 	unsigned int uPadding = 0;
1041 	unsigned int cbReqCount = 0;
1042 	bool bNeedACK = (bool)(fifo_ctl & FIFOCTL_NEEDACK);
1043 	bool bRTS = (bool)(fifo_ctl & FIFOCTL_RTS);
1044 	struct vnt_tx_desc *ptdCurr;
1045 	unsigned int cbHeaderLength = 0;
1046 	void *pvRrvTime;
1047 	struct vnt_mic_hdr *pMICHDR;
1048 	void *pvRTS;
1049 	void *pvCTS;
1050 	void *pvTxDataHd;
1051 	unsigned short wTxBufSize;   /* FFinfo size */
1052 	unsigned char byFBOption = AUTO_FB_NONE;
1053 
1054 	pvRrvTime = pMICHDR = pvRTS = pvCTS = pvTxDataHd = NULL;
1055 
1056 	cbFrameSize = skb->len + 4;
1057 
1058 	if (info->control.hw_key) {
1059 		switch (info->control.hw_key->cipher) {
1060 		case WLAN_CIPHER_SUITE_CCMP:
1061 			cbMICHDR = sizeof(struct vnt_mic_hdr);
1062 		default:
1063 			break;
1064 		}
1065 
1066 		cbFrameSize += info->control.hw_key->icv_len;
1067 
1068 		if (pDevice->byLocalID > REV_ID_VT3253_A1) {
1069 			/* MAC Header should be padding 0 to DW alignment. */
1070 			uPadding = 4 - (ieee80211_get_hdrlen_from_skb(skb) % 4);
1071 			uPadding %= 4;
1072 		}
1073 	}
1074 
1075 	/*
1076 	 * Use for AUTO FALL BACK
1077 	 */
1078 	if (fifo_ctl & FIFOCTL_AUTO_FB_0)
1079 		byFBOption = AUTO_FB_0;
1080 	else if (fifo_ctl & FIFOCTL_AUTO_FB_1)
1081 		byFBOption = AUTO_FB_1;
1082 
1083 
1084 	/* Set RrvTime/RTS/CTS Buffer */
1085 	wTxBufSize = sizeof(struct vnt_tx_fifo_head);
1086 	if (byPktType == PK_TYPE_11GB || byPktType == PK_TYPE_11GA) {/* 802.11g packet */
1087 
1088 		if (byFBOption == AUTO_FB_NONE) {
1089 			if (bRTS) {/* RTS_need */
1090 				pvRrvTime = (void *)(pbyTxBufferAddr + wTxBufSize);
1091 				pMICHDR = (struct vnt_mic_hdr *)(pbyTxBufferAddr + wTxBufSize + sizeof(struct vnt_rrv_time_rts));
1092 				pvRTS = (void *)(pbyTxBufferAddr + wTxBufSize + sizeof(struct vnt_rrv_time_rts) + cbMICHDR);
1093 				pvCTS = NULL;
1094 				pvTxDataHd = (void *)(pbyTxBufferAddr + wTxBufSize + sizeof(struct vnt_rrv_time_rts) +
1095 							cbMICHDR + sizeof(struct vnt_rts_g));
1096 				cbHeaderLength = wTxBufSize + sizeof(struct vnt_rrv_time_rts) +
1097 							cbMICHDR + sizeof(struct vnt_rts_g) +
1098 							sizeof(struct vnt_tx_datahead_g);
1099 			} else { /* RTS_needless */
1100 				pvRrvTime = (void *)(pbyTxBufferAddr + wTxBufSize);
1101 				pMICHDR = (struct vnt_mic_hdr *) (pbyTxBufferAddr + wTxBufSize + sizeof(struct vnt_rrv_time_cts));
1102 				pvRTS = NULL;
1103 				pvCTS = (void *) (pbyTxBufferAddr + wTxBufSize + sizeof(struct vnt_rrv_time_cts) + cbMICHDR);
1104 				pvTxDataHd = (void *)(pbyTxBufferAddr + wTxBufSize +
1105 						sizeof(struct vnt_rrv_time_cts) + cbMICHDR + sizeof(struct vnt_cts));
1106 				cbHeaderLength = wTxBufSize + sizeof(struct vnt_rrv_time_cts) +
1107 							cbMICHDR + sizeof(struct vnt_cts) + sizeof(struct vnt_tx_datahead_g);
1108 			}
1109 		} else {
1110 			/* Auto Fall Back */
1111 			if (bRTS) {/* RTS_need */
1112 				pvRrvTime = (void *)(pbyTxBufferAddr + wTxBufSize);
1113 				pMICHDR = (struct vnt_mic_hdr *) (pbyTxBufferAddr + wTxBufSize + sizeof(struct vnt_rrv_time_rts));
1114 				pvRTS = (void *) (pbyTxBufferAddr + wTxBufSize + sizeof(struct vnt_rrv_time_rts) + cbMICHDR);
1115 				pvCTS = NULL;
1116 				pvTxDataHd = (void *)(pbyTxBufferAddr + wTxBufSize + sizeof(struct vnt_rrv_time_rts) +
1117 					cbMICHDR + sizeof(struct vnt_rts_g_fb));
1118 				cbHeaderLength = wTxBufSize + sizeof(struct vnt_rrv_time_rts) +
1119 					cbMICHDR + sizeof(struct vnt_rts_g_fb) + sizeof(struct vnt_tx_datahead_g_fb);
1120 			} else { /* RTS_needless */
1121 				pvRrvTime = (void *)(pbyTxBufferAddr + wTxBufSize);
1122 				pMICHDR = (struct vnt_mic_hdr *) (pbyTxBufferAddr + wTxBufSize + sizeof(struct vnt_rrv_time_cts));
1123 				pvRTS = NULL;
1124 				pvCTS = (void *)(pbyTxBufferAddr + wTxBufSize + sizeof(struct vnt_rrv_time_cts) + cbMICHDR);
1125 				pvTxDataHd = (void  *)(pbyTxBufferAddr + wTxBufSize + sizeof(struct vnt_rrv_time_cts) +
1126 					cbMICHDR + sizeof(struct vnt_cts_fb));
1127 				cbHeaderLength = wTxBufSize + sizeof(struct vnt_rrv_time_cts) +
1128 					cbMICHDR + sizeof(struct vnt_cts_fb) + sizeof(struct vnt_tx_datahead_g_fb);
1129 			}
1130 		} /* Auto Fall Back */
1131 	} else {/* 802.11a/b packet */
1132 
1133 		if (byFBOption == AUTO_FB_NONE) {
1134 			if (bRTS) {
1135 				pvRrvTime = (void *)(pbyTxBufferAddr + wTxBufSize);
1136 				pMICHDR = (struct vnt_mic_hdr *) (pbyTxBufferAddr + wTxBufSize + sizeof(struct vnt_rrv_time_ab));
1137 				pvRTS = (void *)(pbyTxBufferAddr + wTxBufSize + sizeof(struct vnt_rrv_time_ab) + cbMICHDR);
1138 				pvCTS = NULL;
1139 				pvTxDataHd = (void *)(pbyTxBufferAddr + wTxBufSize +
1140 					sizeof(struct vnt_rrv_time_ab) + cbMICHDR + sizeof(struct vnt_rts_ab));
1141 				cbHeaderLength = wTxBufSize + sizeof(struct vnt_rrv_time_ab) +
1142 					cbMICHDR + sizeof(struct vnt_rts_ab) + sizeof(struct vnt_tx_datahead_ab);
1143 			} else { /* RTS_needless, need MICHDR */
1144 				pvRrvTime = (void *)(pbyTxBufferAddr + wTxBufSize);
1145 				pMICHDR = (struct vnt_mic_hdr *) (pbyTxBufferAddr + wTxBufSize + sizeof(struct vnt_rrv_time_ab));
1146 				pvRTS = NULL;
1147 				pvCTS = NULL;
1148 				pvTxDataHd = (void *)(pbyTxBufferAddr + wTxBufSize + sizeof(struct vnt_rrv_time_ab) + cbMICHDR);
1149 				cbHeaderLength = wTxBufSize + sizeof(struct vnt_rrv_time_ab) +
1150 					cbMICHDR + sizeof(struct vnt_tx_datahead_ab);
1151 			}
1152 		} else {
1153 			/* Auto Fall Back */
1154 			if (bRTS) { /* RTS_need */
1155 				pvRrvTime = (void *)(pbyTxBufferAddr + wTxBufSize);
1156 				pMICHDR = (struct vnt_mic_hdr *) (pbyTxBufferAddr + wTxBufSize + sizeof(struct vnt_rrv_time_ab));
1157 				pvRTS = (void *)(pbyTxBufferAddr + wTxBufSize + sizeof(struct vnt_rrv_time_ab) + cbMICHDR);
1158 				pvCTS = NULL;
1159 				pvTxDataHd = (void *)(pbyTxBufferAddr + wTxBufSize +
1160 					sizeof(struct vnt_rrv_time_ab) + cbMICHDR + sizeof(struct vnt_rts_a_fb));
1161 				cbHeaderLength = wTxBufSize + sizeof(struct vnt_rrv_time_ab) +
1162 					cbMICHDR + sizeof(struct vnt_rts_a_fb) + sizeof(struct vnt_tx_datahead_a_fb);
1163 			} else { /* RTS_needless */
1164 				pvRrvTime = (void *)(pbyTxBufferAddr + wTxBufSize);
1165 				pMICHDR = (struct vnt_mic_hdr *)(pbyTxBufferAddr + wTxBufSize + sizeof(struct vnt_rrv_time_ab));
1166 				pvRTS = NULL;
1167 				pvCTS = NULL;
1168 				pvTxDataHd = (void *)(pbyTxBufferAddr + wTxBufSize + sizeof(struct vnt_rrv_time_ab) + cbMICHDR);
1169 				cbHeaderLength = wTxBufSize + sizeof(struct vnt_rrv_time_ab) +
1170 					cbMICHDR + sizeof(struct vnt_tx_datahead_a_fb);
1171 			}
1172 		} /* Auto Fall Back */
1173 	}
1174 
1175 	td_info->mic_hdr = pMICHDR;
1176 
1177 	memset((void *)(pbyTxBufferAddr + wTxBufSize), 0, (cbHeaderLength - wTxBufSize));
1178 
1179 	/* Fill FIFO,RrvTime,RTS,and CTS */
1180 	s_vGenerateTxParameter(pDevice, byPktType, tx_buffer_head, pvRrvTime, pvRTS, pvCTS,
1181 			       cbFrameSize, bNeedACK, uDMAIdx, hdr, pDevice->wCurrentRate);
1182 	/* Fill DataHead */
1183 	uDuration = s_uFillDataHead(pDevice, byPktType, pvTxDataHd, cbFrameSize, uDMAIdx, bNeedACK,
1184 				    0, 0, uMACfragNum, byFBOption, pDevice->wCurrentRate, is_pspoll);
1185 
1186 	hdr->duration_id = uDuration;
1187 
1188 	cbReqCount = cbHeaderLength + uPadding + skb->len;
1189 	pbyBuffer = (unsigned char *)pHeadTD->td_info->buf;
1190 	uLength = cbHeaderLength + uPadding;
1191 
1192 	/* Copy the Packet into a tx Buffer */
1193 	memcpy((pbyBuffer + uLength), skb->data, skb->len);
1194 
1195 	ptdCurr = pHeadTD;
1196 
1197 	ptdCurr->td_info->req_count = (u16)cbReqCount;
1198 
1199 	return cbHeaderLength;
1200 }
1201 
1202 static void vnt_fill_txkey(struct ieee80211_hdr *hdr, u8 *key_buffer,
1203 			   struct ieee80211_key_conf *tx_key,
1204 			   struct sk_buff *skb,	u16 payload_len,
1205 			   struct vnt_mic_hdr *mic_hdr)
1206 {
1207 	u64 pn64;
1208 	u8 *iv = ((u8 *)hdr + ieee80211_get_hdrlen_from_skb(skb));
1209 
1210 	/* strip header and icv len from payload */
1211 	payload_len -= ieee80211_get_hdrlen_from_skb(skb);
1212 	payload_len -= tx_key->icv_len;
1213 
1214 	switch (tx_key->cipher) {
1215 	case WLAN_CIPHER_SUITE_WEP40:
1216 	case WLAN_CIPHER_SUITE_WEP104:
1217 		memcpy(key_buffer, iv, 3);
1218 		memcpy(key_buffer + 3, tx_key->key, tx_key->keylen);
1219 
1220 		if (tx_key->keylen == WLAN_KEY_LEN_WEP40) {
1221 			memcpy(key_buffer + 8, iv, 3);
1222 			memcpy(key_buffer + 11,
1223 			       tx_key->key, WLAN_KEY_LEN_WEP40);
1224 		}
1225 
1226 		break;
1227 	case WLAN_CIPHER_SUITE_TKIP:
1228 		ieee80211_get_tkip_p2k(tx_key, skb, key_buffer);
1229 
1230 		break;
1231 	case WLAN_CIPHER_SUITE_CCMP:
1232 
1233 		if (!mic_hdr)
1234 			return;
1235 
1236 		mic_hdr->id = 0x59;
1237 		mic_hdr->payload_len = cpu_to_be16(payload_len);
1238 		ether_addr_copy(mic_hdr->mic_addr2, hdr->addr2);
1239 
1240 		pn64 = atomic64_read(&tx_key->tx_pn);
1241 		mic_hdr->ccmp_pn[5] = pn64;
1242 		mic_hdr->ccmp_pn[4] = pn64 >> 8;
1243 		mic_hdr->ccmp_pn[3] = pn64 >> 16;
1244 		mic_hdr->ccmp_pn[2] = pn64 >> 24;
1245 		mic_hdr->ccmp_pn[1] = pn64 >> 32;
1246 		mic_hdr->ccmp_pn[0] = pn64 >> 40;
1247 
1248 		if (ieee80211_has_a4(hdr->frame_control))
1249 			mic_hdr->hlen = cpu_to_be16(28);
1250 		else
1251 			mic_hdr->hlen = cpu_to_be16(22);
1252 
1253 		ether_addr_copy(mic_hdr->addr1, hdr->addr1);
1254 		ether_addr_copy(mic_hdr->addr2, hdr->addr2);
1255 		ether_addr_copy(mic_hdr->addr3, hdr->addr3);
1256 
1257 		mic_hdr->frame_control = cpu_to_le16(
1258 			le16_to_cpu(hdr->frame_control) & 0xc78f);
1259 		mic_hdr->seq_ctrl = cpu_to_le16(
1260 				le16_to_cpu(hdr->seq_ctrl) & 0xf);
1261 
1262 		if (ieee80211_has_a4(hdr->frame_control))
1263 			ether_addr_copy(mic_hdr->addr4, hdr->addr4);
1264 
1265 		memcpy(key_buffer, tx_key->key, WLAN_KEY_LEN_CCMP);
1266 
1267 		break;
1268 	default:
1269 		break;
1270 	}
1271 }
1272 
1273 int vnt_generate_fifo_header(struct vnt_private *priv, u32 dma_idx,
1274 			     struct vnt_tx_desc *head_td, struct sk_buff *skb)
1275 {
1276 	struct vnt_td_info *td_info = head_td->td_info;
1277 	struct ieee80211_tx_info *info = IEEE80211_SKB_CB(skb);
1278 	struct ieee80211_tx_rate *tx_rate = &info->control.rates[0];
1279 	struct ieee80211_rate *rate;
1280 	struct ieee80211_key_conf *tx_key;
1281 	struct ieee80211_hdr *hdr;
1282 	struct vnt_tx_fifo_head *tx_buffer_head =
1283 			(struct vnt_tx_fifo_head *)td_info->buf;
1284 	u16 tx_body_size = skb->len, current_rate;
1285 	u8 pkt_type;
1286 	bool is_pspoll = false;
1287 
1288 	memset(tx_buffer_head, 0, sizeof(*tx_buffer_head));
1289 
1290 	hdr = (struct ieee80211_hdr *)(skb->data);
1291 
1292 	rate = ieee80211_get_tx_rate(priv->hw, info);
1293 
1294 	current_rate = rate->hw_value;
1295 	if (priv->wCurrentRate != current_rate &&
1296 			!(priv->hw->conf.flags & IEEE80211_CONF_OFFCHANNEL)) {
1297 		priv->wCurrentRate = current_rate;
1298 
1299 		RFbSetPower(priv, priv->wCurrentRate,
1300 			    priv->hw->conf.chandef.chan->hw_value);
1301 	}
1302 
1303 	if (current_rate > RATE_11M) {
1304 		if (info->band == NL80211_BAND_5GHZ) {
1305 			pkt_type = PK_TYPE_11A;
1306 		} else {
1307 			if (tx_rate->flags & IEEE80211_TX_RC_USE_CTS_PROTECT)
1308 				pkt_type = PK_TYPE_11GB;
1309 			else
1310 				pkt_type = PK_TYPE_11GA;
1311 		}
1312 	} else {
1313 		pkt_type = PK_TYPE_11B;
1314 	}
1315 
1316 	/*Set fifo controls */
1317 	if (pkt_type == PK_TYPE_11A)
1318 		tx_buffer_head->fifo_ctl = 0;
1319 	else if (pkt_type == PK_TYPE_11B)
1320 		tx_buffer_head->fifo_ctl = cpu_to_le16(FIFOCTL_11B);
1321 	else if (pkt_type == PK_TYPE_11GB)
1322 		tx_buffer_head->fifo_ctl = cpu_to_le16(FIFOCTL_11GB);
1323 	else if (pkt_type == PK_TYPE_11GA)
1324 		tx_buffer_head->fifo_ctl = cpu_to_le16(FIFOCTL_11GA);
1325 
1326 	/* generate interrupt */
1327 	tx_buffer_head->fifo_ctl |= cpu_to_le16(FIFOCTL_GENINT);
1328 
1329 	if (!ieee80211_is_data(hdr->frame_control)) {
1330 		tx_buffer_head->fifo_ctl |= cpu_to_le16(FIFOCTL_TMOEN);
1331 		tx_buffer_head->fifo_ctl |= cpu_to_le16(FIFOCTL_ISDMA0);
1332 		tx_buffer_head->time_stamp =
1333 			cpu_to_le16(DEFAULT_MGN_LIFETIME_RES_64us);
1334 	} else {
1335 		tx_buffer_head->time_stamp =
1336 			cpu_to_le16(DEFAULT_MSDU_LIFETIME_RES_64us);
1337 	}
1338 
1339 	if (!(info->flags & IEEE80211_TX_CTL_NO_ACK))
1340 		tx_buffer_head->fifo_ctl |= cpu_to_le16(FIFOCTL_NEEDACK);
1341 
1342 	if (ieee80211_has_retry(hdr->frame_control))
1343 		tx_buffer_head->fifo_ctl |= cpu_to_le16(FIFOCTL_LRETRY);
1344 
1345 	if (tx_rate->flags & IEEE80211_TX_RC_USE_SHORT_PREAMBLE)
1346 		priv->byPreambleType = PREAMBLE_SHORT;
1347 	else
1348 		priv->byPreambleType = PREAMBLE_LONG;
1349 
1350 	if (tx_rate->flags & IEEE80211_TX_RC_USE_RTS_CTS)
1351 		tx_buffer_head->fifo_ctl |= cpu_to_le16(FIFOCTL_RTS);
1352 
1353 	if (ieee80211_has_a4(hdr->frame_control)) {
1354 		tx_buffer_head->fifo_ctl |= cpu_to_le16(FIFOCTL_LHEAD);
1355 		priv->bLongHeader = true;
1356 	}
1357 
1358 	if (info->flags & IEEE80211_TX_CTL_NO_PS_BUFFER)
1359 		is_pspoll = true;
1360 
1361 	tx_buffer_head->frag_ctl =
1362 			cpu_to_le16(ieee80211_get_hdrlen_from_skb(skb) << 10);
1363 
1364 	if (info->control.hw_key) {
1365 		tx_key = info->control.hw_key;
1366 
1367 		switch (info->control.hw_key->cipher) {
1368 		case WLAN_CIPHER_SUITE_WEP40:
1369 		case WLAN_CIPHER_SUITE_WEP104:
1370 			tx_buffer_head->frag_ctl |= cpu_to_le16(FRAGCTL_LEGACY);
1371 			break;
1372 		case WLAN_CIPHER_SUITE_TKIP:
1373 			tx_buffer_head->frag_ctl |= cpu_to_le16(FRAGCTL_TKIP);
1374 			break;
1375 		case WLAN_CIPHER_SUITE_CCMP:
1376 			tx_buffer_head->frag_ctl |= cpu_to_le16(FRAGCTL_AES);
1377 		default:
1378 			break;
1379 		}
1380 	}
1381 
1382 	tx_buffer_head->current_rate = cpu_to_le16(current_rate);
1383 
1384 	/* legacy rates TODO use ieee80211_tx_rate */
1385 	if (current_rate >= RATE_18M && ieee80211_is_data(hdr->frame_control)) {
1386 		if (priv->byAutoFBCtrl == AUTO_FB_0)
1387 			tx_buffer_head->fifo_ctl |=
1388 						cpu_to_le16(FIFOCTL_AUTO_FB_0);
1389 		else if (priv->byAutoFBCtrl == AUTO_FB_1)
1390 			tx_buffer_head->fifo_ctl |=
1391 						cpu_to_le16(FIFOCTL_AUTO_FB_1);
1392 
1393 	}
1394 
1395 	tx_buffer_head->frag_ctl |= cpu_to_le16(FRAGCTL_NONFRAG);
1396 
1397 	s_cbFillTxBufHead(priv, pkt_type, (u8 *)tx_buffer_head,
1398 			  dma_idx, head_td, is_pspoll);
1399 
1400 	if (info->control.hw_key) {
1401 		tx_key = info->control.hw_key;
1402 		if (tx_key->keylen > 0)
1403 			vnt_fill_txkey(hdr, tx_buffer_head->tx_key,
1404 				tx_key, skb, tx_body_size, td_info->mic_hdr);
1405 	}
1406 
1407 	return 0;
1408 }
1409 
1410 static int vnt_beacon_xmit(struct vnt_private *priv,
1411 			   struct sk_buff *skb)
1412 {
1413 	struct vnt_tx_short_buf_head *short_head =
1414 		(struct vnt_tx_short_buf_head *)priv->tx_beacon_bufs;
1415 	struct ieee80211_mgmt *mgmt_hdr = (struct ieee80211_mgmt *)
1416 				(priv->tx_beacon_bufs + sizeof(*short_head));
1417 	struct ieee80211_tx_info *info;
1418 	u32 frame_size = skb->len + 4;
1419 	u16 current_rate;
1420 
1421 	memset(priv->tx_beacon_bufs, 0, sizeof(*short_head));
1422 
1423 	if (priv->byBBType == BB_TYPE_11A) {
1424 		current_rate = RATE_6M;
1425 
1426 		/* Get SignalField,ServiceField,Length */
1427 		vnt_get_phy_field(priv, frame_size, current_rate,
1428 				  PK_TYPE_11A, &short_head->ab);
1429 
1430 		/* Get Duration and TimeStampOff */
1431 		short_head->duration =
1432 			cpu_to_le16((u16)s_uGetDataDuration(priv, DATADUR_B,
1433 				    frame_size, PK_TYPE_11A, current_rate,
1434 				    false, 0, 0, 1, AUTO_FB_NONE));
1435 
1436 		short_head->time_stamp_off =
1437 				vnt_time_stamp_off(priv, current_rate);
1438 	} else {
1439 		current_rate = RATE_1M;
1440 		short_head->fifo_ctl |= cpu_to_le16(FIFOCTL_11B);
1441 
1442 		/* Get SignalField,ServiceField,Length */
1443 		vnt_get_phy_field(priv, frame_size, current_rate,
1444 				  PK_TYPE_11B, &short_head->ab);
1445 
1446 		/* Get Duration and TimeStampOff */
1447 		short_head->duration =
1448 			cpu_to_le16((u16)s_uGetDataDuration(priv, DATADUR_B,
1449 				    frame_size, PK_TYPE_11B, current_rate,
1450 				    false, 0, 0, 1, AUTO_FB_NONE));
1451 
1452 		short_head->time_stamp_off =
1453 			vnt_time_stamp_off(priv, current_rate);
1454 	}
1455 
1456 	short_head->fifo_ctl |= cpu_to_le16(FIFOCTL_GENINT);
1457 
1458 	/* Copy Beacon */
1459 	memcpy(mgmt_hdr, skb->data, skb->len);
1460 
1461 	/* time stamp always 0 */
1462 	mgmt_hdr->u.beacon.timestamp = 0;
1463 
1464 	info = IEEE80211_SKB_CB(skb);
1465 	if (info->flags & IEEE80211_TX_CTL_ASSIGN_SEQ) {
1466 		struct ieee80211_hdr *hdr = (struct ieee80211_hdr *)mgmt_hdr;
1467 
1468 		hdr->duration_id = 0;
1469 		hdr->seq_ctrl = cpu_to_le16(priv->wSeqCounter << 4);
1470 	}
1471 
1472 	priv->wSeqCounter++;
1473 	if (priv->wSeqCounter > 0x0fff)
1474 		priv->wSeqCounter = 0;
1475 
1476 	priv->wBCNBufLen = sizeof(*short_head) + skb->len;
1477 
1478 	MACvSetCurrBCNTxDescAddr(priv->PortOffset, priv->tx_beacon_dma);
1479 
1480 	MACvSetCurrBCNLength(priv->PortOffset, priv->wBCNBufLen);
1481 	/* Set auto Transmit on */
1482 	MACvRegBitsOn(priv->PortOffset, MAC_REG_TCR, TCR_AUTOBCNTX);
1483 	/* Poll Transmit the adapter */
1484 	MACvTransmitBCN(priv->PortOffset);
1485 
1486 	return 0;
1487 }
1488 
1489 int vnt_beacon_make(struct vnt_private *priv, struct ieee80211_vif *vif)
1490 {
1491 	struct sk_buff *beacon;
1492 
1493 	beacon = ieee80211_beacon_get(priv->hw, vif);
1494 	if (!beacon)
1495 		return -ENOMEM;
1496 
1497 	if (vnt_beacon_xmit(priv, beacon)) {
1498 		ieee80211_free_txskb(priv->hw, beacon);
1499 		return -ENODEV;
1500 	}
1501 
1502 	return 0;
1503 }
1504 
1505 int vnt_beacon_enable(struct vnt_private *priv, struct ieee80211_vif *vif,
1506 		      struct ieee80211_bss_conf *conf)
1507 {
1508 	VNSvOutPortB(priv->PortOffset + MAC_REG_TFTCTL, TFTCTL_TSFCNTRST);
1509 
1510 	VNSvOutPortB(priv->PortOffset + MAC_REG_TFTCTL, TFTCTL_TSFCNTREN);
1511 
1512 	CARDvSetFirstNextTBTT(priv, conf->beacon_int);
1513 
1514 	CARDbSetBeaconPeriod(priv, conf->beacon_int);
1515 
1516 	return vnt_beacon_make(priv, vif);
1517 }
1518