Staging: rt2870:: rtusb_bulk.c: Checkpatch cleanup
[linux-2.6-block.git] / drivers / staging / rt2870 / common / rtusb_bulk.c
CommitLineData
ca97b838 1/*
c55519ff
GKH
2 *************************************************************************
3 * Ralink Tech Inc.
4 * 5F., No.36, Taiyuan St., Jhubei City,
5 * Hsinchu County 302,
6 * Taiwan, R.O.C.
7 *
8 * (c) Copyright 2002-2007, Ralink Technology, Inc.
9 *
10 * This program is free software; you can redistribute it and/or modify *
11 * it under the terms of the GNU General Public License as published by *
12 * the Free Software Foundation; either version 2 of the License, or *
13 * (at your option) any later version. *
14 * *
15 * This program is distributed in the hope that it will be useful, *
16 * but WITHOUT ANY WARRANTY; without even the implied warranty of *
17 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
18 * GNU General Public License for more details. *
19 * *
20 * You should have received a copy of the GNU General Public License *
21 * along with this program; if not, write to the *
22 * Free Software Foundation, Inc., *
23 * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
24 * *
25 *************************************************************************
26
27 Module Name:
28 rtusb_bulk.c
29
30 Abstract:
31
32 Revision History:
33 Who When What
34 -------- ---------- ----------------------------------------------
35 Name Date Modification logs
36 Paul Lin 06-25-2004 created
37
38*/
39
ca97b838
BZ
40#ifdef RTMP_MAC_USB
41
c55519ff 42#include "../rt_config.h"
9f548a2a 43/* Match total 6 bulkout endpoint to corresponding queue. */
51126deb 44u8 EpToQueue[6] =
66cd8d6e 45 { FIFO_EDCA, FIFO_EDCA, FIFO_EDCA, FIFO_EDCA, FIFO_EDCA, FIFO_MGMT };
c55519ff 46
9f548a2a 47/*static BOOLEAN SingleBulkOut = FALSE; */
c55519ff 48
66cd8d6e
BZ
49void RTUSB_FILL_BULK_URB(struct urb *pUrb,
50 struct usb_device *pUsb_Dev,
51 unsigned int bulkpipe,
52 void *pTransferBuf,
53 int BufSize, usb_complete_t Complete, void *pContext)
c55519ff
GKH
54{
55
66cd8d6e
BZ
56 usb_fill_bulk_urb(pUrb, pUsb_Dev, bulkpipe, pTransferBuf, BufSize,
57 (usb_complete_t) Complete, pContext);
c55519ff
GKH
58
59}
60
62eb734b
BZ
61void RTUSBInitTxDesc(struct rt_rtmp_adapter *pAd,
62 struct rt_tx_context *pTxContext,
51126deb 63 u8 BulkOutPipeId, IN usb_complete_t Func)
c55519ff 64{
66cd8d6e 65 PURB pUrb;
51126deb 66 u8 *pSrc = NULL;
8a10a546 67 struct os_cookie *pObj = (struct os_cookie *)pAd->OS_Cookie;
c55519ff
GKH
68
69 pUrb = pTxContext->pUrb;
70 ASSERT(pUrb);
71
9f548a2a 72 /* Store BulkOut PipeId */
c55519ff
GKH
73 pTxContext->BulkOutPipeId = BulkOutPipeId;
74
66cd8d6e 75 if (pTxContext->bAggregatible) {
c55519ff 76 pSrc = &pTxContext->TransferBuffer->Aggregation[2];
66cd8d6e
BZ
77 } else {
78 pSrc =
51126deb 79 (u8 *)pTxContext->TransferBuffer->field.WirelessPacket;
c55519ff
GKH
80 }
81
9f548a2a 82 /*Initialize a tx bulk urb */
c55519ff 83 RTUSB_FILL_BULK_URB(pUrb,
66cd8d6e
BZ
84 pObj->pUsb_Dev,
85 usb_sndbulkpipe(pObj->pUsb_Dev,
86 pAd->BulkOutEpAddr[BulkOutPipeId]),
87 pSrc, pTxContext->BulkOutSize, Func, pTxContext);
c55519ff 88
c55519ff 89 if (pTxContext->bAggregatible)
66cd8d6e
BZ
90 pUrb->transfer_dma =
91 (pTxContext->data_dma + TX_BUFFER_NORMSIZE + 2);
c55519ff 92 else
66cd8d6e 93 pUrb->transfer_dma = pTxContext->data_dma;
c55519ff
GKH
94
95 pUrb->transfer_flags |= URB_NO_TRANSFER_DMA_MAP;
c55519ff
GKH
96
97}
98
62eb734b
BZ
99void RTUSBInitHTTxDesc(struct rt_rtmp_adapter *pAd,
100 struct rt_ht_tx_context *pTxContext,
51126deb
BZ
101 u8 BulkOutPipeId,
102 unsigned long BulkOutSize, IN usb_complete_t Func)
c55519ff 103{
66cd8d6e 104 PURB pUrb;
51126deb 105 u8 *pSrc = NULL;
8a10a546 106 struct os_cookie *pObj = (struct os_cookie *)pAd->OS_Cookie;
c55519ff
GKH
107
108 pUrb = pTxContext->pUrb;
109 ASSERT(pUrb);
110
9f548a2a 111 /* Store BulkOut PipeId */
c55519ff
GKH
112 pTxContext->BulkOutPipeId = BulkOutPipeId;
113
66cd8d6e
BZ
114 pSrc =
115 &pTxContext->TransferBuffer->field.WirelessPacket[pTxContext->
116 NextBulkOutPosition];
c55519ff 117
9f548a2a 118 /*Initialize a tx bulk urb */
c55519ff 119 RTUSB_FILL_BULK_URB(pUrb,
66cd8d6e
BZ
120 pObj->pUsb_Dev,
121 usb_sndbulkpipe(pObj->pUsb_Dev,
122 pAd->BulkOutEpAddr[BulkOutPipeId]),
123 pSrc, BulkOutSize, Func, pTxContext);
124
125 pUrb->transfer_dma =
126 (pTxContext->data_dma + pTxContext->NextBulkOutPosition);
c55519ff 127 pUrb->transfer_flags |= URB_NO_TRANSFER_DMA_MAP;
c55519ff
GKH
128
129}
130
62eb734b 131void RTUSBInitRxDesc(struct rt_rtmp_adapter *pAd, struct rt_rx_context *pRxContext)
c55519ff 132{
66cd8d6e 133 PURB pUrb;
8a10a546 134 struct os_cookie *pObj = (struct os_cookie *)pAd->OS_Cookie;
51126deb 135 unsigned long RX_bulk_size;
c55519ff
GKH
136
137 pUrb = pRxContext->pUrb;
138 ASSERT(pUrb);
139
66cd8d6e 140 if (pAd->BulkInMaxPacketSize == 64)
c55519ff
GKH
141 RX_bulk_size = 4096;
142 else
143 RX_bulk_size = MAX_RXBULK_SIZE;
144
9f548a2a 145 /*Initialize a rx bulk urb */
c55519ff 146 RTUSB_FILL_BULK_URB(pUrb,
66cd8d6e
BZ
147 pObj->pUsb_Dev,
148 usb_rcvbulkpipe(pObj->pUsb_Dev, pAd->BulkInEpAddr),
149 &(pRxContext->
150 TransferBuffer[pAd->NextRxBulkInPosition]),
151 RX_bulk_size - (pAd->NextRxBulkInPosition),
152 (usb_complete_t) RTUSBBulkRxComplete,
153 (void *)pRxContext);
154
155 pUrb->transfer_dma = pRxContext->data_dma + pAd->NextRxBulkInPosition;
c55519ff 156 pUrb->transfer_flags |= URB_NO_TRANSFER_DMA_MAP;
c55519ff 157
c55519ff
GKH
158}
159
160/*
161 ========================================================================
162
163 Routine Description:
164
165 Arguments:
166
167 Return Value:
168
169 Note:
170
171 ========================================================================
172*/
173
174#define BULK_OUT_LOCK(pLock, IrqFlags) \
d24e4497 175 if (1 /*!(in_interrupt() & 0xffff0000)*/) \
c55519ff
GKH
176 RTMP_IRQ_LOCK((pLock), IrqFlags);
177
178#define BULK_OUT_UNLOCK(pLock, IrqFlags) \
d24e4497 179 if (1 /*!(in_interrupt() & 0xffff0000)*/) \
c55519ff
GKH
180 RTMP_IRQ_UNLOCK((pLock), IrqFlags);
181
62eb734b 182void RTUSBBulkOutDataPacket(struct rt_rtmp_adapter *pAd,
51126deb 183 u8 BulkOutPipeId, u8 Index)
c55519ff
GKH
184{
185
62eb734b 186 struct rt_ht_tx_context *pHTTXContext;
66cd8d6e
BZ
187 PURB pUrb;
188 int ret = 0;
62eb734b 189 struct rt_txinfo *pTxInfo, *pLastTxInfo = NULL;
d24e4497 190 struct rt_txwi *pTxWI;
51126deb 191 unsigned long TmpBulkEndPos, ThisBulkSize;
66cd8d6e 192 unsigned long IrqFlags = 0, IrqFlags2 = 0;
51126deb 193 u8 *pWirelessPkt, *pAppendant;
66cd8d6e 194 BOOLEAN bTxQLastRound = FALSE;
51126deb 195 u8 allzero[4] = { 0x0, 0x0, 0x0, 0x0 };
c55519ff
GKH
196
197 BULK_OUT_LOCK(&pAd->BulkOutLock[BulkOutPipeId], IrqFlags);
66cd8d6e
BZ
198 if ((pAd->BulkOutPending[BulkOutPipeId] == TRUE)
199 || RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_NEED_STOP_TX)) {
c55519ff
GKH
200 BULK_OUT_UNLOCK(&pAd->BulkOutLock[BulkOutPipeId], IrqFlags);
201 return;
202 }
203 pAd->BulkOutPending[BulkOutPipeId] = TRUE;
204
205 if (!OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_MEDIA_STATE_CONNECTED)
66cd8d6e 206 ) {
c55519ff
GKH
207 pAd->BulkOutPending[BulkOutPipeId] = FALSE;
208 BULK_OUT_UNLOCK(&pAd->BulkOutLock[BulkOutPipeId], IrqFlags);
209 return;
210 }
211 BULK_OUT_UNLOCK(&pAd->BulkOutLock[BulkOutPipeId], IrqFlags);
212
c55519ff
GKH
213 pHTTXContext = &(pAd->TxContext[BulkOutPipeId]);
214
215 BULK_OUT_LOCK(&pAd->TxContextQueueLock[BulkOutPipeId], IrqFlags2);
66cd8d6e
BZ
216 if ((pHTTXContext->ENextBulkOutPosition ==
217 pHTTXContext->CurWritePosition)
218 || ((pHTTXContext->ENextBulkOutPosition - 8) ==
219 pHTTXContext->CurWritePosition)) {
220 BULK_OUT_UNLOCK(&pAd->TxContextQueueLock[BulkOutPipeId],
221 IrqFlags2);
c55519ff
GKH
222
223 BULK_OUT_LOCK(&pAd->BulkOutLock[BulkOutPipeId], IrqFlags);
224 pAd->BulkOutPending[BulkOutPipeId] = FALSE;
225
9f548a2a 226 /* Clear Data flag */
66cd8d6e
BZ
227 RTUSB_CLEAR_BULK_FLAG(pAd,
228 (fRTUSB_BULK_OUT_DATA_FRAG <<
229 BulkOutPipeId));
230 RTUSB_CLEAR_BULK_FLAG(pAd,
231 (fRTUSB_BULK_OUT_DATA_NORMAL <<
232 BulkOutPipeId));
c55519ff
GKH
233
234 BULK_OUT_UNLOCK(&pAd->BulkOutLock[BulkOutPipeId], IrqFlags);
235 return;
236 }
9f548a2a 237 /* Clear Data flag */
66cd8d6e
BZ
238 RTUSB_CLEAR_BULK_FLAG(pAd,
239 (fRTUSB_BULK_OUT_DATA_FRAG << BulkOutPipeId));
240 RTUSB_CLEAR_BULK_FLAG(pAd,
241 (fRTUSB_BULK_OUT_DATA_NORMAL << BulkOutPipeId));
c55519ff 242
9f548a2a
BZ
243 /*DBGPRINT(RT_DEBUG_TRACE,("BulkOut-B:I=0x%lx, CWPos=%ld, CWRPos=%ld, NBPos=%ld, ENBPos=%ld, bCopy=%d!\n", in_interrupt(), */
244 /* pHTTXContext->CurWritePosition, pHTTXContext->CurWriteRealPos, pHTTXContext->NextBulkOutPosition, */
245 /* pHTTXContext->ENextBulkOutPosition, pHTTXContext->bCopySavePad)); */
c55519ff
GKH
246 pHTTXContext->NextBulkOutPosition = pHTTXContext->ENextBulkOutPosition;
247 ThisBulkSize = 0;
248 TmpBulkEndPos = pHTTXContext->NextBulkOutPosition;
249 pWirelessPkt = &pHTTXContext->TransferBuffer->field.WirelessPacket[0];
250
66cd8d6e
BZ
251 if ((pHTTXContext->bCopySavePad == TRUE)) {
252 if (RTMPEqualMemory(pHTTXContext->SavedPad, allzero, 4)) {
253 DBGPRINT_RAW(RT_DEBUG_ERROR,
254 ("e1, allzero : %x %x %x %x %x %x %x %x \n",
255 pHTTXContext->SavedPad[0],
256 pHTTXContext->SavedPad[1],
257 pHTTXContext->SavedPad[2],
258 pHTTXContext->SavedPad[3]
259 , pHTTXContext->SavedPad[4],
260 pHTTXContext->SavedPad[5],
261 pHTTXContext->SavedPad[6],
262 pHTTXContext->SavedPad[7]));
c55519ff 263 }
66cd8d6e
BZ
264 NdisMoveMemory(&pWirelessPkt[TmpBulkEndPos],
265 pHTTXContext->SavedPad, 8);
c55519ff
GKH
266 pHTTXContext->bCopySavePad = FALSE;
267 if (pAd->bForcePrintTX == TRUE)
66cd8d6e
BZ
268 DBGPRINT(RT_DEBUG_TRACE,
269 ("RTUSBBulkOutDataPacket --> COPY PAD. CurWrite = %ld, NextBulk = %ld. ENextBulk = %ld.\n",
270 pHTTXContext->CurWritePosition,
271 pHTTXContext->NextBulkOutPosition,
272 pHTTXContext->ENextBulkOutPosition));
c55519ff
GKH
273 }
274
66cd8d6e 275 do {
d24e4497 276 pTxInfo = (struct rt_txinfo *)&pWirelessPkt[TmpBulkEndPos];
66cd8d6e 277 pTxWI =
d24e4497 278 (struct rt_txwi *)&pWirelessPkt[TmpBulkEndPos + TXINFO_SIZE];
c55519ff
GKH
279
280 if (pAd->bForcePrintTX == TRUE)
66cd8d6e
BZ
281 DBGPRINT(RT_DEBUG_TRACE,
282 ("RTUSBBulkOutDataPacket AMPDU = %d.\n",
283 pTxWI->AMPDU));
c55519ff 284
9f548a2a
BZ
285 /* add by Iverson, limit BulkOut size to 4k to pass WMM b mode 2T1R test items */
286 /*if ((ThisBulkSize != 0) && (pTxWI->AMPDU == 0)) */
66cd8d6e
BZ
287 if ((ThisBulkSize != 0) && (pTxWI->PHYMODE == MODE_CCK)) {
288 if (((ThisBulkSize & 0xffff8000) != 0)
289 || ((ThisBulkSize & 0x1000) == 0x1000)) {
9f548a2a 290 /* Limit BulkOut size to about 4k bytes. */
66cd8d6e
BZ
291 pHTTXContext->ENextBulkOutPosition =
292 TmpBulkEndPos;
c55519ff 293 break;
66cd8d6e
BZ
294 } else
295 if (((pAd->BulkOutMaxPacketSize < 512)
296 && ((ThisBulkSize & 0xfffff800) !=
297 0))
298 /*|| ( (ThisBulkSize != 0) && (pTxWI->AMPDU == 0)) */
299 ) {
9f548a2a
BZ
300 /* For USB 1.1 or peer which didn't support AMPDU, limit the BulkOut size. */
301 /* For performence in b/g mode, now just check for USB 1.1 and didn't care about the APMDU or not! 2008/06/04. */
66cd8d6e
BZ
302 pHTTXContext->ENextBulkOutPosition =
303 TmpBulkEndPos;
c55519ff
GKH
304 break;
305 }
306 }
9f548a2a 307 /* end Iverson */
66cd8d6e 308 else {
9f548a2a 309 if (((ThisBulkSize & 0xffff8000) != 0) || ((ThisBulkSize & 0x6000) == 0x6000)) { /* Limit BulkOut size to about 24k bytes. */
66cd8d6e
BZ
310 pHTTXContext->ENextBulkOutPosition =
311 TmpBulkEndPos;
c55519ff 312 break;
d24e4497 313 } else if (((pAd->BulkOutMaxPacketSize < 512) && ((ThisBulkSize & 0xfffff800) != 0)) /*|| ( (ThisBulkSize != 0) && (pTxWI->AMPDU == 0)) */) { /* For USB 1.1 or peer which didn't support AMPDU, limit the BulkOut size. */
9f548a2a 314 /* For performence in b/g mode, now just check for USB 1.1 and didn't care about the APMDU or not! 2008/06/04. */
66cd8d6e
BZ
315 pHTTXContext->ENextBulkOutPosition =
316 TmpBulkEndPos;
c55519ff
GKH
317 break;
318 }
319 }
320
66cd8d6e 321 if (TmpBulkEndPos == pHTTXContext->CurWritePosition) {
c55519ff
GKH
322 pHTTXContext->ENextBulkOutPosition = TmpBulkEndPos;
323 break;
324 }
325
66cd8d6e
BZ
326 if (pTxInfo->QSEL != FIFO_EDCA) {
327 DBGPRINT(RT_DEBUG_ERROR,
328 ("%s(): ====> pTxInfo->QueueSel(%d)!= FIFO_EDCA!!!!\n",
d24e4497 329 __func__, pTxInfo->QSEL));
66cd8d6e
BZ
330 DBGPRINT(RT_DEBUG_ERROR,
331 ("\tCWPos=%ld, NBPos=%ld, ENBPos=%ld, bCopy=%d!\n",
332 pHTTXContext->CurWritePosition,
333 pHTTXContext->NextBulkOutPosition,
334 pHTTXContext->ENextBulkOutPosition,
335 pHTTXContext->bCopySavePad));
336 hex_dump("Wrong QSel Pkt:",
d24e4497 337 (u8 *)&pWirelessPkt[TmpBulkEndPos],
66cd8d6e
BZ
338 (pHTTXContext->CurWritePosition -
339 pHTTXContext->NextBulkOutPosition));
c55519ff
GKH
340 }
341
66cd8d6e
BZ
342 if (pTxInfo->USBDMATxPktLen <= 8) {
343 BULK_OUT_UNLOCK(&pAd->TxContextQueueLock[BulkOutPipeId],
344 IrqFlags2);
345 DBGPRINT(RT_DEBUG_ERROR /*RT_DEBUG_TRACE */ ,
346 ("e2, USBDMATxPktLen==0, Size=%ld, bCSPad=%d, CWPos=%ld, NBPos=%ld, CWRPos=%ld!\n",
347 pHTTXContext->BulkOutSize,
348 pHTTXContext->bCopySavePad,
349 pHTTXContext->CurWritePosition,
350 pHTTXContext->NextBulkOutPosition,
351 pHTTXContext->CurWriteRealPos));
c55519ff 352 {
66cd8d6e
BZ
353 DBGPRINT_RAW(RT_DEBUG_ERROR /*RT_DEBUG_TRACE */
354 ,
355 ("%x %x %x %x %x %x %x %x \n",
356 pHTTXContext->SavedPad[0],
357 pHTTXContext->SavedPad[1],
358 pHTTXContext->SavedPad[2],
359 pHTTXContext->SavedPad[3]
360 , pHTTXContext->SavedPad[4],
361 pHTTXContext->SavedPad[5],
362 pHTTXContext->SavedPad[6],
363 pHTTXContext->SavedPad[7]));
c55519ff
GKH
364 }
365 pAd->bForcePrintTX = TRUE;
66cd8d6e
BZ
366 BULK_OUT_LOCK(&pAd->BulkOutLock[BulkOutPipeId],
367 IrqFlags);
c55519ff 368 pAd->BulkOutPending[BulkOutPipeId] = FALSE;
66cd8d6e
BZ
369 BULK_OUT_UNLOCK(&pAd->BulkOutLock[BulkOutPipeId],
370 IrqFlags);
9f548a2a 371 /*DBGPRINT(RT_DEBUG_LOUD,("Out:pTxInfo->USBDMATxPktLen=%d!\n", pTxInfo->USBDMATxPktLen)); */
c55519ff
GKH
372 return;
373 }
9f548a2a 374 /* Increase Total transmit byte counter */
66cd8d6e
BZ
375 pAd->RalinkCounters.OneSecTransmittedByteCount +=
376 pTxWI->MPDUtotalByteCount;
377 pAd->RalinkCounters.TransmittedByteCount +=
378 pTxWI->MPDUtotalByteCount;
c55519ff
GKH
379
380 pLastTxInfo = pTxInfo;
381
9f548a2a 382 /* Make sure we use EDCA QUEUE. */
ca97b838 383 pTxInfo->QSEL = FIFO_EDCA;
66cd8d6e
BZ
384 ThisBulkSize += (pTxInfo->USBDMATxPktLen + 4);
385 TmpBulkEndPos += (pTxInfo->USBDMATxPktLen + 4);
c55519ff
GKH
386
387 if (TmpBulkEndPos != pHTTXContext->CurWritePosition)
388 pTxInfo->USBDMANextVLD = 1;
389
66cd8d6e 390 if (pTxInfo->SwUseLastRound == 1) {
c55519ff
GKH
391 if (pHTTXContext->CurWritePosition == 8)
392 pTxInfo->USBDMANextVLD = 0;
393 pTxInfo->SwUseLastRound = 0;
394
395 bTxQLastRound = TRUE;
396 pHTTXContext->ENextBulkOutPosition = 8;
397
c55519ff
GKH
398 break;
399 }
ca97b838 400
66cd8d6e 401 } while (TRUE);
c55519ff 402
9f548a2a 403 /* adjust the pTxInfo->USBDMANextVLD value of last pTxInfo. */
d24e4497 404 if (pLastTxInfo)
c55519ff 405 pLastTxInfo->USBDMANextVLD = 0;
c55519ff
GKH
406
407 /*
66cd8d6e
BZ
408 We need to copy SavedPad when following condition matched!
409 1. Not the last round of the TxQueue and
410 2. any match of following cases:
411 (1). The End Position of this bulk out is reach to the Currenct Write position and
412 the TxInfo and related header already write to the CurWritePosition.
413 =>(ENextBulkOutPosition == CurWritePosition) && (CurWriteRealPos > CurWritePosition)
414
415 (2). The EndPosition of the bulk out is not reach to the Current Write Position.
416 =>(ENextBulkOutPosition != CurWritePosition)
417 */
c55519ff 418 if ((bTxQLastRound == FALSE) &&
66cd8d6e
BZ
419 (((pHTTXContext->ENextBulkOutPosition ==
420 pHTTXContext->CurWritePosition)
421 && (pHTTXContext->CurWriteRealPos >
422 pHTTXContext->CurWritePosition))
423 || (pHTTXContext->ENextBulkOutPosition !=
424 pHTTXContext->CurWritePosition))
425 ) {
426 NdisMoveMemory(pHTTXContext->SavedPad,
427 &pWirelessPkt[pHTTXContext->
428 ENextBulkOutPosition], 8);
c55519ff 429 pHTTXContext->bCopySavePad = TRUE;
66cd8d6e 430 if (RTMPEqualMemory(pHTTXContext->SavedPad, allzero, 4)) {
51126deb 431 u8 *pBuf = &pHTTXContext->SavedPad[0];
66cd8d6e
BZ
432 DBGPRINT_RAW(RT_DEBUG_ERROR,
433 ("WARNING-Zero-3:%02x%02x%02x%02x%02x%02x%02x%02x,CWPos=%ld, CWRPos=%ld, bCW=%d, NBPos=%ld, TBPos=%ld, TBSize=%ld\n",
434 pBuf[0], pBuf[1], pBuf[2], pBuf[3],
435 pBuf[4], pBuf[5], pBuf[6], pBuf[7],
436 pHTTXContext->CurWritePosition,
437 pHTTXContext->CurWriteRealPos,
438 pHTTXContext->bCurWriting,
439 pHTTXContext->NextBulkOutPosition,
440 TmpBulkEndPos, ThisBulkSize));
c55519ff
GKH
441
442 pBuf = &pWirelessPkt[pHTTXContext->CurWritePosition];
66cd8d6e
BZ
443 DBGPRINT_RAW(RT_DEBUG_ERROR,
444 ("\tCWPos=%02x%02x%02x%02x%02x%02x%02x%02x\n",
445 pBuf[0], pBuf[1], pBuf[2], pBuf[3],
446 pBuf[4], pBuf[5], pBuf[6], pBuf[7]));
c55519ff 447 }
9f548a2a 448 /*DBGPRINT(RT_DEBUG_LOUD,("ENPos==CWPos=%ld, CWRPos=%ld, bCSPad=%d!\n", pHTTXContext->CurWritePosition, pHTTXContext->CurWriteRealPos, pHTTXContext->bCopySavePad)); */
c55519ff
GKH
449 }
450
451 if (pAd->bForcePrintTX == TRUE)
66cd8d6e
BZ
452 DBGPRINT(RT_DEBUG_TRACE,
453 ("BulkOut-A:Size=%ld, CWPos=%ld, NBPos=%ld, ENBPos=%ld, bCopy=%d!\n",
454 ThisBulkSize, pHTTXContext->CurWritePosition,
455 pHTTXContext->NextBulkOutPosition,
456 pHTTXContext->ENextBulkOutPosition,
457 pHTTXContext->bCopySavePad));
9f548a2a 458 /*DBGPRINT(RT_DEBUG_LOUD,("BulkOut-A:Size=%ld, CWPos=%ld, CWRPos=%ld, NBPos=%ld, ENBPos=%ld, bCopy=%d, bLRound=%d!\n", ThisBulkSize, pHTTXContext->CurWritePosition, pHTTXContext->CurWriteRealPos, pHTTXContext->NextBulkOutPosition, pHTTXContext->ENextBulkOutPosition, pHTTXContext->bCopySavePad, bTxQLastRound)); */
c55519ff 459
9f548a2a 460 /* USB DMA engine requires to pad extra 4 bytes. This pad doesn't count into real bulkoutsize. */
c55519ff
GKH
461 pAppendant = &pWirelessPkt[TmpBulkEndPos];
462 NdisZeroMemory(pAppendant, 8);
66cd8d6e
BZ
463 ThisBulkSize += 4;
464 pHTTXContext->LastOne = TRUE;
465 if ((ThisBulkSize % pAd->BulkOutMaxPacketSize) == 0)
c55519ff 466 ThisBulkSize += 4;
c55519ff
GKH
467 pHTTXContext->BulkOutSize = ThisBulkSize;
468
469 pAd->watchDogTxPendingCnt[BulkOutPipeId] = 1;
470 BULK_OUT_UNLOCK(&pAd->TxContextQueueLock[BulkOutPipeId], IrqFlags2);
471
9f548a2a 472 /* Init Tx context descriptor */
66cd8d6e
BZ
473 RTUSBInitHTTxDesc(pAd, pHTTXContext, BulkOutPipeId, ThisBulkSize,
474 (usb_complete_t) RTUSBBulkOutDataPacketComplete);
c55519ff
GKH
475
476 pUrb = pHTTXContext->pUrb;
66cd8d6e
BZ
477 if ((ret = RTUSB_SUBMIT_URB(pUrb)) != 0) {
478 DBGPRINT(RT_DEBUG_ERROR,
479 ("RTUSBBulkOutDataPacket: Submit Tx URB failed %d\n",
480 ret));
c55519ff
GKH
481
482 BULK_OUT_LOCK(&pAd->BulkOutLock[BulkOutPipeId], IrqFlags);
483 pAd->BulkOutPending[BulkOutPipeId] = FALSE;
484 pAd->watchDogTxPendingCnt[BulkOutPipeId] = 0;
485 BULK_OUT_UNLOCK(&pAd->BulkOutLock[BulkOutPipeId], IrqFlags);
486
487 return;
488 }
489
490 BULK_OUT_LOCK(&pAd->BulkOutLock[BulkOutPipeId], IrqFlags);
491 pHTTXContext->IRPPending = TRUE;
492 BULK_OUT_UNLOCK(&pAd->BulkOutLock[BulkOutPipeId], IrqFlags);
493 pAd->BulkOutReq++;
494
495}
496
8a10a546 497void RTUSBBulkOutDataPacketComplete(struct urb *pUrb, struct pt_regs * pt_regs)
c55519ff 498{
62eb734b
BZ
499 struct rt_ht_tx_context *pHTTXContext;
500 struct rt_rtmp_adapter *pAd;
8a10a546 501 struct os_cookie *pObj;
51126deb 502 u8 BulkOutPipeId;
c55519ff 503
62eb734b 504 pHTTXContext = (struct rt_ht_tx_context *)pUrb->context;
66cd8d6e 505 pAd = pHTTXContext->pAd;
8a10a546 506 pObj = (struct os_cookie *)pAd->OS_Cookie;
c55519ff 507
9f548a2a 508 /* Store BulkOut PipeId */
66cd8d6e 509 BulkOutPipeId = pHTTXContext->BulkOutPipeId;
c55519ff
GKH
510 pAd->BulkOutDataOneSecCount++;
511
66cd8d6e
BZ
512 switch (BulkOutPipeId) {
513 case 0:
514 pObj->ac0_dma_done_task.data = (unsigned long)pUrb;
515 tasklet_hi_schedule(&pObj->ac0_dma_done_task);
516 break;
517 case 1:
518 pObj->ac1_dma_done_task.data = (unsigned long)pUrb;
519 tasklet_hi_schedule(&pObj->ac1_dma_done_task);
520 break;
521 case 2:
522 pObj->ac2_dma_done_task.data = (unsigned long)pUrb;
523 tasklet_hi_schedule(&pObj->ac2_dma_done_task);
524 break;
525 case 3:
526 pObj->ac3_dma_done_task.data = (unsigned long)pUrb;
527 tasklet_hi_schedule(&pObj->ac3_dma_done_task);
528 break;
c55519ff 529 }
ca97b838 530
c55519ff 531}
c55519ff 532
c55519ff
GKH
533/*
534 ========================================================================
535
536 Routine Description:
537
538 Arguments:
539
540 Return Value:
541
542 Note: NULL frame use BulkOutPipeId = 0
543
544 ========================================================================
545*/
62eb734b 546void RTUSBBulkOutNullFrame(struct rt_rtmp_adapter *pAd)
c55519ff 547{
62eb734b 548 struct rt_tx_context *pNullContext = &(pAd->NullContext);
66cd8d6e
BZ
549 PURB pUrb;
550 int ret = 0;
551 unsigned long IrqFlags;
c55519ff
GKH
552
553 RTMP_IRQ_LOCK(&pAd->BulkOutLock[0], IrqFlags);
66cd8d6e
BZ
554 if ((pAd->BulkOutPending[0] == TRUE)
555 || RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_NEED_STOP_TX)) {
c55519ff
GKH
556 RTMP_IRQ_UNLOCK(&pAd->BulkOutLock[0], IrqFlags);
557 return;
558 }
559 pAd->BulkOutPending[0] = TRUE;
560 pAd->watchDogTxPendingCnt[0] = 1;
561 pNullContext->IRPPending = TRUE;
562 RTMP_IRQ_UNLOCK(&pAd->BulkOutLock[0], IrqFlags);
563
9f548a2a 564 /* Increase Total transmit byte counter */
66cd8d6e 565 pAd->RalinkCounters.TransmittedByteCount += pNullContext->BulkOutSize;
c55519ff 566
9f548a2a 567 /* Clear Null frame bulk flag */
c55519ff
GKH
568 RTUSB_CLEAR_BULK_FLAG(pAd, fRTUSB_BULK_OUT_DATA_NULL);
569
9f548a2a 570 /* Init Tx context descriptor */
66cd8d6e
BZ
571 RTUSBInitTxDesc(pAd, pNullContext, 0,
572 (usb_complete_t) RTUSBBulkOutNullFrameComplete);
c55519ff
GKH
573
574 pUrb = pNullContext->pUrb;
66cd8d6e 575 if ((ret = RTUSB_SUBMIT_URB(pUrb)) != 0) {
c55519ff
GKH
576 RTMP_IRQ_LOCK(&pAd->BulkOutLock[0], IrqFlags);
577 pAd->BulkOutPending[0] = FALSE;
578 pAd->watchDogTxPendingCnt[0] = 0;
579 pNullContext->IRPPending = FALSE;
580 RTMP_IRQ_UNLOCK(&pAd->BulkOutLock[0], IrqFlags);
581
66cd8d6e
BZ
582 DBGPRINT(RT_DEBUG_ERROR,
583 ("RTUSBBulkOutNullFrame: Submit Tx URB failed %d\n",
584 ret));
c55519ff
GKH
585 return;
586 }
587
588}
589
9f548a2a 590/* NULL frame use BulkOutPipeId = 0 */
8a10a546 591void RTUSBBulkOutNullFrameComplete(struct urb *pUrb, struct pt_regs * pt_regs)
c55519ff 592{
62eb734b
BZ
593 struct rt_rtmp_adapter *pAd;
594 struct rt_tx_context *pNullContext;
51126deb 595 int Status;
8a10a546 596 struct os_cookie *pObj;
c55519ff 597
62eb734b 598 pNullContext = (struct rt_tx_context *)pUrb->context;
66cd8d6e
BZ
599 pAd = pNullContext->pAd;
600 Status = pUrb->status;
c55519ff 601
8a10a546 602 pObj = (struct os_cookie *)pAd->OS_Cookie;
c55519ff
GKH
603 pObj->null_frame_complete_task.data = (unsigned long)pUrb;
604 tasklet_hi_schedule(&pObj->null_frame_complete_task);
c55519ff
GKH
605}
606
c55519ff
GKH
607/*
608 ========================================================================
609
610 Routine Description:
611
612 Arguments:
613
614 Return Value:
615
616 Note: MLME use BulkOutPipeId = 0
617
618 ========================================================================
619*/
62eb734b 620void RTUSBBulkOutMLMEPacket(struct rt_rtmp_adapter *pAd, u8 Index)
c55519ff 621{
62eb734b 622 struct rt_tx_context *pMLMEContext;
66cd8d6e
BZ
623 PURB pUrb;
624 int ret = 0;
625 unsigned long IrqFlags;
c55519ff 626
66cd8d6e 627 pMLMEContext =
62eb734b 628 (struct rt_tx_context *)pAd->MgmtRing.Cell[pAd->MgmtRing.TxDmaIdx].AllocVa;
c55519ff
GKH
629 pUrb = pMLMEContext->pUrb;
630
631 if ((pAd->MgmtRing.TxSwFreeIdx >= MGMT_RING_SIZE) ||
66cd8d6e
BZ
632 (pMLMEContext->InUse == FALSE) ||
633 (pMLMEContext->bWaitingBulkOut == FALSE)) {
c55519ff 634
9f548a2a 635 /* Clear MLME bulk flag */
c55519ff
GKH
636 RTUSB_CLEAR_BULK_FLAG(pAd, fRTUSB_BULK_OUT_MLME);
637
638 return;
639 }
640
c55519ff 641 RTMP_IRQ_LOCK(&pAd->BulkOutLock[MGMTPIPEIDX], IrqFlags);
66cd8d6e
BZ
642 if ((pAd->BulkOutPending[MGMTPIPEIDX] == TRUE)
643 || RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_NEED_STOP_TX)) {
c55519ff
GKH
644 RTMP_IRQ_UNLOCK(&pAd->BulkOutLock[MGMTPIPEIDX], IrqFlags);
645 return;
646 }
647
648 pAd->BulkOutPending[MGMTPIPEIDX] = TRUE;
649 pAd->watchDogTxPendingCnt[MGMTPIPEIDX] = 1;
650 pMLMEContext->IRPPending = TRUE;
651 pMLMEContext->bWaitingBulkOut = FALSE;
652 RTMP_IRQ_UNLOCK(&pAd->BulkOutLock[MGMTPIPEIDX], IrqFlags);
653
9f548a2a 654 /* Increase Total transmit byte counter */
66cd8d6e 655 pAd->RalinkCounters.TransmittedByteCount += pMLMEContext->BulkOutSize;
c55519ff 656
9f548a2a 657 /* Clear MLME bulk flag */
c55519ff
GKH
658 RTUSB_CLEAR_BULK_FLAG(pAd, fRTUSB_BULK_OUT_MLME);
659
9f548a2a 660 /* Init Tx context descriptor */
66cd8d6e
BZ
661 RTUSBInitTxDesc(pAd, pMLMEContext, MGMTPIPEIDX,
662 (usb_complete_t) RTUSBBulkOutMLMEPacketComplete);
c55519ff 663
9f548a2a 664 /*For mgmt urb buffer, because we use sk_buff, so we need to notify the USB controller do dma mapping. */
66cd8d6e 665 pUrb->transfer_dma = 0;
c55519ff 666 pUrb->transfer_flags &= (~URB_NO_TRANSFER_DMA_MAP);
c55519ff
GKH
667
668 pUrb = pMLMEContext->pUrb;
66cd8d6e
BZ
669 if ((ret = RTUSB_SUBMIT_URB(pUrb)) != 0) {
670 DBGPRINT(RT_DEBUG_ERROR,
671 ("RTUSBBulkOutMLMEPacket: Submit MLME URB failed %d\n",
672 ret));
c55519ff
GKH
673 RTMP_IRQ_LOCK(&pAd->BulkOutLock[MGMTPIPEIDX], IrqFlags);
674 pAd->BulkOutPending[MGMTPIPEIDX] = FALSE;
675 pAd->watchDogTxPendingCnt[MGMTPIPEIDX] = 0;
676 pMLMEContext->IRPPending = FALSE;
677 pMLMEContext->bWaitingBulkOut = TRUE;
678 RTMP_IRQ_UNLOCK(&pAd->BulkOutLock[MGMTPIPEIDX], IrqFlags);
679
680 return;
681 }
9f548a2a
BZ
682 /*DBGPRINT_RAW(RT_DEBUG_INFO, ("<---RTUSBBulkOutMLMEPacket \n")); */
683/* printk("<---RTUSBBulkOutMLMEPacket,Cpu=%d!, Dma=%d, SwIdx=%d!\n", pAd->MgmtRing.TxCpuIdx, pAd->MgmtRing.TxDmaIdx, pAd->MgmtRing.TxSwFreeIdx); */
c55519ff
GKH
684}
685
8a10a546 686void RTUSBBulkOutMLMEPacketComplete(struct urb *pUrb, struct pt_regs * pt_regs)
c55519ff 687{
62eb734b
BZ
688 struct rt_tx_context *pMLMEContext;
689 struct rt_rtmp_adapter *pAd;
51126deb 690 int Status;
8a10a546 691 struct os_cookie *pObj;
66cd8d6e 692 int index;
c55519ff 693
9f548a2a 694 /*DBGPRINT_RAW(RT_DEBUG_INFO, ("--->RTUSBBulkOutMLMEPacketComplete\n")); */
62eb734b 695 pMLMEContext = (struct rt_tx_context *)pUrb->context;
66cd8d6e 696 pAd = pMLMEContext->pAd;
8a10a546 697 pObj = (struct os_cookie *)pAd->OS_Cookie;
66cd8d6e
BZ
698 Status = pUrb->status;
699 index = pMLMEContext->SelfIdx;
c55519ff 700
c55519ff
GKH
701 pObj->mgmt_dma_done_task.data = (unsigned long)pUrb;
702 tasklet_hi_schedule(&pObj->mgmt_dma_done_task);
c55519ff
GKH
703}
704
c55519ff
GKH
705/*
706 ========================================================================
707
708 Routine Description:
709
710 Arguments:
711
712 Return Value:
713
714 Note: PsPoll use BulkOutPipeId = 0
715
716 ========================================================================
717*/
62eb734b 718void RTUSBBulkOutPsPoll(struct rt_rtmp_adapter *pAd)
c55519ff 719{
62eb734b 720 struct rt_tx_context *pPsPollContext = &(pAd->PsPollContext);
66cd8d6e
BZ
721 PURB pUrb;
722 int ret = 0;
723 unsigned long IrqFlags;
c55519ff
GKH
724
725 RTMP_IRQ_LOCK(&pAd->BulkOutLock[0], IrqFlags);
66cd8d6e
BZ
726 if ((pAd->BulkOutPending[0] == TRUE)
727 || RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_NEED_STOP_TX)) {
c55519ff
GKH
728 RTMP_IRQ_UNLOCK(&pAd->BulkOutLock[0], IrqFlags);
729 return;
730 }
731 pAd->BulkOutPending[0] = TRUE;
732 pAd->watchDogTxPendingCnt[0] = 1;
733 pPsPollContext->IRPPending = TRUE;
734 RTMP_IRQ_UNLOCK(&pAd->BulkOutLock[0], IrqFlags);
735
9f548a2a 736 /* Clear PS-Poll bulk flag */
c55519ff
GKH
737 RTUSB_CLEAR_BULK_FLAG(pAd, fRTUSB_BULK_OUT_PSPOLL);
738
9f548a2a 739 /* Init Tx context descriptor */
66cd8d6e
BZ
740 RTUSBInitTxDesc(pAd, pPsPollContext, MGMTPIPEIDX,
741 (usb_complete_t) RTUSBBulkOutPsPollComplete);
c55519ff
GKH
742
743 pUrb = pPsPollContext->pUrb;
66cd8d6e 744 if ((ret = RTUSB_SUBMIT_URB(pUrb)) != 0) {
c55519ff
GKH
745 RTMP_IRQ_LOCK(&pAd->BulkOutLock[0], IrqFlags);
746 pAd->BulkOutPending[0] = FALSE;
747 pAd->watchDogTxPendingCnt[0] = 0;
748 pPsPollContext->IRPPending = FALSE;
749 RTMP_IRQ_UNLOCK(&pAd->BulkOutLock[0], IrqFlags);
750
66cd8d6e
BZ
751 DBGPRINT(RT_DEBUG_ERROR,
752 ("RTUSBBulkOutPsPoll: Submit Tx URB failed %d\n",
753 ret));
c55519ff
GKH
754 return;
755 }
756
757}
758
9f548a2a 759/* PS-Poll frame use BulkOutPipeId = 0 */
8a10a546 760void RTUSBBulkOutPsPollComplete(struct urb *pUrb, struct pt_regs * pt_regs)
c55519ff 761{
62eb734b
BZ
762 struct rt_rtmp_adapter *pAd;
763 struct rt_tx_context *pPsPollContext;
51126deb 764 int Status;
8a10a546 765 struct os_cookie *pObj;
c55519ff 766
62eb734b 767 pPsPollContext = (struct rt_tx_context *)pUrb->context;
c55519ff
GKH
768 pAd = pPsPollContext->pAd;
769 Status = pUrb->status;
770
8a10a546 771 pObj = (struct os_cookie *)pAd->OS_Cookie;
c55519ff
GKH
772 pObj->pspoll_frame_complete_task.data = (unsigned long)pUrb;
773 tasklet_hi_schedule(&pObj->pspoll_frame_complete_task);
c55519ff
GKH
774}
775
62eb734b 776void DoBulkIn(struct rt_rtmp_adapter *pAd)
c55519ff 777{
62eb734b 778 struct rt_rx_context *pRxContext;
66cd8d6e
BZ
779 PURB pUrb;
780 int ret = 0;
781 unsigned long IrqFlags;
c55519ff
GKH
782
783 RTMP_IRQ_LOCK(&pAd->BulkInLock, IrqFlags);
784 pRxContext = &(pAd->RxContext[pAd->NextRxBulkInIndex]);
66cd8d6e
BZ
785 if ((pAd->PendingRx > 0) || (pRxContext->Readable == TRUE)
786 || (pRxContext->InUse == TRUE)) {
c55519ff
GKH
787 RTMP_IRQ_UNLOCK(&pAd->BulkInLock, IrqFlags);
788 return;
789 }
790 pRxContext->InUse = TRUE;
791 pRxContext->IRPPending = TRUE;
792 pAd->PendingRx++;
793 pAd->BulkInReq++;
794 RTMP_IRQ_UNLOCK(&pAd->BulkInLock, IrqFlags);
795
9f548a2a 796 /* Init Rx context descriptor */
c55519ff
GKH
797 NdisZeroMemory(pRxContext->TransferBuffer, pRxContext->BulkInOffset);
798 RTUSBInitRxDesc(pAd, pRxContext);
799
800 pUrb = pRxContext->pUrb;
9f548a2a 801 if ((ret = RTUSB_SUBMIT_URB(pUrb)) != 0) { /* fail */
c55519ff
GKH
802
803 RTMP_IRQ_LOCK(&pAd->BulkInLock, IrqFlags);
804 pRxContext->InUse = FALSE;
805 pRxContext->IRPPending = FALSE;
806 pAd->PendingRx--;
807 pAd->BulkInReq--;
808 RTMP_IRQ_UNLOCK(&pAd->BulkInLock, IrqFlags);
66cd8d6e
BZ
809 DBGPRINT(RT_DEBUG_ERROR,
810 ("RTUSBBulkReceive: Submit Rx URB failed %d\n", ret));
9f548a2a 811 } else { /* success */
c55519ff 812 ASSERT((pRxContext->InUse == pRxContext->IRPPending));
9f548a2a 813 /*printk("BIDone, Pend=%d,BIIdx=%d,BIRIdx=%d!\n", pAd->PendingRx, pAd->NextRxBulkInIndex, pAd->NextRxBulkInReadIndex); */
c55519ff
GKH
814 }
815}
816
c55519ff
GKH
817/*
818 ========================================================================
819
820 Routine Description:
821 USB_RxPacket initializes a URB and uses the Rx IRP to submit it
822 to USB. It checks if an Rx Descriptor is available and passes the
823 the coresponding buffer to be filled. If no descriptor is available
824 fails the request. When setting the completion routine we pass our
825 Adapter Object as Context.
826
827 Arguments:
828
829 Return Value:
830 TRUE found matched tuple cache
831 FALSE no matched found
832
833 Note:
834
835 ========================================================================
836*/
837#define fRTMP_ADAPTER_NEED_STOP_RX \
838 (fRTMP_ADAPTER_NIC_NOT_EXIST | fRTMP_ADAPTER_HALT_IN_PROGRESS | \
839 fRTMP_ADAPTER_RADIO_OFF | fRTMP_ADAPTER_RESET_IN_PROGRESS | \
840 fRTMP_ADAPTER_REMOVE_IN_PROGRESS | fRTMP_ADAPTER_BULKIN_RESET)
841
842#define fRTMP_ADAPTER_NEED_STOP_HANDLE_RX \
843 (fRTMP_ADAPTER_NIC_NOT_EXIST | fRTMP_ADAPTER_HALT_IN_PROGRESS | \
844 fRTMP_ADAPTER_RADIO_OFF | fRTMP_ADAPTER_RESET_IN_PROGRESS | \
845 fRTMP_ADAPTER_REMOVE_IN_PROGRESS)
846
62eb734b 847void RTUSBBulkReceive(struct rt_rtmp_adapter *pAd)
c55519ff 848{
62eb734b 849 struct rt_rx_context *pRxContext;
66cd8d6e 850 unsigned long IrqFlags;
c55519ff
GKH
851
852 /* sanity check */
853 if (RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_NEED_STOP_HANDLE_RX))
854 return;
855
66cd8d6e 856 while (1) {
c55519ff
GKH
857
858 RTMP_IRQ_LOCK(&pAd->BulkInLock, IrqFlags);
859 pRxContext = &(pAd->RxContext[pAd->NextRxBulkInReadIndex]);
66cd8d6e
BZ
860 if (((pRxContext->InUse == FALSE)
861 && (pRxContext->Readable == TRUE))
862 && (pRxContext->bRxHandling == FALSE)) {
c55519ff
GKH
863 pRxContext->bRxHandling = TRUE;
864 RTMP_IRQ_UNLOCK(&pAd->BulkInLock, IrqFlags);
865
9f548a2a 866 /* read RxContext, Since not */
303ee97d 867 STARxDoneInterruptHandle(pAd, TRUE);
c55519ff 868
9f548a2a 869 /* Finish to handle this bulkIn buffer. */
c55519ff
GKH
870 RTMP_IRQ_LOCK(&pAd->BulkInLock, IrqFlags);
871 pRxContext->BulkInOffset = 0;
872 pRxContext->Readable = FALSE;
873 pRxContext->bRxHandling = FALSE;
874 pAd->ReadPosition = 0;
875 pAd->TransferBufferLength = 0;
66cd8d6e
BZ
876 INC_RING_INDEX(pAd->NextRxBulkInReadIndex,
877 RX_RING_SIZE);
c55519ff
GKH
878 RTMP_IRQ_UNLOCK(&pAd->BulkInLock, IrqFlags);
879
66cd8d6e 880 } else {
c55519ff
GKH
881 RTMP_IRQ_UNLOCK(&pAd->BulkInLock, IrqFlags);
882 break;
883 }
884 }
885
886 if (!(RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_NEED_STOP_RX)))
887 DoBulkIn(pAd);
888
889}
890
c55519ff
GKH
891/*
892 ========================================================================
893
894 Routine Description:
895 This routine process Rx Irp and call rx complete function.
896
897 Arguments:
898 DeviceObject Pointer to the device object for next lower
899 device. DeviceObject passed in here belongs to
900 the next lower driver in the stack because we
901 were invoked via IoCallDriver in USB_RxPacket
902 AND it is not OUR device object
903 Irp Ptr to completed IRP
904 Context Ptr to our Adapter object (context specified
905 in IoSetCompletionRoutine
906
907 Return Value:
908 Always returns STATUS_MORE_PROCESSING_REQUIRED
909
910 Note:
911 Always returns STATUS_MORE_PROCESSING_REQUIRED
912 ========================================================================
913*/
8a10a546 914void RTUSBBulkRxComplete(struct urb *pUrb, struct pt_regs *pt_regs)
c55519ff 915{
9f548a2a
BZ
916 /* use a receive tasklet to handle received packets; */
917 /* or sometimes hardware IRQ will be disabled here, so we can not */
918 /* use spin_lock_bh()/spin_unlock_bh() after IRQ is disabled. :< */
62eb734b
BZ
919 struct rt_rx_context *pRxContext;
920 struct rt_rtmp_adapter *pAd;
8a10a546 921 struct os_cookie *pObj;
c55519ff 922
62eb734b 923 pRxContext = (struct rt_rx_context *)pUrb->context;
66cd8d6e 924 pAd = pRxContext->pAd;
8a10a546 925 pObj = (struct os_cookie *)pAd->OS_Cookie;
c55519ff
GKH
926
927 pObj->rx_done_task.data = (unsigned long)pUrb;
928 tasklet_hi_schedule(&pObj->rx_done_task);
929
930}
931
c55519ff
GKH
932/*
933 ========================================================================
934
935 Routine Description:
936
937 Arguments:
938
939 Return Value:
940
941 Note:
942
943 ========================================================================
944*/
62eb734b 945void RTUSBKickBulkOut(struct rt_rtmp_adapter *pAd)
c55519ff 946{
9f548a2a 947 /* BulkIn Reset will reset whole USB PHY. So we need to make sure fRTMP_ADAPTER_BULKIN_RESET not flaged. */
66cd8d6e
BZ
948 if (!RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_NEED_STOP_TX)
949 ) {
9f548a2a 950 /* 2. PS-Poll frame is next */
d24e4497 951 if (RTUSB_TEST_BULK_FLAG(pAd, fRTUSB_BULK_OUT_PSPOLL))
c55519ff 952 RTUSBBulkOutPsPoll(pAd);
9f548a2a 953 /* 5. Mlme frame is next */
ca97b838 954 else if ((RTUSB_TEST_BULK_FLAG(pAd, fRTUSB_BULK_OUT_MLME)) ||
66cd8d6e 955 (pAd->MgmtRing.TxSwFreeIdx < MGMT_RING_SIZE)) {
c55519ff
GKH
956 RTUSBBulkOutMLMEPacket(pAd, pAd->MgmtRing.TxDmaIdx);
957 }
9f548a2a 958 /* 6. Data frame normal is next */
66cd8d6e
BZ
959 if (RTUSB_TEST_BULK_FLAG(pAd, fRTUSB_BULK_OUT_DATA_NORMAL)) {
960 if (((!RTMP_TEST_FLAG
961 (pAd, fRTMP_ADAPTER_BSS_SCAN_IN_PROGRESS))
962 ||
963 (!OPSTATUS_TEST_FLAG
964 (pAd, fOP_STATUS_MEDIA_STATE_CONNECTED))
965 )) {
966 RTUSBBulkOutDataPacket(pAd, 0,
967 pAd->
968 NextBulkOutIndex[0]);
c55519ff
GKH
969 }
970 }
66cd8d6e
BZ
971 if (RTUSB_TEST_BULK_FLAG(pAd, fRTUSB_BULK_OUT_DATA_NORMAL_2)) {
972 if (((!RTMP_TEST_FLAG
973 (pAd, fRTMP_ADAPTER_BSS_SCAN_IN_PROGRESS))
974 ||
975 (!OPSTATUS_TEST_FLAG
976 (pAd, fOP_STATUS_MEDIA_STATE_CONNECTED))
977 )) {
978 RTUSBBulkOutDataPacket(pAd, 1,
979 pAd->
980 NextBulkOutIndex[1]);
c55519ff
GKH
981 }
982 }
66cd8d6e
BZ
983 if (RTUSB_TEST_BULK_FLAG(pAd, fRTUSB_BULK_OUT_DATA_NORMAL_3)) {
984 if (((!RTMP_TEST_FLAG
985 (pAd, fRTMP_ADAPTER_BSS_SCAN_IN_PROGRESS))
986 ||
987 (!OPSTATUS_TEST_FLAG
988 (pAd, fOP_STATUS_MEDIA_STATE_CONNECTED))
989 )) {
990 RTUSBBulkOutDataPacket(pAd, 2,
991 pAd->
992 NextBulkOutIndex[2]);
c55519ff
GKH
993 }
994 }
66cd8d6e
BZ
995 if (RTUSB_TEST_BULK_FLAG(pAd, fRTUSB_BULK_OUT_DATA_NORMAL_4)) {
996 if (((!RTMP_TEST_FLAG
997 (pAd, fRTMP_ADAPTER_BSS_SCAN_IN_PROGRESS))
998 ||
999 (!OPSTATUS_TEST_FLAG
1000 (pAd, fOP_STATUS_MEDIA_STATE_CONNECTED))
1001 )) {
1002 RTUSBBulkOutDataPacket(pAd, 3,
1003 pAd->
1004 NextBulkOutIndex[3]);
c55519ff
GKH
1005 }
1006 }
9f548a2a 1007 /* 7. Null frame is the last */
66cd8d6e
BZ
1008 else if (RTUSB_TEST_BULK_FLAG(pAd, fRTUSB_BULK_OUT_DATA_NULL)) {
1009 if (!RTMP_TEST_FLAG
1010 (pAd, fRTMP_ADAPTER_BSS_SCAN_IN_PROGRESS)) {
c55519ff
GKH
1011 RTUSBBulkOutNullFrame(pAd);
1012 }
1013 }
9f548a2a 1014 /* 8. No data avaliable */
d24e4497
AG
1015 else
1016 ;
c55519ff 1017 }
c55519ff
GKH
1018}
1019
1020/*
1021 ========================================================================
1022
1023 Routine Description:
1024 Call from Reset action after BulkOut failed.
1025 Arguments:
1026
1027 Return Value:
1028
1029 Note:
1030
1031 ========================================================================
1032*/
62eb734b 1033void RTUSBCleanUpDataBulkOutQueue(struct rt_rtmp_adapter *pAd)
c55519ff 1034{
51126deb 1035 u8 Idx;
62eb734b 1036 struct rt_ht_tx_context *pTxContext;
c55519ff
GKH
1037
1038 DBGPRINT(RT_DEBUG_TRACE, ("--->CleanUpDataBulkOutQueue\n"));
1039
66cd8d6e 1040 for (Idx = 0; Idx < 4; Idx++) {
c55519ff
GKH
1041 pTxContext = &pAd->TxContext[Idx];
1042
1043 pTxContext->CurWritePosition = pTxContext->NextBulkOutPosition;
1044 pTxContext->LastOne = FALSE;
1045 NdisAcquireSpinLock(&pAd->BulkOutLock[Idx]);
1046 pAd->BulkOutPending[Idx] = FALSE;
1047 NdisReleaseSpinLock(&pAd->BulkOutLock[Idx]);
1048 }
1049
1050 DBGPRINT(RT_DEBUG_TRACE, ("<---CleanUpDataBulkOutQueue\n"));
1051}
1052
1053/*
1054 ========================================================================
1055
1056 Routine Description:
1057
1058 Arguments:
1059
1060 Return Value:
1061
1062 Note:
1063
1064 ========================================================================
1065*/
62eb734b 1066void RTUSBCleanUpMLMEBulkOutQueue(struct rt_rtmp_adapter *pAd)
c55519ff
GKH
1067{
1068 DBGPRINT(RT_DEBUG_TRACE, ("--->CleanUpMLMEBulkOutQueue\n"));
c55519ff
GKH
1069 DBGPRINT(RT_DEBUG_TRACE, ("<---CleanUpMLMEBulkOutQueue\n"));
1070}
1071
c55519ff
GKH
1072/*
1073 ========================================================================
1074
1075 Routine Description:
1076
1077 Arguments:
1078
1079 Return Value:
1080
c55519ff
GKH
1081 Note:
1082
1083 ========================================================================
1084*/
62eb734b 1085void RTUSBCancelPendingIRPs(struct rt_rtmp_adapter *pAd)
c55519ff
GKH
1086{
1087 RTUSBCancelPendingBulkInIRP(pAd);
1088 RTUSBCancelPendingBulkOutIRP(pAd);
1089}
1090
1091/*
1092 ========================================================================
1093
1094 Routine Description:
1095
1096 Arguments:
1097
1098 Return Value:
1099
1100 Note:
1101
1102 ========================================================================
1103*/
62eb734b 1104void RTUSBCancelPendingBulkInIRP(struct rt_rtmp_adapter *pAd)
c55519ff 1105{
62eb734b 1106 struct rt_rx_context *pRxContext;
51126deb 1107 u32 i;
c55519ff
GKH
1108
1109 DBGPRINT_RAW(RT_DEBUG_TRACE, ("--->RTUSBCancelPendingBulkInIRP\n"));
66cd8d6e 1110 for (i = 0; i < (RX_RING_SIZE); i++) {
c55519ff 1111 pRxContext = &(pAd->RxContext[i]);
66cd8d6e 1112 if (pRxContext->IRPPending == TRUE) {
c55519ff
GKH
1113 RTUSB_UNLINK_URB(pRxContext->pUrb);
1114 pRxContext->IRPPending = FALSE;
1115 pRxContext->InUse = FALSE;
9f548a2a
BZ
1116 /*NdisInterlockedDecrement(&pAd->PendingRx); */
1117 /*pAd->PendingRx--; */
c55519ff
GKH
1118 }
1119 }
1120 DBGPRINT_RAW(RT_DEBUG_TRACE, ("<---RTUSBCancelPendingBulkInIRP\n"));
1121}
1122
c55519ff
GKH
1123/*
1124 ========================================================================
1125
1126 Routine Description:
1127
1128 Arguments:
1129
1130 Return Value:
1131
1132 Note:
1133
1134 ========================================================================
1135*/
62eb734b 1136void RTUSBCancelPendingBulkOutIRP(struct rt_rtmp_adapter *pAd)
c55519ff 1137{
62eb734b
BZ
1138 struct rt_ht_tx_context *pHTTXContext;
1139 struct rt_tx_context *pMLMEContext;
1140 struct rt_tx_context *pBeaconContext;
1141 struct rt_tx_context *pNullContext;
1142 struct rt_tx_context *pPsPollContext;
1143 struct rt_tx_context *pRTSContext;
51126deb 1144 u32 i, Idx;
9f548a2a 1145/* unsigned int IrqFlags; */
8a10a546 1146/* spinlock_t *pLock; */
9f548a2a 1147/* BOOLEAN *pPending; */
66cd8d6e 1148
9f548a2a
BZ
1149/* pLock = &pAd->BulkOutLock[MGMTPIPEIDX]; */
1150/* pPending = &pAd->BulkOutPending[MGMTPIPEIDX]; */
66cd8d6e
BZ
1151
1152 for (Idx = 0; Idx < 4; Idx++) {
c55519ff
GKH
1153 pHTTXContext = &(pAd->TxContext[Idx]);
1154
66cd8d6e 1155 if (pHTTXContext->IRPPending == TRUE) {
c55519ff 1156
9f548a2a
BZ
1157 /* Get the USB_CONTEXT and cancel it's IRP; the completion routine will itself */
1158 /* remove it from the HeadPendingSendList and NULL out HeadPendingSendList */
1159 /* when the last IRP on the list has been cancelled; that's how we exit this loop */
1160 /* */
c55519ff
GKH
1161
1162 RTUSB_UNLINK_URB(pHTTXContext->pUrb);
1163
9f548a2a 1164 /* Sleep 200 microseconds to give cancellation time to work */
c55519ff
GKH
1165 RTMPusecDelay(200);
1166 }
1167
c55519ff
GKH
1168 pAd->BulkOutPending[Idx] = FALSE;
1169 }
1170
9f548a2a 1171 /*RTMP_IRQ_LOCK(pLock, IrqFlags); */
66cd8d6e 1172 for (i = 0; i < MGMT_RING_SIZE; i++) {
62eb734b 1173 pMLMEContext = (struct rt_tx_context *)pAd->MgmtRing.Cell[i].AllocVa;
66cd8d6e 1174 if (pMLMEContext && (pMLMEContext->IRPPending == TRUE)) {
c55519ff 1175
9f548a2a
BZ
1176 /* Get the USB_CONTEXT and cancel it's IRP; the completion routine will itself */
1177 /* remove it from the HeadPendingSendList and NULL out HeadPendingSendList */
1178 /* when the last IRP on the list has been cancelled; that's how we exit this loop */
1179 /* */
c55519ff
GKH
1180
1181 RTUSB_UNLINK_URB(pMLMEContext->pUrb);
1182 pMLMEContext->IRPPending = FALSE;
1183
9f548a2a 1184 /* Sleep 200 microsecs to give cancellation time to work */
c55519ff
GKH
1185 RTMPusecDelay(200);
1186 }
1187 }
1188 pAd->BulkOutPending[MGMTPIPEIDX] = FALSE;
9f548a2a 1189 /*RTMP_IRQ_UNLOCK(pLock, IrqFlags); */
c55519ff 1190
66cd8d6e 1191 for (i = 0; i < BEACON_RING_SIZE; i++) {
c55519ff
GKH
1192 pBeaconContext = &(pAd->BeaconContext[i]);
1193
66cd8d6e 1194 if (pBeaconContext->IRPPending == TRUE) {
c55519ff 1195
9f548a2a
BZ
1196 /* Get the USB_CONTEXT and cancel it's IRP; the completion routine will itself */
1197 /* remove it from the HeadPendingSendList and NULL out HeadPendingSendList */
1198 /* when the last IRP on the list has been cancelled; that's how we exit this loop */
1199 /* */
c55519ff
GKH
1200
1201 RTUSB_UNLINK_URB(pBeaconContext->pUrb);
1202
9f548a2a 1203 /* Sleep 200 microsecs to give cancellation time to work */
c55519ff
GKH
1204 RTMPusecDelay(200);
1205 }
1206 }
1207
1208 pNullContext = &(pAd->NullContext);
1209 if (pNullContext->IRPPending == TRUE)
1210 RTUSB_UNLINK_URB(pNullContext->pUrb);
1211
1212 pRTSContext = &(pAd->RTSContext);
1213 if (pRTSContext->IRPPending == TRUE)
1214 RTUSB_UNLINK_URB(pRTSContext->pUrb);
1215
1216 pPsPollContext = &(pAd->PsPollContext);
1217 if (pPsPollContext->IRPPending == TRUE)
1218 RTUSB_UNLINK_URB(pPsPollContext->pUrb);
1219
66cd8d6e 1220 for (Idx = 0; Idx < 4; Idx++) {
c55519ff
GKH
1221 NdisAcquireSpinLock(&pAd->BulkOutLock[Idx]);
1222 pAd->BulkOutPending[Idx] = FALSE;
1223 NdisReleaseSpinLock(&pAd->BulkOutLock[Idx]);
1224 }
1225}
1226
9f548a2a 1227#endif /* RTMP_MAC_USB // */