1 // SPDX-License-Identifier: GPL-2.0+
3 * Copyright (c) 1996, 2003 VIA Networking Technologies, Inc.
8 * Purpose: handle WMAC/802.3/802.11 rx & tx 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
45 /*--------------------- Static Definitions -------------------------*/
47 /*--------------------- Static Classes ----------------------------*/
49 /*--------------------- Static Variables --------------------------*/
51 /*--------------------- Static Functions --------------------------*/
53 /*--------------------- Static Definitions -------------------------*/
54 /* if packet size < 256 -> in-direct send
55 * vpacket size >= 256 -> direct send
57 #define CRITICAL_PACKET_LEN 256
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 */
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 */
69 static const unsigned short wFB_Opt1[2][5] = {
70 {RATE_12M, RATE_18M, RATE_24M, RATE_24M, RATE_36M}, /* fallback_rate0 */
71 {RATE_6M, RATE_6M, RATE_12M, RATE_12M, RATE_18M}, /* fallback_rate1 */
78 #define RTSDUR_BA_F0 4
79 #define RTSDUR_AA_F0 5
80 #define RTSDUR_BA_F1 6
81 #define RTSDUR_AA_F1 7
82 #define CTSDUR_BA_F0 8
83 #define CTSDUR_BA_F1 9
86 #define DATADUR_A_F0 12
87 #define DATADUR_A_F1 13
89 /*--------------------- Static Functions --------------------------*/
93 struct vnt_private *pDevice,
94 unsigned char byPktType,
96 unsigned int cbFrameLength,
99 struct ieee80211_hdr *hdr,
100 unsigned short wCurrentRate,
101 unsigned char byFBOption
106 s_vGenerateTxParameter(
107 struct vnt_private *pDevice,
108 unsigned char byPktType,
109 struct vnt_tx_fifo_head *,
113 unsigned int cbFrameSize,
115 unsigned int uDMAIdx,
117 unsigned short wCurrentRate
121 s_cbFillTxBufHead(struct vnt_private *pDevice, unsigned char byPktType,
122 unsigned char *pbyTxBufferAddr,
123 unsigned int uDMAIdx, struct vnt_tx_desc *pHeadTD,
124 unsigned int uNodeIndex);
129 struct vnt_private *pDevice,
130 unsigned char byPktType,
132 unsigned int cbFrameLength,
133 unsigned int uDMAIdx,
135 unsigned int uFragIdx,
136 unsigned int cbLastFragmentSize,
137 unsigned int uMACfragNum,
138 unsigned char byFBOption,
139 unsigned short wCurrentRate,
143 /*--------------------- Export Variables --------------------------*/
145 static __le16 vnt_time_stamp_off(struct vnt_private *priv, u16 rate)
147 return cpu_to_le16(wTimeStampOff[priv->byPreambleType % 2]
151 /* byPktType : PK_TYPE_11A 0
159 struct vnt_private *pDevice,
160 unsigned char byPktType,
161 unsigned int cbFrameLength,
162 unsigned short wRate,
166 unsigned int uDataTime, uAckTime;
168 uDataTime = BBuGetFrameTime(pDevice->byPreambleType, byPktType, cbFrameLength, wRate);
169 if (byPktType == PK_TYPE_11B) /* llb,CCK mode */
170 uAckTime = BBuGetFrameTime(pDevice->byPreambleType, byPktType, 14, (unsigned short)pDevice->byTopCCKBasicRate);
171 else /* 11g 2.4G OFDM mode & 11a 5G OFDM mode */
172 uAckTime = BBuGetFrameTime(pDevice->byPreambleType, byPktType, 14, (unsigned short)pDevice->byTopOFDMBasicRate);
175 return uDataTime + pDevice->uSIFS + uAckTime;
180 static __le16 vnt_rxtx_rsvtime_le16(struct vnt_private *priv, u8 pkt_type,
181 u32 frame_length, u16 rate, bool need_ack)
183 return cpu_to_le16((u16)s_uGetTxRsvTime(priv, pkt_type,
184 frame_length, rate, need_ack));
187 /* byFreqType: 0=>5GHZ 1=>2.4GHZ */
191 struct vnt_private *pDevice,
192 unsigned char byRTSRsvType,
193 unsigned char byPktType,
194 unsigned int cbFrameLength,
195 unsigned short wCurrentRate
198 unsigned int uRrvTime, uRTSTime, uCTSTime, uAckTime, uDataTime;
200 uRrvTime = uRTSTime = uCTSTime = uAckTime = uDataTime = 0;
202 uDataTime = BBuGetFrameTime(pDevice->byPreambleType, byPktType, cbFrameLength, wCurrentRate);
203 if (byRTSRsvType == 0) { /* RTSTxRrvTime_bb */
204 uRTSTime = BBuGetFrameTime(pDevice->byPreambleType, byPktType, 20, pDevice->byTopCCKBasicRate);
205 uCTSTime = uAckTime = BBuGetFrameTime(pDevice->byPreambleType, byPktType, 14, pDevice->byTopCCKBasicRate);
206 } else if (byRTSRsvType == 1) { /* RTSTxRrvTime_ba, only in 2.4GHZ */
207 uRTSTime = BBuGetFrameTime(pDevice->byPreambleType, byPktType, 20, pDevice->byTopCCKBasicRate);
208 uCTSTime = BBuGetFrameTime(pDevice->byPreambleType, byPktType, 14, pDevice->byTopCCKBasicRate);
209 uAckTime = BBuGetFrameTime(pDevice->byPreambleType, byPktType, 14, pDevice->byTopOFDMBasicRate);
210 } else if (byRTSRsvType == 2) { /* RTSTxRrvTime_aa */
211 uRTSTime = BBuGetFrameTime(pDevice->byPreambleType, byPktType, 20, pDevice->byTopOFDMBasicRate);
212 uCTSTime = uAckTime = BBuGetFrameTime(pDevice->byPreambleType, byPktType, 14, pDevice->byTopOFDMBasicRate);
213 } else if (byRTSRsvType == 3) { /* CTSTxRrvTime_ba, only in 2.4GHZ */
214 uCTSTime = BBuGetFrameTime(pDevice->byPreambleType, byPktType, 14, pDevice->byTopCCKBasicRate);
215 uAckTime = BBuGetFrameTime(pDevice->byPreambleType, byPktType, 14, pDevice->byTopOFDMBasicRate);
216 uRrvTime = uCTSTime + uAckTime + uDataTime + 2 * pDevice->uSIFS;
217 return cpu_to_le16((u16)uRrvTime);
221 uRrvTime = uRTSTime + uCTSTime + uAckTime + uDataTime + 3 * pDevice->uSIFS;
222 return cpu_to_le16((u16)uRrvTime);
225 /* byFreqType 0: 5GHz, 1:2.4Ghz */
229 struct vnt_private *pDevice,
230 unsigned char byDurType,
231 unsigned int cbFrameLength,
232 unsigned char byPktType,
233 unsigned short wRate,
235 unsigned int uFragIdx,
236 unsigned int cbLastFragmentSize,
237 unsigned int uMACfragNum,
238 unsigned char byFBOption
241 bool bLastFrag = false;
242 unsigned int uAckTime = 0, uNextPktTime = 0;
244 if (uFragIdx == (uMACfragNum - 1))
248 case DATADUR_B: /* DATADUR_B */
249 if (((uMACfragNum == 1)) || bLastFrag) {/* Non Frag or Last Frag */
251 uAckTime = BBuGetFrameTime(pDevice->byPreambleType, byPktType, 14, pDevice->byTopCCKBasicRate);
252 return pDevice->uSIFS + uAckTime;
256 } else {/* First Frag or Mid Frag */
257 if (uFragIdx == (uMACfragNum - 2))
258 uNextPktTime = s_uGetTxRsvTime(pDevice, byPktType, cbLastFragmentSize, wRate, bNeedAck);
260 uNextPktTime = s_uGetTxRsvTime(pDevice, byPktType, cbFrameLength, wRate, bNeedAck);
263 uAckTime = BBuGetFrameTime(pDevice->byPreambleType, byPktType, 14, pDevice->byTopCCKBasicRate);
264 return pDevice->uSIFS + uAckTime + uNextPktTime;
266 return pDevice->uSIFS + uNextPktTime;
271 case DATADUR_A: /* DATADUR_A */
272 if (((uMACfragNum == 1)) || bLastFrag) {/* Non Frag or Last Frag */
274 uAckTime = BBuGetFrameTime(pDevice->byPreambleType, byPktType, 14, pDevice->byTopOFDMBasicRate);
275 return pDevice->uSIFS + uAckTime;
279 } else {/* First Frag or Mid Frag */
280 if (uFragIdx == (uMACfragNum - 2))
281 uNextPktTime = s_uGetTxRsvTime(pDevice, byPktType, cbLastFragmentSize, wRate, bNeedAck);
283 uNextPktTime = s_uGetTxRsvTime(pDevice, byPktType, cbFrameLength, wRate, bNeedAck);
286 uAckTime = BBuGetFrameTime(pDevice->byPreambleType, byPktType, 14, pDevice->byTopOFDMBasicRate);
287 return pDevice->uSIFS + uAckTime + uNextPktTime;
289 return pDevice->uSIFS + uNextPktTime;
294 case DATADUR_A_F0: /* DATADUR_A_F0 */
295 if (((uMACfragNum == 1)) || bLastFrag) {/* Non Frag or Last Frag */
297 uAckTime = BBuGetFrameTime(pDevice->byPreambleType, byPktType, 14, pDevice->byTopOFDMBasicRate);
298 return pDevice->uSIFS + uAckTime;
302 } else { /* First Frag or Mid Frag */
303 if (byFBOption == AUTO_FB_0) {
304 if (wRate < RATE_18M)
306 else if (wRate > RATE_54M)
309 if (uFragIdx == (uMACfragNum - 2))
310 uNextPktTime = s_uGetTxRsvTime(pDevice, byPktType, cbLastFragmentSize, wFB_Opt0[FB_RATE0][wRate-RATE_18M], bNeedAck);
312 uNextPktTime = s_uGetTxRsvTime(pDevice, byPktType, cbFrameLength, wFB_Opt0[FB_RATE0][wRate-RATE_18M], bNeedAck);
314 } else { /* (byFBOption == AUTO_FB_1) */
315 if (wRate < RATE_18M)
317 else if (wRate > RATE_54M)
320 if (uFragIdx == (uMACfragNum - 2))
321 uNextPktTime = s_uGetTxRsvTime(pDevice, byPktType, cbLastFragmentSize, wFB_Opt1[FB_RATE0][wRate-RATE_18M], bNeedAck);
323 uNextPktTime = s_uGetTxRsvTime(pDevice, byPktType, cbFrameLength, wFB_Opt1[FB_RATE0][wRate-RATE_18M], bNeedAck);
327 uAckTime = BBuGetFrameTime(pDevice->byPreambleType, byPktType, 14, pDevice->byTopOFDMBasicRate);
328 return pDevice->uSIFS + uAckTime + uNextPktTime;
330 return pDevice->uSIFS + uNextPktTime;
335 case DATADUR_A_F1: /* DATADUR_A_F1 */
336 if (((uMACfragNum == 1)) || bLastFrag) { /* Non Frag or Last Frag */
338 uAckTime = BBuGetFrameTime(pDevice->byPreambleType, byPktType, 14, pDevice->byTopOFDMBasicRate);
339 return pDevice->uSIFS + uAckTime;
343 } else { /* First Frag or Mid Frag */
344 if (byFBOption == AUTO_FB_0) {
345 if (wRate < RATE_18M)
347 else if (wRate > RATE_54M)
350 if (uFragIdx == (uMACfragNum - 2))
351 uNextPktTime = s_uGetTxRsvTime(pDevice, byPktType, cbLastFragmentSize, wFB_Opt0[FB_RATE1][wRate-RATE_18M], bNeedAck);
353 uNextPktTime = s_uGetTxRsvTime(pDevice, byPktType, cbFrameLength, wFB_Opt0[FB_RATE1][wRate-RATE_18M], bNeedAck);
355 } else { /* (byFBOption == AUTO_FB_1) */
356 if (wRate < RATE_18M)
358 else if (wRate > RATE_54M)
361 if (uFragIdx == (uMACfragNum - 2))
362 uNextPktTime = s_uGetTxRsvTime(pDevice, byPktType, cbLastFragmentSize, wFB_Opt1[FB_RATE1][wRate-RATE_18M], bNeedAck);
364 uNextPktTime = s_uGetTxRsvTime(pDevice, byPktType, cbFrameLength, wFB_Opt1[FB_RATE1][wRate-RATE_18M], bNeedAck);
367 uAckTime = BBuGetFrameTime(pDevice->byPreambleType, byPktType, 14, pDevice->byTopOFDMBasicRate);
368 return pDevice->uSIFS + uAckTime + uNextPktTime;
370 return pDevice->uSIFS + uNextPktTime;
382 /* byFreqType: 0=>5GHZ 1=>2.4GHZ */
385 s_uGetRTSCTSDuration(
386 struct vnt_private *pDevice,
387 unsigned char byDurType,
388 unsigned int cbFrameLength,
389 unsigned char byPktType,
390 unsigned short wRate,
392 unsigned char byFBOption
395 unsigned int uCTSTime = 0, uDurTime = 0;
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);
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);
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);
413 case CTSDUR_BA: /* CTSDuration_ba */
414 uDurTime = pDevice->uSIFS + s_uGetTxRsvTime(pDevice, byPktType, cbFrameLength, wRate, bNeedAck);
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);
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);
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);
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);
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);
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);
473 return cpu_to_le16((u16)uDurTime);
479 struct vnt_private *pDevice,
480 unsigned char byPktType,
482 unsigned int cbFrameLength,
483 unsigned int uDMAIdx,
485 unsigned int uFragIdx,
486 unsigned int cbLastFragmentSize,
487 unsigned int uMACfragNum,
488 unsigned char byFBOption,
489 unsigned short wCurrentRate,
496 if (byPktType == PK_TYPE_11GB || byPktType == PK_TYPE_11GA) {
497 if (byFBOption == AUTO_FB_NONE) {
498 struct vnt_tx_datahead_g *buf = pTxDataHead;
499 /* Get SignalField, ServiceField & Length */
500 vnt_get_phy_field(pDevice, cbFrameLength, wCurrentRate,
503 vnt_get_phy_field(pDevice, cbFrameLength,
504 pDevice->byTopCCKBasicRate,
505 PK_TYPE_11B, &buf->b);
508 __le16 dur = cpu_to_le16(pDevice->current_aid | BIT(14) | BIT(15));
510 buf->duration_a = dur;
511 buf->duration_b = dur;
513 /* Get Duration and TimeStamp */
515 cpu_to_le16((u16)s_uGetDataDuration(pDevice, DATADUR_A, cbFrameLength,
516 byPktType, wCurrentRate, bNeedAck, uFragIdx,
517 cbLastFragmentSize, uMACfragNum,
520 cpu_to_le16((u16)s_uGetDataDuration(pDevice, DATADUR_B, cbFrameLength,
521 PK_TYPE_11B, pDevice->byTopCCKBasicRate,
522 bNeedAck, uFragIdx, cbLastFragmentSize,
523 uMACfragNum, byFBOption));
526 buf->time_stamp_off_a = vnt_time_stamp_off(pDevice, wCurrentRate);
527 buf->time_stamp_off_b = vnt_time_stamp_off(pDevice, pDevice->byTopCCKBasicRate);
529 return buf->duration_a;
532 struct vnt_tx_datahead_g_fb *buf = pTxDataHead;
533 /* Get SignalField, ServiceField & Length */
534 vnt_get_phy_field(pDevice, cbFrameLength, wCurrentRate,
537 vnt_get_phy_field(pDevice, cbFrameLength,
538 pDevice->byTopCCKBasicRate,
539 PK_TYPE_11B, &buf->b);
540 /* Get Duration and TimeStamp */
541 buf->duration_a = cpu_to_le16((u16)s_uGetDataDuration(pDevice, DATADUR_A, cbFrameLength, byPktType,
542 wCurrentRate, bNeedAck, uFragIdx, cbLastFragmentSize, uMACfragNum, byFBOption));
543 buf->duration_b = cpu_to_le16((u16)s_uGetDataDuration(pDevice, DATADUR_B, cbFrameLength, PK_TYPE_11B,
544 pDevice->byTopCCKBasicRate, bNeedAck, uFragIdx, cbLastFragmentSize, uMACfragNum, byFBOption));
545 buf->duration_a_f0 = cpu_to_le16((u16)s_uGetDataDuration(pDevice, DATADUR_A_F0, cbFrameLength, byPktType,
546 wCurrentRate, bNeedAck, uFragIdx, cbLastFragmentSize, uMACfragNum, byFBOption));
547 buf->duration_a_f1 = cpu_to_le16((u16)s_uGetDataDuration(pDevice, DATADUR_A_F1, cbFrameLength, byPktType,
548 wCurrentRate, bNeedAck, uFragIdx, cbLastFragmentSize, uMACfragNum, byFBOption));
550 buf->time_stamp_off_a = vnt_time_stamp_off(pDevice, wCurrentRate);
551 buf->time_stamp_off_b = vnt_time_stamp_off(pDevice, pDevice->byTopCCKBasicRate);
553 return buf->duration_a;
554 } /* if (byFBOption == AUTO_FB_NONE) */
555 } else if (byPktType == PK_TYPE_11A) {
556 if (byFBOption != AUTO_FB_NONE) {
558 struct vnt_tx_datahead_a_fb *buf = pTxDataHead;
559 /* Get SignalField, ServiceField & Length */
560 vnt_get_phy_field(pDevice, cbFrameLength, wCurrentRate,
563 /* Get Duration and TimeStampOff */
564 buf->duration = cpu_to_le16((u16)s_uGetDataDuration(pDevice, DATADUR_A, cbFrameLength, byPktType,
565 wCurrentRate, bNeedAck, uFragIdx, cbLastFragmentSize, uMACfragNum, byFBOption));
566 buf->duration_f0 = cpu_to_le16((u16)s_uGetDataDuration(pDevice, DATADUR_A_F0, cbFrameLength, byPktType,
567 wCurrentRate, bNeedAck, uFragIdx, cbLastFragmentSize, uMACfragNum, byFBOption));
568 buf->duration_f1 = cpu_to_le16((u16)s_uGetDataDuration(pDevice, DATADUR_A_F1, cbFrameLength, byPktType,
569 wCurrentRate, bNeedAck, uFragIdx, cbLastFragmentSize, uMACfragNum, byFBOption));
570 buf->time_stamp_off = vnt_time_stamp_off(pDevice, wCurrentRate);
571 return buf->duration;
573 struct vnt_tx_datahead_ab *buf = pTxDataHead;
574 /* Get SignalField, ServiceField & Length */
575 vnt_get_phy_field(pDevice, cbFrameLength, wCurrentRate,
576 byPktType, &buf->ab);
579 __le16 dur = cpu_to_le16(pDevice->current_aid | BIT(14) | BIT(15));
583 /* Get Duration and TimeStampOff */
585 cpu_to_le16((u16)s_uGetDataDuration(pDevice, DATADUR_A, cbFrameLength, byPktType,
586 wCurrentRate, bNeedAck, uFragIdx,
587 cbLastFragmentSize, uMACfragNum,
591 buf->time_stamp_off = vnt_time_stamp_off(pDevice, wCurrentRate);
592 return buf->duration;
595 struct vnt_tx_datahead_ab *buf = pTxDataHead;
596 /* Get SignalField, ServiceField & Length */
597 vnt_get_phy_field(pDevice, cbFrameLength, wCurrentRate,
598 byPktType, &buf->ab);
601 __le16 dur = cpu_to_le16(pDevice->current_aid | BIT(14) | BIT(15));
605 /* Get Duration and TimeStampOff */
607 cpu_to_le16((u16)s_uGetDataDuration(pDevice, DATADUR_B, cbFrameLength, byPktType,
608 wCurrentRate, bNeedAck, uFragIdx,
609 cbLastFragmentSize, uMACfragNum,
613 buf->time_stamp_off = vnt_time_stamp_off(pDevice, wCurrentRate);
614 return buf->duration;
622 struct vnt_private *pDevice,
623 unsigned char byPktType,
625 unsigned int cbFrameLength,
628 struct ieee80211_hdr *hdr,
629 unsigned short wCurrentRate,
630 unsigned char byFBOption
633 unsigned int uRTSFrameLen = 20;
639 /* When CRCDIS bit is on, H/W forgot to generate FCS for
640 * RTS frame, in this case we need to decrease its length by 4.
645 /* Note: So far RTSHead doesn't appear in ATIM & Beacom DMA,
646 * so we don't need to take them into account.
647 * Otherwise, we need to modify codes for them.
649 if (byPktType == PK_TYPE_11GB || byPktType == PK_TYPE_11GA) {
650 if (byFBOption == AUTO_FB_NONE) {
651 struct vnt_rts_g *buf = pvRTS;
652 /* Get SignalField, ServiceField & Length */
653 vnt_get_phy_field(pDevice, uRTSFrameLen,
654 pDevice->byTopCCKBasicRate,
655 PK_TYPE_11B, &buf->b);
657 vnt_get_phy_field(pDevice, uRTSFrameLen,
658 pDevice->byTopOFDMBasicRate,
662 s_uGetRTSCTSDuration(pDevice, RTSDUR_BB,
663 cbFrameLength, PK_TYPE_11B,
664 pDevice->byTopCCKBasicRate,
665 bNeedAck, byFBOption);
667 s_uGetRTSCTSDuration(pDevice, RTSDUR_AA,
668 cbFrameLength, byPktType,
669 wCurrentRate, bNeedAck,
672 s_uGetRTSCTSDuration(pDevice, RTSDUR_BA,
673 cbFrameLength, byPktType,
674 wCurrentRate, bNeedAck,
677 buf->data.duration = buf->duration_aa;
678 /* Get RTS Frame body */
679 buf->data.frame_control =
680 cpu_to_le16(IEEE80211_FTYPE_CTL |
681 IEEE80211_STYPE_RTS);
683 ether_addr_copy(buf->data.ra, hdr->addr1);
684 ether_addr_copy(buf->data.ta, hdr->addr2);
686 struct vnt_rts_g_fb *buf = pvRTS;
687 /* Get SignalField, ServiceField & Length */
688 vnt_get_phy_field(pDevice, uRTSFrameLen,
689 pDevice->byTopCCKBasicRate,
690 PK_TYPE_11B, &buf->b);
692 vnt_get_phy_field(pDevice, uRTSFrameLen,
693 pDevice->byTopOFDMBasicRate,
697 s_uGetRTSCTSDuration(pDevice, RTSDUR_BB,
698 cbFrameLength, PK_TYPE_11B,
699 pDevice->byTopCCKBasicRate,
700 bNeedAck, byFBOption);
702 s_uGetRTSCTSDuration(pDevice, RTSDUR_AA,
703 cbFrameLength, byPktType,
704 wCurrentRate, bNeedAck,
707 s_uGetRTSCTSDuration(pDevice, RTSDUR_BA,
708 cbFrameLength, byPktType,
709 wCurrentRate, bNeedAck,
711 buf->rts_duration_ba_f0 =
712 s_uGetRTSCTSDuration(pDevice, RTSDUR_BA_F0,
713 cbFrameLength, byPktType,
714 wCurrentRate, bNeedAck,
716 buf->rts_duration_aa_f0 =
717 s_uGetRTSCTSDuration(pDevice, RTSDUR_AA_F0,
718 cbFrameLength, byPktType,
719 wCurrentRate, bNeedAck,
721 buf->rts_duration_ba_f1 =
722 s_uGetRTSCTSDuration(pDevice, RTSDUR_BA_F1,
723 cbFrameLength, byPktType,
724 wCurrentRate, bNeedAck,
726 buf->rts_duration_aa_f1 =
727 s_uGetRTSCTSDuration(pDevice, RTSDUR_AA_F1,
728 cbFrameLength, byPktType,
729 wCurrentRate, bNeedAck,
731 buf->data.duration = buf->duration_aa;
732 /* Get RTS Frame body */
733 buf->data.frame_control =
734 cpu_to_le16(IEEE80211_FTYPE_CTL |
735 IEEE80211_STYPE_RTS);
737 ether_addr_copy(buf->data.ra, hdr->addr1);
738 ether_addr_copy(buf->data.ta, hdr->addr2);
739 } /* if (byFBOption == AUTO_FB_NONE) */
740 } else if (byPktType == PK_TYPE_11A) {
741 if (byFBOption == AUTO_FB_NONE) {
742 struct vnt_rts_ab *buf = pvRTS;
743 /* Get SignalField, ServiceField & Length */
744 vnt_get_phy_field(pDevice, uRTSFrameLen,
745 pDevice->byTopOFDMBasicRate,
746 byPktType, &buf->ab);
749 s_uGetRTSCTSDuration(pDevice, RTSDUR_AA,
750 cbFrameLength, byPktType,
751 wCurrentRate, bNeedAck,
753 buf->data.duration = buf->duration;
754 /* Get RTS Frame body */
755 buf->data.frame_control =
756 cpu_to_le16(IEEE80211_FTYPE_CTL |
757 IEEE80211_STYPE_RTS);
759 ether_addr_copy(buf->data.ra, hdr->addr1);
760 ether_addr_copy(buf->data.ta, hdr->addr2);
762 struct vnt_rts_a_fb *buf = pvRTS;
763 /* Get SignalField, ServiceField & Length */
764 vnt_get_phy_field(pDevice, uRTSFrameLen,
765 pDevice->byTopOFDMBasicRate,
769 s_uGetRTSCTSDuration(pDevice, RTSDUR_AA,
770 cbFrameLength, byPktType,
771 wCurrentRate, bNeedAck,
773 buf->rts_duration_f0 =
774 s_uGetRTSCTSDuration(pDevice, RTSDUR_AA_F0,
775 cbFrameLength, byPktType,
776 wCurrentRate, bNeedAck,
778 buf->rts_duration_f1 =
779 s_uGetRTSCTSDuration(pDevice, RTSDUR_AA_F1,
780 cbFrameLength, byPktType,
781 wCurrentRate, bNeedAck,
783 buf->data.duration = buf->duration;
784 /* Get RTS Frame body */
785 buf->data.frame_control =
786 cpu_to_le16(IEEE80211_FTYPE_CTL |
787 IEEE80211_STYPE_RTS);
789 ether_addr_copy(buf->data.ra, hdr->addr1);
790 ether_addr_copy(buf->data.ta, hdr->addr2);
792 } else if (byPktType == PK_TYPE_11B) {
793 struct vnt_rts_ab *buf = pvRTS;
794 /* Get SignalField, ServiceField & Length */
795 vnt_get_phy_field(pDevice, uRTSFrameLen,
796 pDevice->byTopCCKBasicRate,
797 PK_TYPE_11B, &buf->ab);
800 s_uGetRTSCTSDuration(pDevice, RTSDUR_BB, cbFrameLength,
801 byPktType, wCurrentRate, bNeedAck,
804 buf->data.duration = buf->duration;
805 /* Get RTS Frame body */
806 buf->data.frame_control =
807 cpu_to_le16(IEEE80211_FTYPE_CTL | IEEE80211_STYPE_RTS);
809 ether_addr_copy(buf->data.ra, hdr->addr1);
810 ether_addr_copy(buf->data.ta, hdr->addr2);
817 struct vnt_private *pDevice,
818 unsigned int uDMAIdx,
819 unsigned char byPktType,
821 unsigned int cbFrameLength,
824 unsigned short wCurrentRate,
825 unsigned char byFBOption
828 unsigned int uCTSFrameLen = 14;
834 /* When CRCDIS bit is on, H/W forgot to generate FCS for
835 * CTS frame, in this case we need to decrease its length by 4.
840 if (byPktType == PK_TYPE_11GB || byPktType == PK_TYPE_11GA) {
841 if (byFBOption != AUTO_FB_NONE && uDMAIdx != TYPE_ATIMDMA && uDMAIdx != TYPE_BEACONDMA) {
843 struct vnt_cts_fb *buf = pvCTS;
844 /* Get SignalField, ServiceField & Length */
845 vnt_get_phy_field(pDevice, uCTSFrameLen,
846 pDevice->byTopCCKBasicRate,
847 PK_TYPE_11B, &buf->b);
850 s_uGetRTSCTSDuration(pDevice, CTSDUR_BA,
851 cbFrameLength, byPktType,
852 wCurrentRate, bNeedAck,
855 /* Get CTSDuration_ba_f0 */
856 buf->cts_duration_ba_f0 =
857 s_uGetRTSCTSDuration(pDevice, CTSDUR_BA_F0,
858 cbFrameLength, byPktType,
859 wCurrentRate, bNeedAck,
862 /* Get CTSDuration_ba_f1 */
863 buf->cts_duration_ba_f1 =
864 s_uGetRTSCTSDuration(pDevice, CTSDUR_BA_F1,
865 cbFrameLength, byPktType,
866 wCurrentRate, bNeedAck,
869 /* Get CTS Frame body */
870 buf->data.duration = buf->duration_ba;
872 buf->data.frame_control =
873 cpu_to_le16(IEEE80211_FTYPE_CTL |
874 IEEE80211_STYPE_CTS);
876 buf->reserved2 = 0x0;
878 ether_addr_copy(buf->data.ra,
879 pDevice->abyCurrentNetAddr);
880 } else { /* if (byFBOption != AUTO_FB_NONE && uDMAIdx != TYPE_ATIMDMA && uDMAIdx != TYPE_BEACONDMA) */
881 struct vnt_cts *buf = pvCTS;
882 /* Get SignalField, ServiceField & Length */
883 vnt_get_phy_field(pDevice, uCTSFrameLen,
884 pDevice->byTopCCKBasicRate,
885 PK_TYPE_11B, &buf->b);
887 /* Get CTSDuration_ba */
889 s_uGetRTSCTSDuration(pDevice, CTSDUR_BA,
890 cbFrameLength, byPktType,
891 wCurrentRate, bNeedAck,
894 /* Get CTS Frame body */
895 buf->data.duration = buf->duration_ba;
897 buf->data.frame_control =
898 cpu_to_le16(IEEE80211_FTYPE_CTL |
899 IEEE80211_STYPE_CTS);
901 buf->reserved2 = 0x0;
902 ether_addr_copy(buf->data.ra,
903 pDevice->abyCurrentNetAddr);
911 * Generate FIFO control for MAC & Baseband controller
915 * pDevice - Pointer to adapter
916 * pTxDataHead - Transmit Data Buffer
917 * pTxBufHead - pTxBufHead
918 * pvRrvTime - pvRrvTime
921 * cbFrameSize - Transmit Data Length (Hdr+Payload+FCS)
922 * bNeedACK - If need ACK
923 * uDescIdx - Desc Index
930 * unsigned int cbFrameSize, Hdr+Payload+FCS
934 s_vGenerateTxParameter(
935 struct vnt_private *pDevice,
936 unsigned char byPktType,
937 struct vnt_tx_fifo_head *tx_buffer_head,
941 unsigned int cbFrameSize,
943 unsigned int uDMAIdx,
945 unsigned short wCurrentRate
948 u16 fifo_ctl = le16_to_cpu(tx_buffer_head->fifo_ctl);
949 bool bDisCRC = false;
950 unsigned char byFBOption = AUTO_FB_NONE;
952 tx_buffer_head->current_rate = cpu_to_le16(wCurrentRate);
954 if (fifo_ctl & FIFOCTL_CRCDIS)
957 if (fifo_ctl & FIFOCTL_AUTO_FB_0)
958 byFBOption = AUTO_FB_0;
959 else if (fifo_ctl & FIFOCTL_AUTO_FB_1)
960 byFBOption = AUTO_FB_1;
965 if (byPktType == PK_TYPE_11GB || byPktType == PK_TYPE_11GA) {
966 if (pvRTS) { /* RTS_need */
968 struct vnt_rrv_time_rts *buf = pvRrvTime;
970 buf->rts_rrv_time_aa = s_uGetRTSCTSRsvTime(pDevice, 2, byPktType, cbFrameSize, wCurrentRate);
971 buf->rts_rrv_time_ba = s_uGetRTSCTSRsvTime(pDevice, 1, byPktType, cbFrameSize, wCurrentRate);
972 buf->rts_rrv_time_bb = s_uGetRTSCTSRsvTime(pDevice, 0, byPktType, cbFrameSize, wCurrentRate);
973 buf->rrv_time_a = vnt_rxtx_rsvtime_le16(pDevice, byPktType, cbFrameSize, wCurrentRate, bNeedACK);
974 buf->rrv_time_b = vnt_rxtx_rsvtime_le16(pDevice, PK_TYPE_11B, cbFrameSize, pDevice->byTopCCKBasicRate, bNeedACK);
976 s_vFillRTSHead(pDevice, byPktType, pvRTS, cbFrameSize, bNeedACK, bDisCRC, psEthHeader, wCurrentRate, byFBOption);
977 } else {/* RTS_needless, PCF mode */
978 struct vnt_rrv_time_cts *buf = pvRrvTime;
980 buf->rrv_time_a = vnt_rxtx_rsvtime_le16(pDevice, byPktType, cbFrameSize, wCurrentRate, bNeedACK);
981 buf->rrv_time_b = vnt_rxtx_rsvtime_le16(pDevice, PK_TYPE_11B, cbFrameSize, pDevice->byTopCCKBasicRate, bNeedACK);
982 buf->cts_rrv_time_ba = s_uGetRTSCTSRsvTime(pDevice, 3, byPktType, cbFrameSize, wCurrentRate);
985 s_vFillCTSHead(pDevice, uDMAIdx, byPktType, pvCTS, cbFrameSize, bNeedACK, bDisCRC, wCurrentRate, byFBOption);
987 } else if (byPktType == PK_TYPE_11A) {
988 if (pvRTS) {/* RTS_need, non PCF mode */
989 struct vnt_rrv_time_ab *buf = pvRrvTime;
991 buf->rts_rrv_time = s_uGetRTSCTSRsvTime(pDevice, 2, byPktType, cbFrameSize, wCurrentRate);
992 buf->rrv_time = vnt_rxtx_rsvtime_le16(pDevice, byPktType, cbFrameSize, wCurrentRate, bNeedACK);
995 s_vFillRTSHead(pDevice, byPktType, pvRTS, cbFrameSize, bNeedACK, bDisCRC, psEthHeader, wCurrentRate, byFBOption);
996 } else if (!pvRTS) {/* RTS_needless, non PCF mode */
997 struct vnt_rrv_time_ab *buf = pvRrvTime;
999 buf->rrv_time = vnt_rxtx_rsvtime_le16(pDevice, PK_TYPE_11A, cbFrameSize, wCurrentRate, bNeedACK);
1001 } else if (byPktType == PK_TYPE_11B) {
1002 if (pvRTS) {/* RTS_need, non PCF mode */
1003 struct vnt_rrv_time_ab *buf = pvRrvTime;
1005 buf->rts_rrv_time = s_uGetRTSCTSRsvTime(pDevice, 0, byPktType, cbFrameSize, wCurrentRate);
1006 buf->rrv_time = vnt_rxtx_rsvtime_le16(pDevice, PK_TYPE_11B, cbFrameSize, wCurrentRate, bNeedACK);
1009 s_vFillRTSHead(pDevice, byPktType, pvRTS, cbFrameSize, bNeedACK, bDisCRC, psEthHeader, wCurrentRate, byFBOption);
1010 } else { /* RTS_needless, non PCF mode */
1011 struct vnt_rrv_time_ab *buf = pvRrvTime;
1013 buf->rrv_time = vnt_rxtx_rsvtime_le16(pDevice, PK_TYPE_11B, cbFrameSize, wCurrentRate, bNeedACK);
1019 s_cbFillTxBufHead(struct vnt_private *pDevice, unsigned char byPktType,
1020 unsigned char *pbyTxBufferAddr,
1021 unsigned int uDMAIdx, struct vnt_tx_desc *pHeadTD,
1022 unsigned int is_pspoll)
1024 struct vnt_td_info *td_info = pHeadTD->td_info;
1025 struct sk_buff *skb = td_info->skb;
1026 struct ieee80211_tx_info *info = IEEE80211_SKB_CB(skb);
1027 struct ieee80211_hdr *hdr = (struct ieee80211_hdr *)skb->data;
1028 struct vnt_tx_fifo_head *tx_buffer_head =
1029 (struct vnt_tx_fifo_head *)td_info->buf;
1030 u16 fifo_ctl = le16_to_cpu(tx_buffer_head->fifo_ctl);
1031 unsigned int cbFrameSize;
1033 unsigned char *pbyBuffer;
1034 unsigned int uLength = 0;
1035 unsigned int cbMICHDR = 0;
1036 unsigned int uMACfragNum = 1;
1037 unsigned int uPadding = 0;
1038 unsigned int cbReqCount = 0;
1039 bool bNeedACK = (bool)(fifo_ctl & FIFOCTL_NEEDACK);
1040 bool bRTS = (bool)(fifo_ctl & FIFOCTL_RTS);
1041 struct vnt_tx_desc *ptdCurr;
1042 unsigned int cbHeaderLength = 0;
1044 struct vnt_mic_hdr *pMICHDR;
1048 unsigned short wTxBufSize; /* FFinfo size */
1049 unsigned char byFBOption = AUTO_FB_NONE;
1051 pvRrvTime = pMICHDR = pvRTS = pvCTS = pvTxDataHd = NULL;
1053 cbFrameSize = skb->len + 4;
1055 if (info->control.hw_key) {
1056 switch (info->control.hw_key->cipher) {
1057 case WLAN_CIPHER_SUITE_CCMP:
1058 cbMICHDR = sizeof(struct vnt_mic_hdr);
1063 cbFrameSize += info->control.hw_key->icv_len;
1065 if (pDevice->byLocalID > REV_ID_VT3253_A1) {
1066 /* MAC Header should be padding 0 to DW alignment. */
1067 uPadding = 4 - (ieee80211_get_hdrlen_from_skb(skb) % 4);
1073 * Use for AUTO FALL BACK
1075 if (fifo_ctl & FIFOCTL_AUTO_FB_0)
1076 byFBOption = AUTO_FB_0;
1077 else if (fifo_ctl & FIFOCTL_AUTO_FB_1)
1078 byFBOption = AUTO_FB_1;
1080 /* Set RrvTime/RTS/CTS Buffer */
1081 wTxBufSize = sizeof(struct vnt_tx_fifo_head);
1082 if (byPktType == PK_TYPE_11GB || byPktType == PK_TYPE_11GA) {/* 802.11g packet */
1084 if (byFBOption == AUTO_FB_NONE) {
1085 if (bRTS) {/* RTS_need */
1086 pvRrvTime = (void *)(pbyTxBufferAddr + wTxBufSize);
1087 pMICHDR = (struct vnt_mic_hdr *)(pbyTxBufferAddr + wTxBufSize + sizeof(struct vnt_rrv_time_rts));
1088 pvRTS = (void *)(pbyTxBufferAddr + wTxBufSize + sizeof(struct vnt_rrv_time_rts) + cbMICHDR);
1090 pvTxDataHd = (void *)(pbyTxBufferAddr + wTxBufSize + sizeof(struct vnt_rrv_time_rts) +
1091 cbMICHDR + sizeof(struct vnt_rts_g));
1092 cbHeaderLength = wTxBufSize + sizeof(struct vnt_rrv_time_rts) +
1093 cbMICHDR + sizeof(struct vnt_rts_g) +
1094 sizeof(struct vnt_tx_datahead_g);
1095 } else { /* RTS_needless */
1096 pvRrvTime = (void *)(pbyTxBufferAddr + wTxBufSize);
1097 pMICHDR = (struct vnt_mic_hdr *)(pbyTxBufferAddr + wTxBufSize + sizeof(struct vnt_rrv_time_cts));
1099 pvCTS = (void *) (pbyTxBufferAddr + wTxBufSize + sizeof(struct vnt_rrv_time_cts) + cbMICHDR);
1100 pvTxDataHd = (void *)(pbyTxBufferAddr + wTxBufSize +
1101 sizeof(struct vnt_rrv_time_cts) + cbMICHDR + sizeof(struct vnt_cts));
1102 cbHeaderLength = wTxBufSize + sizeof(struct vnt_rrv_time_cts) +
1103 cbMICHDR + sizeof(struct vnt_cts) + sizeof(struct vnt_tx_datahead_g);
1106 /* Auto Fall Back */
1107 if (bRTS) {/* RTS_need */
1108 pvRrvTime = (void *)(pbyTxBufferAddr + wTxBufSize);
1109 pMICHDR = (struct vnt_mic_hdr *)(pbyTxBufferAddr + wTxBufSize + sizeof(struct vnt_rrv_time_rts));
1110 pvRTS = (void *) (pbyTxBufferAddr + wTxBufSize + sizeof(struct vnt_rrv_time_rts) + cbMICHDR);
1112 pvTxDataHd = (void *)(pbyTxBufferAddr + wTxBufSize + sizeof(struct vnt_rrv_time_rts) +
1113 cbMICHDR + sizeof(struct vnt_rts_g_fb));
1114 cbHeaderLength = wTxBufSize + sizeof(struct vnt_rrv_time_rts) +
1115 cbMICHDR + sizeof(struct vnt_rts_g_fb) + sizeof(struct vnt_tx_datahead_g_fb);
1116 } else { /* RTS_needless */
1117 pvRrvTime = (void *)(pbyTxBufferAddr + wTxBufSize);
1118 pMICHDR = (struct vnt_mic_hdr *)(pbyTxBufferAddr + wTxBufSize + sizeof(struct vnt_rrv_time_cts));
1120 pvCTS = (void *)(pbyTxBufferAddr + wTxBufSize + sizeof(struct vnt_rrv_time_cts) + cbMICHDR);
1121 pvTxDataHd = (void *)(pbyTxBufferAddr + wTxBufSize + sizeof(struct vnt_rrv_time_cts) +
1122 cbMICHDR + sizeof(struct vnt_cts_fb));
1123 cbHeaderLength = wTxBufSize + sizeof(struct vnt_rrv_time_cts) +
1124 cbMICHDR + sizeof(struct vnt_cts_fb) + sizeof(struct vnt_tx_datahead_g_fb);
1126 } /* Auto Fall Back */
1127 } else {/* 802.11a/b packet */
1129 if (byFBOption == AUTO_FB_NONE) {
1131 pvRrvTime = (void *)(pbyTxBufferAddr + wTxBufSize);
1132 pMICHDR = (struct vnt_mic_hdr *)(pbyTxBufferAddr + wTxBufSize + sizeof(struct vnt_rrv_time_ab));
1133 pvRTS = (void *)(pbyTxBufferAddr + wTxBufSize + sizeof(struct vnt_rrv_time_ab) + cbMICHDR);
1135 pvTxDataHd = (void *)(pbyTxBufferAddr + wTxBufSize +
1136 sizeof(struct vnt_rrv_time_ab) + cbMICHDR + sizeof(struct vnt_rts_ab));
1137 cbHeaderLength = wTxBufSize + sizeof(struct vnt_rrv_time_ab) +
1138 cbMICHDR + sizeof(struct vnt_rts_ab) + sizeof(struct vnt_tx_datahead_ab);
1139 } else { /* RTS_needless, need MICHDR */
1140 pvRrvTime = (void *)(pbyTxBufferAddr + wTxBufSize);
1141 pMICHDR = (struct vnt_mic_hdr *)(pbyTxBufferAddr + wTxBufSize + sizeof(struct vnt_rrv_time_ab));
1144 pvTxDataHd = (void *)(pbyTxBufferAddr + wTxBufSize + sizeof(struct vnt_rrv_time_ab) + cbMICHDR);
1145 cbHeaderLength = wTxBufSize + sizeof(struct vnt_rrv_time_ab) +
1146 cbMICHDR + sizeof(struct vnt_tx_datahead_ab);
1149 /* Auto Fall Back */
1150 if (bRTS) { /* RTS_need */
1151 pvRrvTime = (void *)(pbyTxBufferAddr + wTxBufSize);
1152 pMICHDR = (struct vnt_mic_hdr *)(pbyTxBufferAddr + wTxBufSize + sizeof(struct vnt_rrv_time_ab));
1153 pvRTS = (void *)(pbyTxBufferAddr + wTxBufSize + sizeof(struct vnt_rrv_time_ab) + cbMICHDR);
1155 pvTxDataHd = (void *)(pbyTxBufferAddr + wTxBufSize +
1156 sizeof(struct vnt_rrv_time_ab) + cbMICHDR + sizeof(struct vnt_rts_a_fb));
1157 cbHeaderLength = wTxBufSize + sizeof(struct vnt_rrv_time_ab) +
1158 cbMICHDR + sizeof(struct vnt_rts_a_fb) + sizeof(struct vnt_tx_datahead_a_fb);
1159 } else { /* RTS_needless */
1160 pvRrvTime = (void *)(pbyTxBufferAddr + wTxBufSize);
1161 pMICHDR = (struct vnt_mic_hdr *)(pbyTxBufferAddr + wTxBufSize + sizeof(struct vnt_rrv_time_ab));
1164 pvTxDataHd = (void *)(pbyTxBufferAddr + wTxBufSize + sizeof(struct vnt_rrv_time_ab) + cbMICHDR);
1165 cbHeaderLength = wTxBufSize + sizeof(struct vnt_rrv_time_ab) +
1166 cbMICHDR + sizeof(struct vnt_tx_datahead_a_fb);
1168 } /* Auto Fall Back */
1171 td_info->mic_hdr = pMICHDR;
1173 memset((void *)(pbyTxBufferAddr + wTxBufSize), 0, (cbHeaderLength - wTxBufSize));
1175 /* Fill FIFO,RrvTime,RTS,and CTS */
1176 s_vGenerateTxParameter(pDevice, byPktType, tx_buffer_head, pvRrvTime, pvRTS, pvCTS,
1177 cbFrameSize, bNeedACK, uDMAIdx, hdr, pDevice->wCurrentRate);
1179 uDuration = s_uFillDataHead(pDevice, byPktType, pvTxDataHd, cbFrameSize, uDMAIdx, bNeedACK,
1180 0, 0, uMACfragNum, byFBOption, pDevice->wCurrentRate, is_pspoll);
1182 hdr->duration_id = uDuration;
1184 cbReqCount = cbHeaderLength + uPadding + skb->len;
1185 pbyBuffer = (unsigned char *)pHeadTD->td_info->buf;
1186 uLength = cbHeaderLength + uPadding;
1188 /* Copy the Packet into a tx Buffer */
1189 memcpy((pbyBuffer + uLength), skb->data, skb->len);
1193 ptdCurr->td_info->req_count = (u16)cbReqCount;
1195 return cbHeaderLength;
1198 static void vnt_fill_txkey(struct ieee80211_hdr *hdr, u8 *key_buffer,
1199 struct ieee80211_key_conf *tx_key,
1200 struct sk_buff *skb, u16 payload_len,
1201 struct vnt_mic_hdr *mic_hdr)
1204 u8 *iv = ((u8 *)hdr + ieee80211_get_hdrlen_from_skb(skb));
1206 /* strip header and icv len from payload */
1207 payload_len -= ieee80211_get_hdrlen_from_skb(skb);
1208 payload_len -= tx_key->icv_len;
1210 switch (tx_key->cipher) {
1211 case WLAN_CIPHER_SUITE_WEP40:
1212 case WLAN_CIPHER_SUITE_WEP104:
1213 memcpy(key_buffer, iv, 3);
1214 memcpy(key_buffer + 3, tx_key->key, tx_key->keylen);
1216 if (tx_key->keylen == WLAN_KEY_LEN_WEP40) {
1217 memcpy(key_buffer + 8, iv, 3);
1218 memcpy(key_buffer + 11,
1219 tx_key->key, WLAN_KEY_LEN_WEP40);
1223 case WLAN_CIPHER_SUITE_TKIP:
1224 ieee80211_get_tkip_p2k(tx_key, skb, key_buffer);
1227 case WLAN_CIPHER_SUITE_CCMP:
1233 mic_hdr->payload_len = cpu_to_be16(payload_len);
1234 ether_addr_copy(mic_hdr->mic_addr2, hdr->addr2);
1236 pn64 = atomic64_read(&tx_key->tx_pn);
1237 mic_hdr->ccmp_pn[5] = pn64;
1238 mic_hdr->ccmp_pn[4] = pn64 >> 8;
1239 mic_hdr->ccmp_pn[3] = pn64 >> 16;
1240 mic_hdr->ccmp_pn[2] = pn64 >> 24;
1241 mic_hdr->ccmp_pn[1] = pn64 >> 32;
1242 mic_hdr->ccmp_pn[0] = pn64 >> 40;
1244 if (ieee80211_has_a4(hdr->frame_control))
1245 mic_hdr->hlen = cpu_to_be16(28);
1247 mic_hdr->hlen = cpu_to_be16(22);
1249 ether_addr_copy(mic_hdr->addr1, hdr->addr1);
1250 ether_addr_copy(mic_hdr->addr2, hdr->addr2);
1251 ether_addr_copy(mic_hdr->addr3, hdr->addr3);
1253 mic_hdr->frame_control = cpu_to_le16(
1254 le16_to_cpu(hdr->frame_control) & 0xc78f);
1255 mic_hdr->seq_ctrl = cpu_to_le16(
1256 le16_to_cpu(hdr->seq_ctrl) & 0xf);
1258 if (ieee80211_has_a4(hdr->frame_control))
1259 ether_addr_copy(mic_hdr->addr4, hdr->addr4);
1261 memcpy(key_buffer, tx_key->key, WLAN_KEY_LEN_CCMP);
1269 int vnt_generate_fifo_header(struct vnt_private *priv, u32 dma_idx,
1270 struct vnt_tx_desc *head_td, struct sk_buff *skb)
1272 struct vnt_td_info *td_info = head_td->td_info;
1273 struct ieee80211_tx_info *info = IEEE80211_SKB_CB(skb);
1274 struct ieee80211_tx_rate *tx_rate = &info->control.rates[0];
1275 struct ieee80211_rate *rate;
1276 struct ieee80211_key_conf *tx_key;
1277 struct ieee80211_hdr *hdr;
1278 struct vnt_tx_fifo_head *tx_buffer_head =
1279 (struct vnt_tx_fifo_head *)td_info->buf;
1280 u16 tx_body_size = skb->len, current_rate;
1282 bool is_pspoll = false;
1284 memset(tx_buffer_head, 0, sizeof(*tx_buffer_head));
1286 hdr = (struct ieee80211_hdr *)(skb->data);
1288 rate = ieee80211_get_tx_rate(priv->hw, info);
1290 current_rate = rate->hw_value;
1291 if (priv->wCurrentRate != current_rate &&
1292 !(priv->hw->conf.flags & IEEE80211_CONF_OFFCHANNEL)) {
1293 priv->wCurrentRate = current_rate;
1295 RFbSetPower(priv, priv->wCurrentRate,
1296 priv->hw->conf.chandef.chan->hw_value);
1299 if (current_rate > RATE_11M) {
1300 if (info->band == NL80211_BAND_5GHZ) {
1301 pkt_type = PK_TYPE_11A;
1303 if (tx_rate->flags & IEEE80211_TX_RC_USE_CTS_PROTECT)
1304 pkt_type = PK_TYPE_11GB;
1306 pkt_type = PK_TYPE_11GA;
1309 pkt_type = PK_TYPE_11B;
1312 /*Set fifo controls */
1313 if (pkt_type == PK_TYPE_11A)
1314 tx_buffer_head->fifo_ctl = 0;
1315 else if (pkt_type == PK_TYPE_11B)
1316 tx_buffer_head->fifo_ctl = cpu_to_le16(FIFOCTL_11B);
1317 else if (pkt_type == PK_TYPE_11GB)
1318 tx_buffer_head->fifo_ctl = cpu_to_le16(FIFOCTL_11GB);
1319 else if (pkt_type == PK_TYPE_11GA)
1320 tx_buffer_head->fifo_ctl = cpu_to_le16(FIFOCTL_11GA);
1322 /* generate interrupt */
1323 tx_buffer_head->fifo_ctl |= cpu_to_le16(FIFOCTL_GENINT);
1325 if (!ieee80211_is_data(hdr->frame_control)) {
1326 tx_buffer_head->fifo_ctl |= cpu_to_le16(FIFOCTL_TMOEN);
1327 tx_buffer_head->fifo_ctl |= cpu_to_le16(FIFOCTL_ISDMA0);
1328 tx_buffer_head->time_stamp =
1329 cpu_to_le16(DEFAULT_MGN_LIFETIME_RES_64us);
1331 tx_buffer_head->time_stamp =
1332 cpu_to_le16(DEFAULT_MSDU_LIFETIME_RES_64us);
1335 if (!(info->flags & IEEE80211_TX_CTL_NO_ACK))
1336 tx_buffer_head->fifo_ctl |= cpu_to_le16(FIFOCTL_NEEDACK);
1338 if (ieee80211_has_retry(hdr->frame_control))
1339 tx_buffer_head->fifo_ctl |= cpu_to_le16(FIFOCTL_LRETRY);
1341 if (tx_rate->flags & IEEE80211_TX_RC_USE_SHORT_PREAMBLE)
1342 priv->byPreambleType = PREAMBLE_SHORT;
1344 priv->byPreambleType = PREAMBLE_LONG;
1346 if (tx_rate->flags & IEEE80211_TX_RC_USE_RTS_CTS)
1347 tx_buffer_head->fifo_ctl |= cpu_to_le16(FIFOCTL_RTS);
1349 if (ieee80211_has_a4(hdr->frame_control)) {
1350 tx_buffer_head->fifo_ctl |= cpu_to_le16(FIFOCTL_LHEAD);
1351 priv->bLongHeader = true;
1354 if (info->flags & IEEE80211_TX_CTL_NO_PS_BUFFER)
1357 tx_buffer_head->frag_ctl =
1358 cpu_to_le16(ieee80211_get_hdrlen_from_skb(skb) << 10);
1360 if (info->control.hw_key) {
1361 tx_key = info->control.hw_key;
1363 switch (info->control.hw_key->cipher) {
1364 case WLAN_CIPHER_SUITE_WEP40:
1365 case WLAN_CIPHER_SUITE_WEP104:
1366 tx_buffer_head->frag_ctl |= cpu_to_le16(FRAGCTL_LEGACY);
1368 case WLAN_CIPHER_SUITE_TKIP:
1369 tx_buffer_head->frag_ctl |= cpu_to_le16(FRAGCTL_TKIP);
1371 case WLAN_CIPHER_SUITE_CCMP:
1372 tx_buffer_head->frag_ctl |= cpu_to_le16(FRAGCTL_AES);
1378 tx_buffer_head->current_rate = cpu_to_le16(current_rate);
1380 /* legacy rates TODO use ieee80211_tx_rate */
1381 if (current_rate >= RATE_18M && ieee80211_is_data(hdr->frame_control)) {
1382 if (priv->byAutoFBCtrl == AUTO_FB_0)
1383 tx_buffer_head->fifo_ctl |=
1384 cpu_to_le16(FIFOCTL_AUTO_FB_0);
1385 else if (priv->byAutoFBCtrl == AUTO_FB_1)
1386 tx_buffer_head->fifo_ctl |=
1387 cpu_to_le16(FIFOCTL_AUTO_FB_1);
1390 tx_buffer_head->frag_ctl |= cpu_to_le16(FRAGCTL_NONFRAG);
1392 s_cbFillTxBufHead(priv, pkt_type, (u8 *)tx_buffer_head,
1393 dma_idx, head_td, is_pspoll);
1395 if (info->control.hw_key) {
1396 tx_key = info->control.hw_key;
1397 if (tx_key->keylen > 0)
1398 vnt_fill_txkey(hdr, tx_buffer_head->tx_key,
1399 tx_key, skb, tx_body_size, td_info->mic_hdr);
1405 static int vnt_beacon_xmit(struct vnt_private *priv,
1406 struct sk_buff *skb)
1408 struct vnt_tx_short_buf_head *short_head =
1409 (struct vnt_tx_short_buf_head *)priv->tx_beacon_bufs;
1410 struct ieee80211_mgmt *mgmt_hdr = (struct ieee80211_mgmt *)
1411 (priv->tx_beacon_bufs + sizeof(*short_head));
1412 struct ieee80211_tx_info *info;
1413 u32 frame_size = skb->len + 4;
1416 memset(priv->tx_beacon_bufs, 0, sizeof(*short_head));
1418 if (priv->byBBType == BB_TYPE_11A) {
1419 current_rate = RATE_6M;
1421 /* Get SignalField,ServiceField,Length */
1422 vnt_get_phy_field(priv, frame_size, current_rate,
1423 PK_TYPE_11A, &short_head->ab);
1425 /* Get Duration and TimeStampOff */
1426 short_head->duration =
1427 cpu_to_le16((u16)s_uGetDataDuration(priv, DATADUR_B,
1428 frame_size, PK_TYPE_11A, current_rate,
1429 false, 0, 0, 1, AUTO_FB_NONE));
1431 short_head->time_stamp_off =
1432 vnt_time_stamp_off(priv, current_rate);
1434 current_rate = RATE_1M;
1435 short_head->fifo_ctl |= cpu_to_le16(FIFOCTL_11B);
1437 /* Get SignalField,ServiceField,Length */
1438 vnt_get_phy_field(priv, frame_size, current_rate,
1439 PK_TYPE_11B, &short_head->ab);
1441 /* Get Duration and TimeStampOff */
1442 short_head->duration =
1443 cpu_to_le16((u16)s_uGetDataDuration(priv, DATADUR_B,
1444 frame_size, PK_TYPE_11B, current_rate,
1445 false, 0, 0, 1, AUTO_FB_NONE));
1447 short_head->time_stamp_off =
1448 vnt_time_stamp_off(priv, current_rate);
1451 short_head->fifo_ctl |= cpu_to_le16(FIFOCTL_GENINT);
1454 memcpy(mgmt_hdr, skb->data, skb->len);
1456 /* time stamp always 0 */
1457 mgmt_hdr->u.beacon.timestamp = 0;
1459 info = IEEE80211_SKB_CB(skb);
1460 if (info->flags & IEEE80211_TX_CTL_ASSIGN_SEQ) {
1461 struct ieee80211_hdr *hdr = (struct ieee80211_hdr *)mgmt_hdr;
1463 hdr->duration_id = 0;
1464 hdr->seq_ctrl = cpu_to_le16(priv->wSeqCounter << 4);
1467 priv->wSeqCounter++;
1468 if (priv->wSeqCounter > 0x0fff)
1469 priv->wSeqCounter = 0;
1471 priv->wBCNBufLen = sizeof(*short_head) + skb->len;
1473 MACvSetCurrBCNTxDescAddr(priv->PortOffset, priv->tx_beacon_dma);
1475 MACvSetCurrBCNLength(priv->PortOffset, priv->wBCNBufLen);
1476 /* Set auto Transmit on */
1477 MACvRegBitsOn(priv->PortOffset, MAC_REG_TCR, TCR_AUTOBCNTX);
1478 /* Poll Transmit the adapter */
1479 MACvTransmitBCN(priv->PortOffset);
1484 int vnt_beacon_make(struct vnt_private *priv, struct ieee80211_vif *vif)
1486 struct sk_buff *beacon;
1488 beacon = ieee80211_beacon_get(priv->hw, vif);
1492 if (vnt_beacon_xmit(priv, beacon)) {
1493 ieee80211_free_txskb(priv->hw, beacon);
1500 int vnt_beacon_enable(struct vnt_private *priv, struct ieee80211_vif *vif,
1501 struct ieee80211_bss_conf *conf)
1503 VNSvOutPortB(priv->PortOffset + MAC_REG_TFTCTL, TFTCTL_TSFCNTRST);
1505 VNSvOutPortB(priv->PortOffset + MAC_REG_TFTCTL, TFTCTL_TSFCNTREN);
1507 CARDvSetFirstNextTBTT(priv, conf->beacon_int);
1509 CARDbSetBeaconPeriod(priv, conf->beacon_int);
1511 return vnt_beacon_make(priv, vif);