Staging: rt2870: add fRTUSB_BULK_OUT_DATA_NORMAL_5 quirk
[linux-2.6/kvm.git] / drivers / staging / rt2870 / common / 2870_rtmp_init.c
blobf517d9e902711fae99a6f01a680dbff223bc3382
1 /*
2 *************************************************************************
3 * Ralink Tech Inc.
4 * 5F., No.36, Taiyuan St., Jhubei City,
5 * Hsinchu County 302,
6 * Taiwan, R.O.C.
8 * (c) Copyright 2002-2007, Ralink Technology, Inc.
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 *************************************************************************
27 Module Name:
28 2870_rtmp_init.c
30 Abstract:
31 Miniport generic portion header file
33 Revision History:
34 Who When What
35 -------- ---------- ----------------------------------------------
36 Paul Lin 2002-08-01 created
37 John Chang 2004-08-20 RT2561/2661 use scatter-gather scheme
38 Jan Lee 2006-09-15 RT2860. Change for 802.11n , EEPROM, Led, BA, HT.
39 Sample Lin 2007-05-31 Merge RT2860 and RT2870 drivers.
42 #include "../rt_config.h"
45 static void rx_done_tasklet(unsigned long data);
46 static void rt2870_hcca_dma_done_tasklet(unsigned long data);
47 static void rt2870_ac3_dma_done_tasklet(unsigned long data);
48 static void rt2870_ac2_dma_done_tasklet(unsigned long data);
49 static void rt2870_ac1_dma_done_tasklet(unsigned long data);
50 static void rt2870_ac0_dma_done_tasklet(unsigned long data);
51 static void rt2870_mgmt_dma_done_tasklet(unsigned long data);
52 static void rt2870_null_frame_complete_tasklet(unsigned long data);
53 static void rt2870_rts_frame_complete_tasklet(unsigned long data);
54 static void rt2870_pspoll_frame_complete_tasklet(unsigned long data);
55 static void rt2870_dataout_complete_tasklet(unsigned long data);
59 ========================================================================
60 Routine Description:
61 Initialize receive data structures.
63 Arguments:
64 pAd Pointer to our adapter
66 Return Value:
67 NDIS_STATUS_SUCCESS
68 NDIS_STATUS_RESOURCES
70 Note:
71 Initialize all receive releated private buffer, include those define
72 in RTMP_ADAPTER structure and all private data structures. The mahor
73 work is to allocate buffer for each packet and chain buffer to
74 NDIS packet descriptor.
75 ========================================================================
77 NDIS_STATUS NICInitRecv(
78 IN PRTMP_ADAPTER pAd)
80 UCHAR i;
81 NDIS_STATUS Status = NDIS_STATUS_SUCCESS;
82 POS_COOKIE pObj = (POS_COOKIE) pAd->OS_Cookie;
85 DBGPRINT(RT_DEBUG_TRACE, ("--> NICInitRecv\n"));
86 pObj = pObj;
88 //InterlockedExchange(&pAd->PendingRx, 0);
89 pAd->PendingRx = 0;
90 pAd->NextRxBulkInReadIndex = 0; // Next Rx Read index
91 pAd->NextRxBulkInIndex = 0 ; //RX_RING_SIZE -1; // Rx Bulk pointer
92 pAd->NextRxBulkInPosition = 0;
94 for (i = 0; i < (RX_RING_SIZE); i++)
96 PRX_CONTEXT pRxContext = &(pAd->RxContext[i]);
98 //Allocate URB
99 pRxContext->pUrb = RTUSB_ALLOC_URB(0);
100 if (pRxContext->pUrb == NULL)
102 Status = NDIS_STATUS_RESOURCES;
103 goto out1;
106 // Allocate transfer buffer
107 pRxContext->TransferBuffer = RTUSB_URB_ALLOC_BUFFER(pObj->pUsb_Dev, MAX_RXBULK_SIZE, &pRxContext->data_dma);
108 if (pRxContext->TransferBuffer == NULL)
110 Status = NDIS_STATUS_RESOURCES;
111 goto out1;
114 NdisZeroMemory(pRxContext->TransferBuffer, MAX_RXBULK_SIZE);
116 pRxContext->pAd = pAd;
117 pRxContext->pIrp = NULL;
118 pRxContext->InUse = FALSE;
119 pRxContext->IRPPending = FALSE;
120 pRxContext->Readable = FALSE;
121 //pRxContext->ReorderInUse = FALSE;
122 pRxContext->bRxHandling = FALSE;
123 pRxContext->BulkInOffset = 0;
126 DBGPRINT(RT_DEBUG_TRACE, ("<-- NICInitRecv\n"));
127 return Status;
129 out1:
130 for (i = 0; i < (RX_RING_SIZE); i++)
132 PRX_CONTEXT pRxContext = &(pAd->RxContext[i]);
134 if (NULL != pRxContext->TransferBuffer)
136 RTUSB_URB_FREE_BUFFER(pObj->pUsb_Dev, MAX_RXBULK_SIZE,
137 pRxContext->TransferBuffer, pRxContext->data_dma);
138 pRxContext->TransferBuffer = NULL;
141 if (NULL != pRxContext->pUrb)
143 RTUSB_UNLINK_URB(pRxContext->pUrb);
144 RTUSB_FREE_URB(pRxContext->pUrb);
145 pRxContext->pUrb = NULL;
149 return Status;
154 ========================================================================
155 Routine Description:
156 Initialize transmit data structures.
158 Arguments:
159 pAd Pointer to our adapter
161 Return Value:
162 NDIS_STATUS_SUCCESS
163 NDIS_STATUS_RESOURCES
165 Note:
166 ========================================================================
168 NDIS_STATUS NICInitTransmit(
169 IN PRTMP_ADAPTER pAd)
171 #define LM_USB_ALLOC(pObj, Context, TB_Type, BufferSize, Status, msg1, err1, msg2, err2) \
172 Context->pUrb = RTUSB_ALLOC_URB(0); \
173 if (Context->pUrb == NULL) { \
174 DBGPRINT(RT_DEBUG_ERROR, msg1); \
175 Status = NDIS_STATUS_RESOURCES; \
176 goto err1; } \
178 Context->TransferBuffer = \
179 (TB_Type)RTUSB_URB_ALLOC_BUFFER(pObj->pUsb_Dev, BufferSize, &Context->data_dma); \
180 if (Context->TransferBuffer == NULL) { \
181 DBGPRINT(RT_DEBUG_ERROR, msg2); \
182 Status = NDIS_STATUS_RESOURCES; \
183 goto err2; }
185 #define LM_URB_FREE(pObj, Context, BufferSize) \
186 if (NULL != Context->pUrb) { \
187 RTUSB_UNLINK_URB(Context->pUrb); \
188 RTUSB_FREE_URB(Context->pUrb); \
189 Context->pUrb = NULL; } \
190 if (NULL != Context->TransferBuffer) { \
191 RTUSB_URB_FREE_BUFFER(pObj->pUsb_Dev, BufferSize, \
192 Context->TransferBuffer, \
193 Context->data_dma); \
194 Context->TransferBuffer = NULL; }
196 UCHAR i, acidx;
197 NDIS_STATUS Status = NDIS_STATUS_SUCCESS;
198 PTX_CONTEXT pNullContext = &(pAd->NullContext);
199 PTX_CONTEXT pPsPollContext = &(pAd->PsPollContext);
200 PTX_CONTEXT pRTSContext = &(pAd->RTSContext);
201 PTX_CONTEXT pMLMEContext = NULL;
202 // PHT_TX_CONTEXT pHTTXContext = NULL;
203 POS_COOKIE pObj = (POS_COOKIE) pAd->OS_Cookie;
204 PVOID RingBaseVa;
205 // RTMP_TX_RING *pTxRing;
206 RTMP_MGMT_RING *pMgmtRing;
208 DBGPRINT(RT_DEBUG_TRACE, ("--> NICInitTransmit\n"));
209 pObj = pObj;
211 // Init 4 set of Tx parameters
212 for(acidx = 0; acidx < NUM_OF_TX_RING; acidx++)
214 // Initialize all Transmit releated queues
215 InitializeQueueHeader(&pAd->TxSwQueue[acidx]);
217 // Next Local tx ring pointer waiting for buck out
218 pAd->NextBulkOutIndex[acidx] = acidx;
219 pAd->BulkOutPending[acidx] = FALSE; // Buck Out control flag
220 //pAd->DataBulkDoneIdx[acidx] = 0;
223 //pAd->NextMLMEIndex = 0;
224 //pAd->PushMgmtIndex = 0;
225 //pAd->PopMgmtIndex = 0;
226 //InterlockedExchange(&pAd->MgmtQueueSize, 0);
227 //InterlockedExchange(&pAd->TxCount, 0);
229 //pAd->PrioRingFirstIndex = 0;
230 //pAd->PrioRingTxCnt = 0;
235 // TX_RING_SIZE, 4 ACs
237 for(acidx=0; acidx<4; acidx++)
239 PHT_TX_CONTEXT pHTTXContext = &(pAd->TxContext[acidx]);
241 NdisZeroMemory(pHTTXContext, sizeof(HT_TX_CONTEXT));
242 //Allocate URB
243 LM_USB_ALLOC(pObj, pHTTXContext, PHTTX_BUFFER, sizeof(HTTX_BUFFER), Status,
244 ("<-- ERROR in Alloc TX TxContext[%d] urb!! \n", acidx),
245 done,
246 ("<-- ERROR in Alloc TX TxContext[%d] HTTX_BUFFER !! \n", acidx),
247 out1);
249 NdisZeroMemory(pHTTXContext->TransferBuffer->Aggregation, 4);
250 pHTTXContext->pAd = pAd;
251 pHTTXContext->pIrp = NULL;
252 pHTTXContext->IRPPending = FALSE;
253 pHTTXContext->NextBulkOutPosition = 0;
254 pHTTXContext->ENextBulkOutPosition = 0;
255 pHTTXContext->CurWritePosition = 0;
256 pHTTXContext->CurWriteRealPos = 0;
257 pHTTXContext->BulkOutSize = 0;
258 pHTTXContext->BulkOutPipeId = acidx;
259 pHTTXContext->bRingEmpty = TRUE;
260 pHTTXContext->bCopySavePad = FALSE;
262 pAd->BulkOutPending[acidx] = FALSE;
267 // MGMT_RING_SIZE
269 // Allocate MGMT ring descriptor's memory
270 pAd->MgmtDescRing.AllocSize = MGMT_RING_SIZE * sizeof(TX_CONTEXT);
271 RTMPAllocateMemory(&pAd->MgmtDescRing.AllocVa, pAd->MgmtDescRing.AllocSize);
272 if (pAd->MgmtDescRing.AllocVa == NULL)
274 DBGPRINT_ERR(("Failed to allocate a big buffer for MgmtDescRing!\n"));
275 Status = NDIS_STATUS_RESOURCES;
276 goto out1;
278 NdisZeroMemory(pAd->MgmtDescRing.AllocVa, pAd->MgmtDescRing.AllocSize);
279 RingBaseVa = pAd->MgmtDescRing.AllocVa;
281 // Initialize MGMT Ring and associated buffer memory
282 pMgmtRing = &pAd->MgmtRing;
283 for (i = 0; i < MGMT_RING_SIZE; i++)
285 // link the pre-allocated Mgmt buffer to MgmtRing.Cell
286 pMgmtRing->Cell[i].AllocSize = sizeof(TX_CONTEXT);
287 pMgmtRing->Cell[i].AllocVa = RingBaseVa;
288 pMgmtRing->Cell[i].pNdisPacket = NULL;
289 pMgmtRing->Cell[i].pNextNdisPacket = NULL;
291 //Allocate URB for MLMEContext
292 pMLMEContext = (PTX_CONTEXT) pAd->MgmtRing.Cell[i].AllocVa;
293 pMLMEContext->pUrb = RTUSB_ALLOC_URB(0);
294 if (pMLMEContext->pUrb == NULL)
296 DBGPRINT(RT_DEBUG_ERROR, ("<-- ERROR in Alloc TX MLMEContext[%d] urb!! \n", i));
297 Status = NDIS_STATUS_RESOURCES;
298 goto out2;
300 pMLMEContext->pAd = pAd;
301 pMLMEContext->pIrp = NULL;
302 pMLMEContext->TransferBuffer = NULL;
303 pMLMEContext->InUse = FALSE;
304 pMLMEContext->IRPPending = FALSE;
305 pMLMEContext->bWaitingBulkOut = FALSE;
306 pMLMEContext->BulkOutSize = 0;
307 pMLMEContext->SelfIdx = i;
309 // Offset to next ring descriptor address
310 RingBaseVa = (PUCHAR) RingBaseVa + sizeof(TX_CONTEXT);
312 DBGPRINT(RT_DEBUG_TRACE, ("MGMT Ring: total %d entry allocated\n", i));
314 //pAd->MgmtRing.TxSwFreeIdx = (MGMT_RING_SIZE - 1);
315 pAd->MgmtRing.TxSwFreeIdx = MGMT_RING_SIZE;
316 pAd->MgmtRing.TxCpuIdx = 0;
317 pAd->MgmtRing.TxDmaIdx = 0;
320 // BEACON_RING_SIZE
322 for(i=0; i<BEACON_RING_SIZE; i++) // 2
324 PTX_CONTEXT pBeaconContext = &(pAd->BeaconContext[i]);
327 NdisZeroMemory(pBeaconContext, sizeof(TX_CONTEXT));
329 //Allocate URB
330 LM_USB_ALLOC(pObj, pBeaconContext, PTX_BUFFER, sizeof(TX_BUFFER), Status,
331 ("<-- ERROR in Alloc TX BeaconContext[%d] urb!! \n", i),
332 out2,
333 ("<-- ERROR in Alloc TX BeaconContext[%d] TX_BUFFER !! \n", i),
334 out3);
336 pBeaconContext->pAd = pAd;
337 pBeaconContext->pIrp = NULL;
338 pBeaconContext->InUse = FALSE;
339 pBeaconContext->IRPPending = FALSE;
343 // NullContext
345 NdisZeroMemory(pNullContext, sizeof(TX_CONTEXT));
347 //Allocate URB
348 LM_USB_ALLOC(pObj, pNullContext, PTX_BUFFER, sizeof(TX_BUFFER), Status,
349 ("<-- ERROR in Alloc TX NullContext urb!! \n"),
350 out3,
351 ("<-- ERROR in Alloc TX NullContext TX_BUFFER !! \n"),
352 out4);
354 pNullContext->pAd = pAd;
355 pNullContext->pIrp = NULL;
356 pNullContext->InUse = FALSE;
357 pNullContext->IRPPending = FALSE;
360 // RTSContext
362 NdisZeroMemory(pRTSContext, sizeof(TX_CONTEXT));
364 //Allocate URB
365 LM_USB_ALLOC(pObj, pRTSContext, PTX_BUFFER, sizeof(TX_BUFFER), Status,
366 ("<-- ERROR in Alloc TX RTSContext urb!! \n"),
367 out4,
368 ("<-- ERROR in Alloc TX RTSContext TX_BUFFER !! \n"),
369 out5);
371 pRTSContext->pAd = pAd;
372 pRTSContext->pIrp = NULL;
373 pRTSContext->InUse = FALSE;
374 pRTSContext->IRPPending = FALSE;
377 // PsPollContext
379 //NdisZeroMemory(pPsPollContext, sizeof(TX_CONTEXT));
380 //Allocate URB
381 LM_USB_ALLOC(pObj, pPsPollContext, PTX_BUFFER, sizeof(TX_BUFFER), Status,
382 ("<-- ERROR in Alloc TX PsPollContext urb!! \n"),
383 out5,
384 ("<-- ERROR in Alloc TX PsPollContext TX_BUFFER !! \n"),
385 out6);
387 pPsPollContext->pAd = pAd;
388 pPsPollContext->pIrp = NULL;
389 pPsPollContext->InUse = FALSE;
390 pPsPollContext->IRPPending = FALSE;
391 pPsPollContext->bAggregatible = FALSE;
392 pPsPollContext->LastOne = TRUE;
394 } while (FALSE);
397 done:
398 DBGPRINT(RT_DEBUG_TRACE, ("<-- NICInitTransmit\n"));
400 return Status;
402 /* --------------------------- ERROR HANDLE --------------------------- */
403 out6:
404 LM_URB_FREE(pObj, pPsPollContext, sizeof(TX_BUFFER));
406 out5:
407 LM_URB_FREE(pObj, pRTSContext, sizeof(TX_BUFFER));
409 out4:
410 LM_URB_FREE(pObj, pNullContext, sizeof(TX_BUFFER));
412 out3:
413 for(i=0; i<BEACON_RING_SIZE; i++)
415 PTX_CONTEXT pBeaconContext = &(pAd->BeaconContext[i]);
416 if (pBeaconContext)
417 LM_URB_FREE(pObj, pBeaconContext, sizeof(TX_BUFFER));
420 out2:
421 if (pAd->MgmtDescRing.AllocVa)
423 pMgmtRing = &pAd->MgmtRing;
424 for(i=0; i<MGMT_RING_SIZE; i++)
426 pMLMEContext = (PTX_CONTEXT) pAd->MgmtRing.Cell[i].AllocVa;
427 if (pMLMEContext)
428 LM_URB_FREE(pObj, pMLMEContext, sizeof(TX_BUFFER));
430 NdisFreeMemory(pAd->MgmtDescRing.AllocVa, pAd->MgmtDescRing.AllocSize, 0);
431 pAd->MgmtDescRing.AllocVa = NULL;
434 out1:
435 for (acidx = 0; acidx < 4; acidx++)
437 PHT_TX_CONTEXT pTxContext = &(pAd->TxContext[acidx]);
438 if (pTxContext)
439 LM_URB_FREE(pObj, pTxContext, sizeof(HTTX_BUFFER));
442 // Here we didn't have any pre-allocated memory need to free.
444 return Status;
449 ========================================================================
450 Routine Description:
451 Allocate DMA memory blocks for send, receive.
453 Arguments:
454 pAd Pointer to our adapter
456 Return Value:
457 NDIS_STATUS_SUCCESS
458 NDIS_STATUS_FAILURE
459 NDIS_STATUS_RESOURCES
461 Note:
462 ========================================================================
464 NDIS_STATUS RTMPAllocTxRxRingMemory(
465 IN PRTMP_ADAPTER pAd)
467 // COUNTER_802_11 pCounter = &pAd->WlanCounters;
468 NDIS_STATUS Status;
469 INT num;
472 DBGPRINT(RT_DEBUG_TRACE, ("--> RTMPAllocTxRxRingMemory\n"));
477 // Init the CmdQ and CmdQLock
478 NdisAllocateSpinLock(&pAd->CmdQLock);
479 NdisAcquireSpinLock(&pAd->CmdQLock);
480 RTUSBInitializeCmdQ(&pAd->CmdQ);
481 NdisReleaseSpinLock(&pAd->CmdQLock);
484 NdisAllocateSpinLock(&pAd->MLMEBulkOutLock);
485 //NdisAllocateSpinLock(&pAd->MLMEWaitQueueLock);
486 NdisAllocateSpinLock(&pAd->BulkOutLock[0]);
487 NdisAllocateSpinLock(&pAd->BulkOutLock[1]);
488 NdisAllocateSpinLock(&pAd->BulkOutLock[2]);
489 NdisAllocateSpinLock(&pAd->BulkOutLock[3]);
490 NdisAllocateSpinLock(&pAd->BulkOutLock[4]);
491 NdisAllocateSpinLock(&pAd->BulkOutLock[5]);
492 NdisAllocateSpinLock(&pAd->BulkInLock);
494 for (num = 0; num < NUM_OF_TX_RING; num++)
496 NdisAllocateSpinLock(&pAd->TxContextQueueLock[num]);
499 // NdisAllocateSpinLock(&pAd->MemLock); // Not used in RT28XX
501 // NdisAllocateSpinLock(&pAd->MacTabLock); // init it in UserCfgInit()
502 // NdisAllocateSpinLock(&pAd->BATabLock); // init it in BATableInit()
504 // for(num=0; num<MAX_LEN_OF_BA_REC_TABLE; num++)
505 // {
506 // NdisAllocateSpinLock(&pAd->BATable.BARecEntry[num].RxReRingLock);
507 // }
510 // Init Mac Table
512 // MacTableInitialize(pAd);
515 // Init send data structures and related parameters
517 Status = NICInitTransmit(pAd);
518 if (Status != NDIS_STATUS_SUCCESS)
519 break;
522 // Init receive data structures and related parameters
524 Status = NICInitRecv(pAd);
525 if (Status != NDIS_STATUS_SUCCESS)
526 break;
528 pAd->PendingIoCount = 1;
530 } while (FALSE);
532 NdisZeroMemory(&pAd->FragFrame, sizeof(FRAGMENT_FRAME));
533 pAd->FragFrame.pFragPacket = RTMP_AllocateFragPacketBuffer(pAd, RX_BUFFER_NORMSIZE);
535 if (pAd->FragFrame.pFragPacket == NULL)
537 Status = NDIS_STATUS_RESOURCES;
540 DBGPRINT_S(Status, ("<-- RTMPAllocTxRxRingMemory, Status=%x\n", Status));
541 return Status;
546 ========================================================================
547 Routine Description:
548 Calls USB_InterfaceStop and frees memory allocated for the URBs
549 calls NdisMDeregisterDevice and frees the memory
550 allocated in VNetInitialize for the Adapter Object
552 Arguments:
553 *pAd the raxx interface data pointer
555 Return Value:
556 None
558 Note:
559 ========================================================================
561 VOID RTMPFreeTxRxRingMemory(
562 IN PRTMP_ADAPTER pAd)
564 #define LM_URB_FREE(pObj, Context, BufferSize) \
565 if (NULL != Context->pUrb) { \
566 RTUSB_UNLINK_URB(Context->pUrb); \
567 RTUSB_FREE_URB(Context->pUrb); \
568 Context->pUrb = NULL; } \
569 if (NULL != Context->TransferBuffer) { \
570 RTUSB_URB_FREE_BUFFER(pObj->pUsb_Dev, BufferSize, \
571 Context->TransferBuffer, \
572 Context->data_dma); \
573 Context->TransferBuffer = NULL; }
576 UINT i, acidx;
577 PTX_CONTEXT pNullContext = &pAd->NullContext;
578 PTX_CONTEXT pPsPollContext = &pAd->PsPollContext;
579 PTX_CONTEXT pRTSContext = &pAd->RTSContext;
580 // PHT_TX_CONTEXT pHTTXContext;
581 //PRTMP_REORDERBUF pReorderBuf;
582 POS_COOKIE pObj = (POS_COOKIE) pAd->OS_Cookie;
583 // RTMP_TX_RING *pTxRing;
585 DBGPRINT(RT_DEBUG_ERROR, ("---> RTMPFreeTxRxRingMemory\n"));
586 pObj = pObj;
588 // Free all resources for the RECEIVE buffer queue.
589 for(i=0; i<(RX_RING_SIZE); i++)
591 PRX_CONTEXT pRxContext = &(pAd->RxContext[i]);
592 if (pRxContext)
593 LM_URB_FREE(pObj, pRxContext, MAX_RXBULK_SIZE);
596 // Free PsPoll frame resource
597 LM_URB_FREE(pObj, pPsPollContext, sizeof(TX_BUFFER));
599 // Free NULL frame resource
600 LM_URB_FREE(pObj, pNullContext, sizeof(TX_BUFFER));
602 // Free RTS frame resource
603 LM_URB_FREE(pObj, pRTSContext, sizeof(TX_BUFFER));
606 // Free beacon frame resource
607 for(i=0; i<BEACON_RING_SIZE; i++)
609 PTX_CONTEXT pBeaconContext = &(pAd->BeaconContext[i]);
610 if (pBeaconContext)
611 LM_URB_FREE(pObj, pBeaconContext, sizeof(TX_BUFFER));
615 // Free mgmt frame resource
616 for(i = 0; i < MGMT_RING_SIZE; i++)
618 PTX_CONTEXT pMLMEContext = (PTX_CONTEXT)pAd->MgmtRing.Cell[i].AllocVa;
619 //LM_URB_FREE(pObj, pMLMEContext, sizeof(TX_BUFFER));
620 if (NULL != pAd->MgmtRing.Cell[i].pNdisPacket)
622 RTMPFreeNdisPacket(pAd, pAd->MgmtRing.Cell[i].pNdisPacket);
623 pAd->MgmtRing.Cell[i].pNdisPacket = NULL;
624 pMLMEContext->TransferBuffer = NULL;
627 if (pMLMEContext)
629 if (NULL != pMLMEContext->pUrb)
631 RTUSB_UNLINK_URB(pMLMEContext->pUrb);
632 RTUSB_FREE_URB(pMLMEContext->pUrb);
633 pMLMEContext->pUrb = NULL;
637 if (pAd->MgmtDescRing.AllocVa)
638 NdisFreeMemory(pAd->MgmtDescRing.AllocVa, pAd->MgmtDescRing.AllocSize, 0);
641 // Free Tx frame resource
642 for(acidx=0; acidx<4; acidx++)
644 PHT_TX_CONTEXT pHTTXContext = &(pAd->TxContext[acidx]);
645 if (pHTTXContext)
646 LM_URB_FREE(pObj, pHTTXContext, sizeof(HTTX_BUFFER));
649 if (pAd->FragFrame.pFragPacket)
650 RELEASE_NDIS_PACKET(pAd, pAd->FragFrame.pFragPacket, NDIS_STATUS_SUCCESS);
652 for(i=0; i<6; i++)
654 NdisFreeSpinLock(&pAd->BulkOutLock[i]);
657 NdisFreeSpinLock(&pAd->BulkInLock);
658 NdisFreeSpinLock(&pAd->MLMEBulkOutLock);
660 NdisFreeSpinLock(&pAd->CmdQLock);
662 // Clear all pending bulk-out request flags.
663 RTUSB_CLEAR_BULK_FLAG(pAd, 0xffffffff);
665 // NdisFreeSpinLock(&pAd->MacTabLock);
667 // for(i=0; i<MAX_LEN_OF_BA_REC_TABLE; i++)
668 // {
669 // NdisFreeSpinLock(&pAd->BATable.BARecEntry[i].RxReRingLock);
670 // }
672 DBGPRINT(RT_DEBUG_ERROR, ("<--- ReleaseAdapter\n"));
677 ========================================================================
678 Routine Description:
679 Allocate memory for adapter control block.
681 Arguments:
682 pAd Pointer to our adapter
684 Return Value:
685 NDIS_STATUS_SUCCESS
686 NDIS_STATUS_FAILURE
687 NDIS_STATUS_RESOURCES
689 Note:
690 ========================================================================
692 NDIS_STATUS AdapterBlockAllocateMemory(
693 IN PVOID handle,
694 OUT PVOID *ppAd)
696 PUSB_DEV usb_dev;
697 POS_COOKIE pObj = (POS_COOKIE) handle;
700 usb_dev = pObj->pUsb_Dev;
702 pObj->MLMEThr_pid = NULL;
703 pObj->RTUSBCmdThr_pid = NULL;
705 *ppAd = (PVOID)vmalloc(sizeof(RTMP_ADAPTER));
707 if (*ppAd)
709 NdisZeroMemory(*ppAd, sizeof(RTMP_ADAPTER));
710 ((PRTMP_ADAPTER)*ppAd)->OS_Cookie = handle;
711 return (NDIS_STATUS_SUCCESS);
713 else
715 return (NDIS_STATUS_FAILURE);
721 ========================================================================
722 Routine Description:
723 Create kernel threads & tasklets.
725 Arguments:
726 *net_dev Pointer to wireless net device interface
728 Return Value:
729 NDIS_STATUS_SUCCESS
730 NDIS_STATUS_FAILURE
732 Note:
733 ========================================================================
735 NDIS_STATUS CreateThreads(
736 IN struct net_device *net_dev)
738 PRTMP_ADAPTER pAd = net_dev->ml_priv;
739 POS_COOKIE pObj = (POS_COOKIE) pAd->OS_Cookie;
740 pid_t pid_number;
742 //init_MUTEX(&(pAd->usbdev_semaphore));
744 init_MUTEX_LOCKED(&(pAd->mlme_semaphore));
745 init_completion (&pAd->mlmeComplete);
747 init_MUTEX_LOCKED(&(pAd->RTUSBCmd_semaphore));
748 init_completion (&pAd->CmdQComplete);
750 init_MUTEX_LOCKED(&(pAd->RTUSBTimer_semaphore));
751 init_completion (&pAd->TimerQComplete);
753 // Creat MLME Thread
754 pObj->MLMEThr_pid = NULL;
755 pid_number = kernel_thread(MlmeThread, pAd, CLONE_VM);
756 if (pid_number < 0)
758 printk (KERN_WARNING "%s: unable to start Mlme thread\n",pAd->net_dev->name);
759 return NDIS_STATUS_FAILURE;
762 pObj->MLMEThr_pid = find_get_pid(pid_number);
764 // Wait for the thread to start
765 wait_for_completion(&(pAd->mlmeComplete));
767 // Creat Command Thread
768 pObj->RTUSBCmdThr_pid = NULL;
769 pid_number = kernel_thread(RTUSBCmdThread, pAd, CLONE_VM);
770 if (pid_number < 0)
772 printk (KERN_WARNING "%s: unable to start RTUSBCmd thread\n",pAd->net_dev->name);
773 return NDIS_STATUS_FAILURE;
776 pObj->RTUSBCmdThr_pid = find_get_pid(pid_number);
778 wait_for_completion(&(pAd->CmdQComplete));
780 pObj->TimerQThr_pid = NULL;
781 pid_number = kernel_thread(TimerQThread, pAd, CLONE_VM);
782 if (pid_number < 0)
784 printk (KERN_WARNING "%s: unable to start TimerQThread\n",pAd->net_dev->name);
785 return NDIS_STATUS_FAILURE;
788 pObj->TimerQThr_pid = find_get_pid(pid_number);
790 // Wait for the thread to start
791 wait_for_completion(&(pAd->TimerQComplete));
793 // Create receive tasklet
794 tasklet_init(&pObj->rx_done_task, rx_done_tasklet, (ULONG)pAd);
795 tasklet_init(&pObj->mgmt_dma_done_task, rt2870_mgmt_dma_done_tasklet, (unsigned long)pAd);
796 tasklet_init(&pObj->ac0_dma_done_task, rt2870_ac0_dma_done_tasklet, (unsigned long)pAd);
797 tasklet_init(&pObj->ac1_dma_done_task, rt2870_ac1_dma_done_tasklet, (unsigned long)pAd);
798 tasklet_init(&pObj->ac2_dma_done_task, rt2870_ac2_dma_done_tasklet, (unsigned long)pAd);
799 tasklet_init(&pObj->ac3_dma_done_task, rt2870_ac3_dma_done_tasklet, (unsigned long)pAd);
800 tasklet_init(&pObj->hcca_dma_done_task, rt2870_hcca_dma_done_tasklet, (unsigned long)pAd);
801 tasklet_init(&pObj->tbtt_task, tbtt_tasklet, (unsigned long)pAd);
802 tasklet_init(&pObj->null_frame_complete_task, rt2870_null_frame_complete_tasklet, (unsigned long)pAd);
803 tasklet_init(&pObj->rts_frame_complete_task, rt2870_rts_frame_complete_tasklet, (unsigned long)pAd);
804 tasklet_init(&pObj->pspoll_frame_complete_task, rt2870_pspoll_frame_complete_tasklet, (unsigned long)pAd);
806 return NDIS_STATUS_SUCCESS;
810 ========================================================================
811 Routine Description:
812 As STA's BSSID is a WC too, it uses shared key table.
813 This function write correct unicast TX key to ASIC WCID.
814 And we still make a copy in our MacTab.Content[BSSID_WCID].PairwiseKey.
815 Caller guarantee TKIP/AES always has keyidx = 0. (pairwise key)
816 Caller guarantee WEP calls this function when set Txkey, default key index=0~3.
818 Arguments:
819 pAd Pointer to our adapter
820 pKey Pointer to the where the key stored
822 Return Value:
823 NDIS_SUCCESS Add key successfully
825 Note:
826 ========================================================================
828 VOID RTMPAddBSSIDCipher(
829 IN PRTMP_ADAPTER pAd,
830 IN UCHAR Aid,
831 IN PNDIS_802_11_KEY pKey,
832 IN UCHAR CipherAlg)
834 PUCHAR pTxMic, pRxMic;
835 BOOLEAN bKeyRSC, bAuthenticator; // indicate the receive SC set by KeyRSC value
836 // UCHAR CipherAlg;
837 UCHAR i;
838 ULONG WCIDAttri;
839 USHORT offset;
840 UCHAR KeyIdx, IVEIV[8];
841 UINT32 Value;
843 DBGPRINT(RT_DEBUG_TRACE, ("RTMPAddBSSIDCipher==> Aid = %d\n",Aid));
845 // Bit 29 of Add-key KeyRSC
846 bKeyRSC = (pKey->KeyIndex & 0x20000000) ? TRUE : FALSE;
848 // Bit 28 of Add-key Authenticator
849 bAuthenticator = (pKey->KeyIndex & 0x10000000) ? TRUE : FALSE;
850 KeyIdx = (UCHAR)pKey->KeyIndex&0xff;
852 if (KeyIdx > 4)
853 return;
856 if (pAd->MacTab.Content[Aid].PairwiseKey.CipherAlg == CIPHER_TKIP)
857 { if (pAd->StaCfg.AuthMode == Ndis802_11AuthModeWPANone)
859 // for WPA-None Tx, Rx MIC is the same
860 pTxMic = (PUCHAR) (&pKey->KeyMaterial) + 16;
861 pRxMic = pTxMic;
863 else if (bAuthenticator == TRUE)
865 pTxMic = (PUCHAR) (&pKey->KeyMaterial) + 16;
866 pRxMic = (PUCHAR) (&pKey->KeyMaterial) + 24;
868 else
870 pRxMic = (PUCHAR) (&pKey->KeyMaterial) + 16;
871 pTxMic = (PUCHAR) (&pKey->KeyMaterial) + 24;
874 offset = PAIRWISE_KEY_TABLE_BASE + (Aid * HW_KEY_ENTRY_SIZE) + 0x10;
875 for (i=0; i<8; )
877 Value = *(pTxMic+i);
878 Value += (*(pTxMic+i+1)<<8);
879 Value += (*(pTxMic+i+2)<<16);
880 Value += (*(pTxMic+i+3)<<24);
881 RTUSBWriteMACRegister(pAd, offset+i, Value);
882 i+=4;
885 offset = PAIRWISE_KEY_TABLE_BASE + (Aid * HW_KEY_ENTRY_SIZE) + 0x18;
886 for (i=0; i<8; )
888 Value = *(pRxMic+i);
889 Value += (*(pRxMic+i+1)<<8);
890 Value += (*(pRxMic+i+2)<<16);
891 Value += (*(pRxMic+i+3)<<24);
892 RTUSBWriteMACRegister(pAd, offset+i, Value);
893 i+=4;
896 // Only Key lenth equal to TKIP key have these
897 NdisMoveMemory(pAd->MacTab.Content[Aid].PairwiseKey.RxMic, pRxMic, 8);
898 NdisMoveMemory(pAd->MacTab.Content[Aid].PairwiseKey.TxMic, pTxMic, 8);
900 DBGPRINT(RT_DEBUG_TRACE,
901 (" TxMIC = %02x:%02x:%02x:%02x:%02x:%02x:%02x:%02x \n",
902 pTxMic[0],pTxMic[1],pTxMic[2],pTxMic[3],
903 pTxMic[4],pTxMic[5],pTxMic[6],pTxMic[7]));
904 DBGPRINT(RT_DEBUG_TRACE,
905 (" RxMIC = %02x:%02x:%02x:%02x:%02x:%02x:%02x:%02x \n",
906 pRxMic[0],pRxMic[1],pRxMic[2],pRxMic[3],
907 pRxMic[4],pRxMic[5],pRxMic[6],pRxMic[7]));
910 // 2. Record Security Key.
911 pAd->MacTab.Content[BSSID_WCID].PairwiseKey.KeyLen= (UCHAR)pKey->KeyLength;
912 NdisMoveMemory(pAd->MacTab.Content[Aid].PairwiseKey.Key, &pKey->KeyMaterial, pKey->KeyLength);
914 // 3. Check RxTsc. And used to init to ASIC IV.
915 if (bKeyRSC == TRUE)
916 NdisMoveMemory(pAd->MacTab.Content[Aid].PairwiseKey.RxTsc, &pKey->KeyRSC, 6);
917 else
918 NdisZeroMemory(pAd->MacTab.Content[Aid].PairwiseKey.RxTsc, 6);
920 // 4. Init TxTsc to one based on WiFi WPA specs
921 pAd->MacTab.Content[Aid].PairwiseKey.TxTsc[0] = 1;
922 pAd->MacTab.Content[Aid].PairwiseKey.TxTsc[1] = 0;
923 pAd->MacTab.Content[Aid].PairwiseKey.TxTsc[2] = 0;
924 pAd->MacTab.Content[Aid].PairwiseKey.TxTsc[3] = 0;
925 pAd->MacTab.Content[Aid].PairwiseKey.TxTsc[4] = 0;
926 pAd->MacTab.Content[Aid].PairwiseKey.TxTsc[5] = 0;
928 CipherAlg = pAd->MacTab.Content[Aid].PairwiseKey.CipherAlg;
930 offset = PAIRWISE_KEY_TABLE_BASE + (Aid * HW_KEY_ENTRY_SIZE);
931 RTUSBMultiWrite(pAd, (USHORT) offset, pKey->KeyMaterial,
932 ((pKey->KeyLength == LEN_TKIP_KEY) ? 16 : (USHORT)pKey->KeyLength));
934 offset = SHARED_KEY_TABLE_BASE + (KeyIdx * HW_KEY_ENTRY_SIZE);
935 RTUSBMultiWrite(pAd, (USHORT) offset, pKey->KeyMaterial, (USHORT)pKey->KeyLength);
937 offset = PAIRWISE_IVEIV_TABLE_BASE + (Aid * HW_IVEIV_ENTRY_SIZE);
938 NdisZeroMemory(IVEIV, 8);
940 // IV/EIV
941 if ((CipherAlg == CIPHER_TKIP) ||
942 (CipherAlg == CIPHER_TKIP_NO_MIC) ||
943 (CipherAlg == CIPHER_AES))
945 IVEIV[3] = 0x20; // Eiv bit on. keyid always 0 for pairwise key
947 // default key idx needs to set.
948 // in TKIP/AES KeyIdx = 0 , WEP KeyIdx is default tx key.
949 else
951 IVEIV[3] |= (KeyIdx<< 6);
953 RTUSBMultiWrite(pAd, (USHORT) offset, IVEIV, 8);
955 // WCID Attribute UDF:3, BSSIdx:3, Alg:3, Keytable:1=PAIRWISE KEY, BSSIdx is 0
956 if ((CipherAlg == CIPHER_TKIP) ||
957 (CipherAlg == CIPHER_TKIP_NO_MIC) ||
958 (CipherAlg == CIPHER_AES))
960 WCIDAttri = (CipherAlg<<1)|SHAREDKEYTABLE;
962 else
963 WCIDAttri = (CipherAlg<<1)|SHAREDKEYTABLE;
965 offset = MAC_WCID_ATTRIBUTE_BASE + (Aid* HW_WCID_ATTRI_SIZE);
966 RTUSBWriteMACRegister(pAd, offset, WCIDAttri);
967 RTUSBReadMACRegister(pAd, offset, &Value);
969 DBGPRINT(RT_DEBUG_TRACE, ("BSSID_WCID : offset = %x, WCIDAttri = %lx\n",
970 offset, WCIDAttri));
972 // pAddr
973 // Add Bssid mac address at linkup. not here. check!
974 /*offset = MAC_WCID_BASE + (BSSID_WCID * HW_WCID_ENTRY_SIZE);
975 *for (i=0; i<MAC_ADDR_LEN; i++)
977 RTMP_IO_WRITE8(pAd, offset+i, pKey->BSSID[i]);
981 DBGPRINT(RT_DEBUG_ERROR, ("AddBSSIDasWCIDEntry: Alg=%s, KeyLength = %d\n",
982 CipherName[CipherAlg], pKey->KeyLength));
983 DBGPRINT(RT_DEBUG_TRACE, ("Key [idx=%x] [KeyLen = %d]\n",
984 pKey->KeyIndex, pKey->KeyLength));
985 for(i=0; i<pKey->KeyLength; i++)
986 DBGPRINT_RAW(RT_DEBUG_TRACE,(" %x:", pKey->KeyMaterial[i]));
987 DBGPRINT(RT_DEBUG_TRACE,(" \n"));
991 ========================================================================
992 Routine Description:
993 Get a received packet.
995 Arguments:
996 pAd device control block
997 pSaveRxD receive descriptor information
998 *pbReschedule need reschedule flag
999 *pRxPending pending received packet flag
1001 Return Value:
1002 the recieved packet
1004 Note:
1005 ========================================================================
1007 #define RT2870_RXDMALEN_FIELD_SIZE 4
1008 PNDIS_PACKET GetPacketFromRxRing(
1009 IN PRTMP_ADAPTER pAd,
1010 OUT PRT28XX_RXD_STRUC pSaveRxD,
1011 OUT BOOLEAN *pbReschedule,
1012 IN OUT UINT32 *pRxPending)
1014 PRX_CONTEXT pRxContext;
1015 PNDIS_PACKET pSkb;
1016 PUCHAR pData;
1017 ULONG ThisFrameLen;
1018 ULONG RxBufferLength;
1019 PRXWI_STRUC pRxWI;
1021 pRxContext = &pAd->RxContext[pAd->NextRxBulkInReadIndex];
1022 if ((pRxContext->Readable == FALSE) || (pRxContext->InUse == TRUE))
1023 return NULL;
1025 RxBufferLength = pRxContext->BulkInOffset - pAd->ReadPosition;
1026 if (RxBufferLength < (RT2870_RXDMALEN_FIELD_SIZE + sizeof(RXWI_STRUC) + sizeof(RXINFO_STRUC)))
1028 goto label_null;
1031 pData = &pRxContext->TransferBuffer[pAd->ReadPosition]; /* 4KB */
1032 // The RXDMA field is 4 bytes, now just use the first 2 bytes. The Length including the (RXWI + MSDU + Padding)
1033 ThisFrameLen = *pData + (*(pData+1)<<8);
1034 if (ThisFrameLen == 0)
1036 DBGPRINT(RT_DEBUG_TRACE, ("BIRIdx(%d): RXDMALen is zero.[%ld], BulkInBufLen = %ld)\n",
1037 pAd->NextRxBulkInReadIndex, ThisFrameLen, pRxContext->BulkInOffset));
1038 goto label_null;
1040 if ((ThisFrameLen&0x3) != 0)
1042 DBGPRINT(RT_DEBUG_ERROR, ("BIRIdx(%d): RXDMALen not multiple of 4.[%ld], BulkInBufLen = %ld)\n",
1043 pAd->NextRxBulkInReadIndex, ThisFrameLen, pRxContext->BulkInOffset));
1044 goto label_null;
1047 if ((ThisFrameLen + 8)> RxBufferLength) // 8 for (RT2870_RXDMALEN_FIELD_SIZE + sizeof(RXINFO_STRUC))
1049 DBGPRINT(RT_DEBUG_TRACE,("BIRIdx(%d):FrameLen(0x%lx) outranges. BulkInLen=0x%lx, remaining RxBufLen=0x%lx, ReadPos=0x%lx\n",
1050 pAd->NextRxBulkInReadIndex, ThisFrameLen, pRxContext->BulkInOffset, RxBufferLength, pAd->ReadPosition));
1052 // error frame. finish this loop
1053 goto label_null;
1056 // skip USB frame length field
1057 pData += RT2870_RXDMALEN_FIELD_SIZE;
1058 pRxWI = (PRXWI_STRUC)pData;
1060 if (pRxWI->MPDUtotalByteCount > ThisFrameLen)
1062 DBGPRINT(RT_DEBUG_ERROR, ("%s():pRxWIMPDUtotalByteCount(%d) large than RxDMALen(%ld)\n",
1063 __func__, pRxWI->MPDUtotalByteCount, ThisFrameLen));
1064 goto label_null;
1067 // allocate a rx packet
1068 pSkb = dev_alloc_skb(ThisFrameLen);
1069 if (pSkb == NULL)
1071 DBGPRINT(RT_DEBUG_ERROR,("%s():Cannot Allocate sk buffer for this Bulk-In buffer!\n", __func__));
1072 goto label_null;
1075 // copy the rx packet
1076 memcpy(skb_put(pSkb, ThisFrameLen), pData, ThisFrameLen);
1077 RTPKT_TO_OSPKT(pSkb)->dev = get_netdev_from_bssid(pAd, BSS0);
1078 RTMP_SET_PACKET_SOURCE(OSPKT_TO_RTPKT(pSkb), PKTSRC_NDIS);
1080 // copy RxD
1081 *pSaveRxD = *(PRXINFO_STRUC)(pData + ThisFrameLen);
1083 // update next packet read position.
1084 pAd->ReadPosition += (ThisFrameLen + RT2870_RXDMALEN_FIELD_SIZE + RXINFO_SIZE); // 8 for (RT2870_RXDMALEN_FIELD_SIZE + sizeof(RXINFO_STRUC))
1086 return pSkb;
1088 label_null:
1090 return NULL;
1095 ========================================================================
1096 Routine Description:
1097 Handle received packets.
1099 Arguments:
1100 data - URB information pointer
1102 Return Value:
1103 None
1105 Note:
1106 ========================================================================
1108 static void rx_done_tasklet(unsigned long data)
1110 purbb_t pUrb;
1111 PRX_CONTEXT pRxContext;
1112 PRTMP_ADAPTER pAd;
1113 NTSTATUS Status;
1114 unsigned int IrqFlags;
1116 pUrb = (purbb_t)data;
1117 pRxContext = (PRX_CONTEXT)pUrb->context;
1118 pAd = pRxContext->pAd;
1119 Status = pUrb->status;
1122 RTMP_IRQ_LOCK(&pAd->BulkInLock, IrqFlags);
1123 pRxContext->InUse = FALSE;
1124 pRxContext->IRPPending = FALSE;
1125 pRxContext->BulkInOffset += pUrb->actual_length;
1126 //NdisInterlockedDecrement(&pAd->PendingRx);
1127 pAd->PendingRx--;
1129 if (Status == USB_ST_NOERROR)
1131 pAd->BulkInComplete++;
1132 pAd->NextRxBulkInPosition = 0;
1133 if (pRxContext->BulkInOffset) // As jan's comment, it may bulk-in success but size is zero.
1135 pRxContext->Readable = TRUE;
1136 INC_RING_INDEX(pAd->NextRxBulkInIndex, RX_RING_SIZE);
1138 RTMP_IRQ_UNLOCK(&pAd->BulkInLock, IrqFlags);
1140 else // STATUS_OTHER
1142 pAd->BulkInCompleteFail++;
1143 // Still read this packet although it may comtain wrong bytes.
1144 pRxContext->Readable = FALSE;
1145 RTMP_IRQ_UNLOCK(&pAd->BulkInLock, IrqFlags);
1147 // Parsing all packets. because after reset, the index will reset to all zero.
1148 if ((!RTMP_TEST_FLAG(pAd, (fRTMP_ADAPTER_RESET_IN_PROGRESS |
1149 fRTMP_ADAPTER_BULKIN_RESET |
1150 fRTMP_ADAPTER_HALT_IN_PROGRESS |
1151 fRTMP_ADAPTER_NIC_NOT_EXIST))))
1154 DBGPRINT_RAW(RT_DEBUG_ERROR, ("Bulk In Failed. Status=%d, BIIdx=0x%x, BIRIdx=0x%x, actual_length= 0x%x\n",
1155 Status, pAd->NextRxBulkInIndex, pAd->NextRxBulkInReadIndex, pRxContext->pUrb->actual_length));
1157 RTMP_SET_FLAG(pAd, fRTMP_ADAPTER_BULKIN_RESET);
1158 RTUSBEnqueueInternalCmd(pAd, CMDTHREAD_RESET_BULK_IN, NULL, 0);
1162 ASSERT((pRxContext->InUse == pRxContext->IRPPending));
1164 RTUSBBulkReceive(pAd);
1166 return;
1171 static void rt2870_mgmt_dma_done_tasklet(unsigned long data)
1173 PRTMP_ADAPTER pAd;
1174 PTX_CONTEXT pMLMEContext;
1175 int index;
1176 PNDIS_PACKET pPacket;
1177 purbb_t pUrb;
1178 NTSTATUS Status;
1179 unsigned long IrqFlags;
1182 pUrb = (purbb_t)data;
1183 pMLMEContext = (PTX_CONTEXT)pUrb->context;
1184 pAd = pMLMEContext->pAd;
1185 Status = pUrb->status;
1186 index = pMLMEContext->SelfIdx;
1188 ASSERT((pAd->MgmtRing.TxDmaIdx == index));
1190 RTMP_IRQ_LOCK(&pAd->BulkOutLock[MGMTPIPEIDX], IrqFlags);
1193 if (Status != USB_ST_NOERROR)
1195 //Bulk-Out fail status handle
1196 if ((!RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_RESET_IN_PROGRESS)) &&
1197 (!RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_HALT_IN_PROGRESS)) &&
1198 (!RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_NIC_NOT_EXIST)) &&
1199 (!RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_BULKOUT_RESET)))
1201 DBGPRINT_RAW(RT_DEBUG_ERROR, ("Bulk Out MLME Failed, Status=%d!\n", Status));
1202 // TODO: How to handle about the MLMEBulkOut failed issue. Need to resend the mgmt pkt?
1203 RTMP_SET_FLAG(pAd, fRTMP_ADAPTER_BULKOUT_RESET);
1204 pAd->bulkResetPipeid = (MGMTPIPEIDX | BULKOUT_MGMT_RESET_FLAG);
1208 pAd->BulkOutPending[MGMTPIPEIDX] = FALSE;
1209 RTMP_IRQ_UNLOCK(&pAd->BulkOutLock[MGMTPIPEIDX], IrqFlags);
1211 RTMP_IRQ_LOCK(&pAd->MLMEBulkOutLock, IrqFlags);
1212 // Reset MLME context flags
1213 pMLMEContext->IRPPending = FALSE;
1214 pMLMEContext->InUse = FALSE;
1215 pMLMEContext->bWaitingBulkOut = FALSE;
1216 pMLMEContext->BulkOutSize = 0;
1218 pPacket = pAd->MgmtRing.Cell[index].pNdisPacket;
1219 pAd->MgmtRing.Cell[index].pNdisPacket = NULL;
1221 // Increase MgmtRing Index
1222 INC_RING_INDEX(pAd->MgmtRing.TxDmaIdx, MGMT_RING_SIZE);
1223 pAd->MgmtRing.TxSwFreeIdx++;
1224 RTMP_IRQ_UNLOCK(&pAd->MLMEBulkOutLock, IrqFlags);
1226 // No-matter success or fail, we free the mgmt packet.
1227 if (pPacket)
1228 RTMPFreeNdisPacket(pAd, pPacket);
1230 if ((RTMP_TEST_FLAG(pAd, (fRTMP_ADAPTER_RESET_IN_PROGRESS |
1231 fRTMP_ADAPTER_HALT_IN_PROGRESS |
1232 fRTMP_ADAPTER_NIC_NOT_EXIST))))
1234 // do nothing and return directly.
1236 else
1238 if (RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_BULKOUT_RESET) &&
1239 ((pAd->bulkResetPipeid & BULKOUT_MGMT_RESET_FLAG) == BULKOUT_MGMT_RESET_FLAG))
1240 { // For Mgmt Bulk-Out failed, ignore it now.
1241 RTUSBEnqueueInternalCmd(pAd, CMDTHREAD_RESET_BULK_OUT, NULL, 0);
1243 else
1246 // Always call Bulk routine, even reset bulk.
1247 // The protectioon of rest bulk should be in BulkOut routine
1248 if (pAd->MgmtRing.TxSwFreeIdx < MGMT_RING_SIZE /* pMLMEContext->bWaitingBulkOut == TRUE */)
1250 RTUSB_SET_BULK_FLAG(pAd, fRTUSB_BULK_OUT_MLME);
1252 RTUSBKickBulkOut(pAd);
1259 static void rt2870_hcca_dma_done_tasklet(unsigned long data)
1261 PRTMP_ADAPTER pAd;
1262 PHT_TX_CONTEXT pHTTXContext;
1263 UCHAR BulkOutPipeId = 4;
1264 purbb_t pUrb;
1266 DBGPRINT_RAW(RT_DEBUG_ERROR, ("--->hcca_dma_done_tasklet\n"));
1268 pUrb = (purbb_t)data;
1269 pHTTXContext = (PHT_TX_CONTEXT)pUrb->context;
1270 pAd = pHTTXContext->pAd;
1272 rt2870_dataout_complete_tasklet((unsigned long)pUrb);
1274 if ((RTMP_TEST_FLAG(pAd, (fRTMP_ADAPTER_RESET_IN_PROGRESS |
1275 fRTMP_ADAPTER_HALT_IN_PROGRESS |
1276 fRTMP_ADAPTER_NIC_NOT_EXIST))))
1278 // do nothing and return directly.
1280 else
1282 if (RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_BULKOUT_RESET))
1284 RTUSBEnqueueInternalCmd(pAd, CMDTHREAD_RESET_BULK_OUT, NULL, 0);
1286 else
1287 { pHTTXContext = &pAd->TxContext[BulkOutPipeId];
1288 if ((pAd->TxSwQueue[BulkOutPipeId].Number > 0) &&
1289 /*((pHTTXContext->CurWritePosition > (pHTTXContext->NextBulkOutPosition + 0x6000)) || (pHTTXContext->NextBulkOutPosition > pHTTXContext->CurWritePosition + 0x6000)) && */
1290 (pAd->DeQueueRunning[BulkOutPipeId] == FALSE) &&
1291 (pHTTXContext->bCurWriting == FALSE))
1293 RTMPDeQueuePacket(pAd, FALSE, BulkOutPipeId, MAX_TX_PROCESS);
1296 RTUSB_SET_BULK_FLAG(pAd, fRTUSB_BULK_OUT_DATA_NORMAL<<4);
1297 RTUSBKickBulkOut(pAd);
1301 DBGPRINT_RAW(RT_DEBUG_ERROR, ("<---hcca_dma_done_tasklet\n"));
1305 static void rt2870_ac3_dma_done_tasklet(unsigned long data)
1307 PRTMP_ADAPTER pAd;
1308 PHT_TX_CONTEXT pHTTXContext;
1309 UCHAR BulkOutPipeId = 3;
1310 purbb_t pUrb;
1313 pUrb = (purbb_t)data;
1314 pHTTXContext = (PHT_TX_CONTEXT)pUrb->context;
1315 pAd = pHTTXContext->pAd;
1317 rt2870_dataout_complete_tasklet((unsigned long)pUrb);
1319 if ((RTMP_TEST_FLAG(pAd, (fRTMP_ADAPTER_RESET_IN_PROGRESS |
1320 fRTMP_ADAPTER_HALT_IN_PROGRESS |
1321 fRTMP_ADAPTER_NIC_NOT_EXIST))))
1323 // do nothing and return directly.
1325 else
1327 if (RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_BULKOUT_RESET))
1329 RTUSBEnqueueInternalCmd(pAd, CMDTHREAD_RESET_BULK_OUT, NULL, 0);
1331 else
1332 { pHTTXContext = &pAd->TxContext[BulkOutPipeId];
1333 if ((pAd->TxSwQueue[BulkOutPipeId].Number > 0) &&
1334 /*((pHTTXContext->CurWritePosition > (pHTTXContext->NextBulkOutPosition + 0x6000)) || (pHTTXContext->NextBulkOutPosition > pHTTXContext->CurWritePosition + 0x6000)) && */
1335 (pAd->DeQueueRunning[BulkOutPipeId] == FALSE) &&
1336 (pHTTXContext->bCurWriting == FALSE))
1338 RTMPDeQueuePacket(pAd, FALSE, BulkOutPipeId, MAX_TX_PROCESS);
1341 RTUSB_SET_BULK_FLAG(pAd, fRTUSB_BULK_OUT_DATA_NORMAL<<3);
1342 RTUSBKickBulkOut(pAd);
1347 return;
1351 static void rt2870_ac2_dma_done_tasklet(unsigned long data)
1353 PRTMP_ADAPTER pAd;
1354 PHT_TX_CONTEXT pHTTXContext;
1355 UCHAR BulkOutPipeId = 2;
1356 purbb_t pUrb;
1359 pUrb = (purbb_t)data;
1360 pHTTXContext = (PHT_TX_CONTEXT)pUrb->context;
1361 pAd = pHTTXContext->pAd;
1363 rt2870_dataout_complete_tasklet((unsigned long)pUrb);
1365 if ((RTMP_TEST_FLAG(pAd, (fRTMP_ADAPTER_RESET_IN_PROGRESS |
1366 fRTMP_ADAPTER_HALT_IN_PROGRESS |
1367 fRTMP_ADAPTER_NIC_NOT_EXIST))))
1369 // do nothing and return directly.
1371 else
1373 if (RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_BULKOUT_RESET))
1375 RTUSBEnqueueInternalCmd(pAd, CMDTHREAD_RESET_BULK_OUT, NULL, 0);
1377 else
1378 { pHTTXContext = &pAd->TxContext[BulkOutPipeId];
1379 if ((pAd->TxSwQueue[BulkOutPipeId].Number > 0) &&
1380 /*((pHTTXContext->CurWritePosition > (pHTTXContext->NextBulkOutPosition + 0x6000)) || (pHTTXContext->NextBulkOutPosition > pHTTXContext->CurWritePosition + 0x6000)) && */
1381 (pAd->DeQueueRunning[BulkOutPipeId] == FALSE) &&
1382 (pHTTXContext->bCurWriting == FALSE))
1384 RTMPDeQueuePacket(pAd, FALSE, BulkOutPipeId, MAX_TX_PROCESS);
1387 RTUSB_SET_BULK_FLAG(pAd, fRTUSB_BULK_OUT_DATA_NORMAL<<2);
1388 RTUSBKickBulkOut(pAd);
1392 return;
1396 static void rt2870_ac1_dma_done_tasklet(unsigned long data)
1398 PRTMP_ADAPTER pAd;
1399 PHT_TX_CONTEXT pHTTXContext;
1400 UCHAR BulkOutPipeId = 1;
1401 purbb_t pUrb;
1404 pUrb = (purbb_t)data;
1405 pHTTXContext = (PHT_TX_CONTEXT)pUrb->context;
1406 pAd = pHTTXContext->pAd;
1408 rt2870_dataout_complete_tasklet((unsigned long)pUrb);
1410 if ((RTMP_TEST_FLAG(pAd, (fRTMP_ADAPTER_RESET_IN_PROGRESS |
1411 fRTMP_ADAPTER_HALT_IN_PROGRESS |
1412 fRTMP_ADAPTER_NIC_NOT_EXIST))))
1414 // do nothing and return directly.
1416 else
1418 if (RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_BULKOUT_RESET))
1420 RTUSBEnqueueInternalCmd(pAd, CMDTHREAD_RESET_BULK_OUT, NULL, 0);
1422 else
1423 { pHTTXContext = &pAd->TxContext[BulkOutPipeId];
1424 if ((pAd->TxSwQueue[BulkOutPipeId].Number > 0) &&
1425 /*((pHTTXContext->CurWritePosition > (pHTTXContext->NextBulkOutPosition + 0x6000)) || (pHTTXContext->NextBulkOutPosition > pHTTXContext->CurWritePosition + 0x6000)) && */
1426 (pAd->DeQueueRunning[BulkOutPipeId] == FALSE) &&
1427 (pHTTXContext->bCurWriting == FALSE))
1429 RTMPDeQueuePacket(pAd, FALSE, BulkOutPipeId, MAX_TX_PROCESS);
1432 RTUSB_SET_BULK_FLAG(pAd, fRTUSB_BULK_OUT_DATA_NORMAL<<1);
1433 RTUSBKickBulkOut(pAd);
1438 return;
1442 static void rt2870_ac0_dma_done_tasklet(unsigned long data)
1444 PRTMP_ADAPTER pAd;
1445 PHT_TX_CONTEXT pHTTXContext;
1446 UCHAR BulkOutPipeId = 0;
1447 purbb_t pUrb;
1450 pUrb = (purbb_t)data;
1451 pHTTXContext = (PHT_TX_CONTEXT)pUrb->context;
1452 pAd = pHTTXContext->pAd;
1454 rt2870_dataout_complete_tasklet((unsigned long)pUrb);
1456 if ((RTMP_TEST_FLAG(pAd, (fRTMP_ADAPTER_RESET_IN_PROGRESS |
1457 fRTMP_ADAPTER_HALT_IN_PROGRESS |
1458 fRTMP_ADAPTER_NIC_NOT_EXIST))))
1460 // do nothing and return directly.
1462 else
1464 if (RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_BULKOUT_RESET))
1466 RTUSBEnqueueInternalCmd(pAd, CMDTHREAD_RESET_BULK_OUT, NULL, 0);
1468 else
1469 { pHTTXContext = &pAd->TxContext[BulkOutPipeId];
1470 if ((pAd->TxSwQueue[BulkOutPipeId].Number > 0) &&
1471 /* ((pHTTXContext->CurWritePosition > (pHTTXContext->NextBulkOutPosition + 0x6000)) || (pHTTXContext->NextBulkOutPosition > pHTTXContext->CurWritePosition + 0x6000)) && */
1472 (pAd->DeQueueRunning[BulkOutPipeId] == FALSE) &&
1473 (pHTTXContext->bCurWriting == FALSE))
1475 RTMPDeQueuePacket(pAd, FALSE, BulkOutPipeId, MAX_TX_PROCESS);
1478 RTUSB_SET_BULK_FLAG(pAd, fRTUSB_BULK_OUT_DATA_NORMAL);
1479 RTUSBKickBulkOut(pAd);
1484 return;
1489 static void rt2870_null_frame_complete_tasklet(unsigned long data)
1491 PRTMP_ADAPTER pAd;
1492 PTX_CONTEXT pNullContext;
1493 purbb_t pUrb;
1494 NTSTATUS Status;
1495 unsigned long irqFlag;
1498 pUrb = (purbb_t)data;
1499 pNullContext = (PTX_CONTEXT)pUrb->context;
1500 pAd = pNullContext->pAd;
1501 Status = pUrb->status;
1503 // Reset Null frame context flags
1504 RTMP_IRQ_LOCK(&pAd->BulkOutLock[0], irqFlag);
1505 pNullContext->IRPPending = FALSE;
1506 pNullContext->InUse = FALSE;
1507 pAd->BulkOutPending[0] = FALSE;
1508 pAd->watchDogTxPendingCnt[0] = 0;
1510 if (Status == USB_ST_NOERROR)
1512 RTMP_IRQ_UNLOCK(&pAd->BulkOutLock[0], irqFlag);
1514 RTMPDeQueuePacket(pAd, FALSE, NUM_OF_TX_RING, MAX_TX_PROCESS);
1516 else // STATUS_OTHER
1518 if ((!RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_RESET_IN_PROGRESS)) &&
1519 (!RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_HALT_IN_PROGRESS)) &&
1520 (!RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_NIC_NOT_EXIST)) &&
1521 (!RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_BULKOUT_RESET)))
1523 DBGPRINT_RAW(RT_DEBUG_ERROR, ("Bulk Out Null Frame Failed, ReasonCode=%d!\n", Status));
1524 RTMP_SET_FLAG(pAd, fRTMP_ADAPTER_BULKOUT_RESET);
1525 pAd->bulkResetPipeid = (MGMTPIPEIDX | BULKOUT_MGMT_RESET_FLAG);
1526 RTMP_IRQ_UNLOCK(&pAd->BulkOutLock[0], irqFlag);
1527 RTUSBEnqueueInternalCmd(pAd, CMDTHREAD_RESET_BULK_OUT, NULL, 0);
1529 else
1531 RTMP_IRQ_UNLOCK(&pAd->BulkOutLock[0], irqFlag);
1535 // Always call Bulk routine, even reset bulk.
1536 // The protectioon of rest bulk should be in BulkOut routine
1537 RTUSBKickBulkOut(pAd);
1542 static void rt2870_rts_frame_complete_tasklet(unsigned long data)
1544 PRTMP_ADAPTER pAd;
1545 PTX_CONTEXT pRTSContext;
1546 purbb_t pUrb;
1547 NTSTATUS Status;
1548 unsigned long irqFlag;
1551 pUrb = (purbb_t)data;
1552 pRTSContext = (PTX_CONTEXT)pUrb->context;
1553 pAd = pRTSContext->pAd;
1554 Status = pUrb->status;
1556 // Reset RTS frame context flags
1557 RTMP_IRQ_LOCK(&pAd->BulkOutLock[0], irqFlag);
1558 pRTSContext->IRPPending = FALSE;
1559 pRTSContext->InUse = FALSE;
1561 if (Status == USB_ST_NOERROR)
1563 RTMP_IRQ_UNLOCK(&pAd->BulkOutLock[0], irqFlag);
1564 RTMPDeQueuePacket(pAd, FALSE, NUM_OF_TX_RING, MAX_TX_PROCESS);
1566 else // STATUS_OTHER
1568 if ((!RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_RESET_IN_PROGRESS)) &&
1569 (!RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_HALT_IN_PROGRESS)) &&
1570 (!RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_NIC_NOT_EXIST)) &&
1571 (!RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_BULKOUT_RESET)))
1573 DBGPRINT_RAW(RT_DEBUG_ERROR, ("Bulk Out RTS Frame Failed\n"));
1574 RTMP_SET_FLAG(pAd, fRTMP_ADAPTER_BULKOUT_RESET);
1575 pAd->bulkResetPipeid = (MGMTPIPEIDX | BULKOUT_MGMT_RESET_FLAG);
1576 RTMP_IRQ_UNLOCK(&pAd->BulkOutLock[0], irqFlag);
1577 RTUSBEnqueueInternalCmd(pAd, CMDTHREAD_RESET_BULK_OUT, NULL, 0);
1579 else
1581 RTMP_IRQ_UNLOCK(&pAd->BulkOutLock[0], irqFlag);
1585 RTMP_SEM_LOCK(&pAd->BulkOutLock[pRTSContext->BulkOutPipeId]);
1586 pAd->BulkOutPending[pRTSContext->BulkOutPipeId] = FALSE;
1587 RTMP_SEM_UNLOCK(&pAd->BulkOutLock[pRTSContext->BulkOutPipeId]);
1589 // Always call Bulk routine, even reset bulk.
1590 // The protectioon of rest bulk should be in BulkOut routine
1591 RTUSBKickBulkOut(pAd);
1596 static void rt2870_pspoll_frame_complete_tasklet(unsigned long data)
1598 PRTMP_ADAPTER pAd;
1599 PTX_CONTEXT pPsPollContext;
1600 purbb_t pUrb;
1601 NTSTATUS Status;
1604 pUrb = (purbb_t)data;
1605 pPsPollContext = (PTX_CONTEXT)pUrb->context;
1606 pAd = pPsPollContext->pAd;
1607 Status = pUrb->status;
1609 // Reset PsPoll context flags
1610 pPsPollContext->IRPPending = FALSE;
1611 pPsPollContext->InUse = FALSE;
1612 pAd->watchDogTxPendingCnt[0] = 0;
1614 if (Status == USB_ST_NOERROR)
1616 RTMPDeQueuePacket(pAd, FALSE, NUM_OF_TX_RING, MAX_TX_PROCESS);
1618 else // STATUS_OTHER
1620 if ((!RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_RESET_IN_PROGRESS)) &&
1621 (!RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_HALT_IN_PROGRESS)) &&
1622 (!RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_NIC_NOT_EXIST)) &&
1623 (!RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_BULKOUT_RESET)))
1625 DBGPRINT_RAW(RT_DEBUG_ERROR, ("Bulk Out PSPoll Failed\n"));
1626 RTMP_SET_FLAG(pAd, fRTMP_ADAPTER_BULKOUT_RESET);
1627 pAd->bulkResetPipeid = (MGMTPIPEIDX | BULKOUT_MGMT_RESET_FLAG);
1628 RTUSBEnqueueInternalCmd(pAd, CMDTHREAD_RESET_BULK_OUT, NULL, 0);
1632 RTMP_SEM_LOCK(&pAd->BulkOutLock[0]);
1633 pAd->BulkOutPending[0] = FALSE;
1634 RTMP_SEM_UNLOCK(&pAd->BulkOutLock[0]);
1636 // Always call Bulk routine, even reset bulk.
1637 // The protectioon of rest bulk should be in BulkOut routine
1638 RTUSBKickBulkOut(pAd);
1643 static void rt2870_dataout_complete_tasklet(unsigned long data)
1645 PRTMP_ADAPTER pAd;
1646 purbb_t pUrb;
1647 POS_COOKIE pObj;
1648 PHT_TX_CONTEXT pHTTXContext;
1649 UCHAR BulkOutPipeId;
1650 NTSTATUS Status;
1651 unsigned long IrqFlags;
1654 pUrb = (purbb_t)data;
1655 pHTTXContext = (PHT_TX_CONTEXT)pUrb->context;
1656 pAd = pHTTXContext->pAd;
1657 pObj = (POS_COOKIE) pAd->OS_Cookie;
1658 Status = pUrb->status;
1660 // Store BulkOut PipeId
1661 BulkOutPipeId = pHTTXContext->BulkOutPipeId;
1662 pAd->BulkOutDataOneSecCount++;
1664 //DBGPRINT(RT_DEBUG_LOUD, ("Done-B(%d):I=0x%lx, CWPos=%ld, NBPos=%ld, ENBPos=%ld, bCopy=%d!\n", BulkOutPipeId, in_interrupt(), pHTTXContext->CurWritePosition,
1665 // pHTTXContext->NextBulkOutPosition, pHTTXContext->ENextBulkOutPosition, pHTTXContext->bCopySavePad));
1667 RTMP_IRQ_LOCK(&pAd->BulkOutLock[BulkOutPipeId], IrqFlags);
1668 pAd->BulkOutPending[BulkOutPipeId] = FALSE;
1669 pHTTXContext->IRPPending = FALSE;
1670 pAd->watchDogTxPendingCnt[BulkOutPipeId] = 0;
1672 if (Status == USB_ST_NOERROR)
1674 pAd->BulkOutComplete++;
1676 RTMP_IRQ_UNLOCK(&pAd->BulkOutLock[BulkOutPipeId], IrqFlags);
1678 pAd->Counters8023.GoodTransmits++;
1679 //RTMP_IRQ_LOCK(&pAd->TxContextQueueLock[BulkOutPipeId], IrqFlags);
1680 FREE_HTTX_RING(pAd, BulkOutPipeId, pHTTXContext);
1681 //RTMP_IRQ_UNLOCK(&pAd->TxContextQueueLock[BulkOutPipeId], IrqFlags);
1685 else // STATUS_OTHER
1687 PUCHAR pBuf;
1689 pAd->BulkOutCompleteOther++;
1691 pBuf = &pHTTXContext->TransferBuffer->field.WirelessPacket[pHTTXContext->NextBulkOutPosition];
1693 if (!RTMP_TEST_FLAG(pAd, (fRTMP_ADAPTER_RESET_IN_PROGRESS |
1694 fRTMP_ADAPTER_HALT_IN_PROGRESS |
1695 fRTMP_ADAPTER_NIC_NOT_EXIST |
1696 fRTMP_ADAPTER_BULKOUT_RESET)))
1698 RTMP_SET_FLAG(pAd, fRTMP_ADAPTER_BULKOUT_RESET);
1699 pAd->bulkResetPipeid = BulkOutPipeId;
1700 pAd->bulkResetReq[BulkOutPipeId] = pAd->BulkOutReq;
1702 RTMP_IRQ_UNLOCK(&pAd->BulkOutLock[BulkOutPipeId], IrqFlags);
1704 DBGPRINT_RAW(RT_DEBUG_ERROR, ("BulkOutDataPacket failed: ReasonCode=%d!\n", Status));
1705 DBGPRINT_RAW(RT_DEBUG_ERROR, ("\t>>BulkOut Req=0x%lx, Complete=0x%lx, Other=0x%lx\n", pAd->BulkOutReq, pAd->BulkOutComplete, pAd->BulkOutCompleteOther));
1706 DBGPRINT_RAW(RT_DEBUG_ERROR, ("\t>>BulkOut Header:%x %x %x %x %x %x %x %x\n", pBuf[0], pBuf[1], pBuf[2], pBuf[3], pBuf[4], pBuf[5], pBuf[6], pBuf[7]));
1707 //DBGPRINT_RAW(RT_DEBUG_ERROR, (">>BulkOutCompleteCancel=0x%x, BulkOutCompleteOther=0x%x\n", pAd->BulkOutCompleteCancel, pAd->BulkOutCompleteOther));
1712 // bInUse = TRUE, means some process are filling TX data, after that must turn on bWaitingBulkOut
1713 // bWaitingBulkOut = TRUE, means the TX data are waiting for bulk out.
1715 //RTMP_IRQ_LOCK(&pAd->TxContextQueueLock[BulkOutPipeId], IrqFlags);
1716 if ((pHTTXContext->ENextBulkOutPosition != pHTTXContext->CurWritePosition) &&
1717 (pHTTXContext->ENextBulkOutPosition != (pHTTXContext->CurWritePosition+8)) &&
1718 !RTUSB_TEST_BULK_FLAG(pAd, (fRTUSB_BULK_OUT_DATA_FRAG << BulkOutPipeId)))
1720 // Indicate There is data avaliable
1721 RTUSB_SET_BULK_FLAG(pAd, (fRTUSB_BULK_OUT_DATA_NORMAL << BulkOutPipeId));
1723 //RTMP_IRQ_UNLOCK(&pAd->TxContextQueueLock[BulkOutPipeId], IrqFlags);
1725 // Always call Bulk routine, even reset bulk.
1726 // The protection of rest bulk should be in BulkOut routine
1727 RTUSBKickBulkOut(pAd);
1730 /* End of 2870_rtmp_init.c */