1 /**************************************************************************** 2 **+-----------------------------------------------------------------------+** 3 **| |** 4 **| Copyright(c) 1998 - 2008 Texas Instruments. All rights reserved. |** 5 **| All rights reserved. |** 6 **| |** 7 **| Redistribution and use in source and binary forms, with or without |** 8 **| modification, are permitted provided that the following conditions |** 9 **| are met: |** 10 **| |** 11 **| * Redistributions of source code must retain the above copyright |** 12 **| notice, this list of conditions and the following disclaimer. |** 13 **| * Redistributions in binary form must reproduce the above copyright |** 14 **| notice, this list of conditions and the following disclaimer in |** 15 **| the documentation and/or other materials provided with the |** 16 **| distribution. |** 17 **| * Neither the name Texas Instruments nor the names of its |** 18 **| contributors may be used to endorse or promote products derived |** 19 **| from this software without specific prior written permission. |** 20 **| |** 21 **| THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS |** 22 **| "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT |** 23 **| LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR |** 24 **| A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT |** 25 **| OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, |** 26 **| SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT |** 27 **| LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, |** 28 **| DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY |** 29 **| THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT |** 30 **| (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE |** 31 **| OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. |** 32 **| |** 33 **+-----------------------------------------------------------------------+** 34 ****************************************************************************/ 35 36 /**************************************************************************** 37 * 38 * MODULE: TNETW_Driver_Tx.c 39 * 40 * PURPOSE: TNETW_Driver Tx API functions needed externally to the driver. 41 * 42 ****************************************************************************/ 43 44 #include "whalParams.h" 45 #include "report.h" 46 #include "TNETW_Driver_api.h" 47 #include "txCtrlBlk_api.h" 48 #include "txHwQueue_api.h" 49 #include "txXfer_api.h" 50 #include "txResult_api.h" 51 #include "TNETW_Driver.h" 52 53 54 static systemStatus_e ConvertTxResultStatus(TxDescStatus_enum txResultStatus); 55 56 57 /**************************************************************************** 58 * Tx Control Block API functions * 59 ****************************************************************************/ 60 61 txCtrlBlkEntry_t *TnetwDrv_txCtrlBlk_alloc(TI_HANDLE hTnetwDrv) 62 { 63 TnetwDrv_t *pTnetwDrv = (TnetwDrv_t *)hTnetwDrv; 64 65 return txCtrlBlk_alloc(pTnetwDrv->hTxCtrlBlk); 66 } 67 68 69 void TnetwDrv_txCtrlBlk_free(TI_HANDLE hTnetwDrv, txCtrlBlkEntry_t *pCurrentEntry) 70 { 71 TnetwDrv_t *pTnetwDrv = (TnetwDrv_t *)hTnetwDrv; 72 73 txCtrlBlk_free(pTnetwDrv->hTxCtrlBlk, pCurrentEntry); 74 } 75 76 77 txCtrlBlkEntry_t *TnetwDrv_txCtrlBlk_GetPointer(TI_HANDLE hTnetwDrv, UINT8 descId) 78 { 79 TnetwDrv_t *pTnetwDrv = (TnetwDrv_t *)hTnetwDrv; 80 81 return txCtrlBlk_GetPointer(pTnetwDrv->hTxCtrlBlk, descId); 82 } 83 84 85 86 /**************************************************************************** 87 * Tx HW Queue API functions * 88 ****************************************************************************/ 89 90 TI_STATUS TnetwDrv_txHwQueue_alloc(TI_HANDLE hTnetwDrv, txCtrlBlkEntry_t *pPktCtrlBlk) 91 { 92 TnetwDrv_t *pTnetwDrv = (TnetwDrv_t *)hTnetwDrv; 93 94 return txHwQueue_alloc(pTnetwDrv->hTxHwQueue, pPktCtrlBlk); 95 } 96 97 98 TI_STATUS TnetwDrv_txHwQueue_free(TI_HANDLE hTnetwDrv, txCtrlBlkEntry_t *pPktCtrlBlk) 99 { 100 TnetwDrv_t *pTnetwDrv = (TnetwDrv_t *)hTnetwDrv; 101 102 return txHwQueue_free(pTnetwDrv->hTxHwQueue, pPktCtrlBlk); 103 } 104 105 106 UINT8 TnetwDrv_txHwQueue_GetUsedHwBlks(TI_HANDLE hTnetwDrv, int TxQid) 107 { 108 TnetwDrv_t *pTnetwDrv = (TnetwDrv_t *)hTnetwDrv; 109 110 return txHwQueue_GetUsedHwBlks(pTnetwDrv->hTxHwQueue, TxQid); 111 } 112 113 114 115 /**************************************************************************** 116 * Tx Xfer API functions * 117 ****************************************************************************/ 118 119 systemStatus_e TnetwDrv_txXfer_sendPacket(TI_HANDLE hTnetwDrv, 120 const void *aFrame, /* Pointer to the packet content. points to */ 121 /* the place that the actual packet begins. */ 122 /* a size of TX_TOTAL_OFFSET_BEFORE_DATA */ 123 /* must be saved before that pointer */ 124 UINT16 aLength, /* MSDU length from first byte of MAC */ 125 /* header to last byteof frame body. */ 126 UINT8 aQueueId, /* Tx queue as defined in ConfigureQueue. */ 127 UINT8 aTxRateClassId, /* Tx rate class ID defined in txRatePolicy.*/ 128 UINT16 aMaxTransmitRate,/* A bit mask that specifies the initial */ 129 /* (highest) rate to use. */ 130 BOOL aMore, /* Tells if there is another packet coming */ 131 /* shortly after this one. */ 132 UINT32 aPacketId, /* Packet identifier used as a context by */ 133 /* the host driver. */ 134 UINT8 aPowerLevel, /* Transmission power level. */ 135 UINT32 aExpiryTime, /* Time left for this MSDU to live. */ 136 void *aReserved) /* Optional parameters pointer. */ 137 138 { 139 TnetwDrv_t *pTnetwDrv = (TnetwDrv_t *)hTnetwDrv; 140 TxDescCtrl_t txAttr, *pTxAttr = &txAttr; /* A union for setting the txAttr bit fields. */ 141 dot11_header_t *pDot11Hdr; 142 systemStatus_e status; 143 txCtrlBlkEntry_t *pPktCtrlBlk; 144 WhalParams_T *pWhalParams = (WhalParams_T *)(pTnetwDrv->hWhalParams); 145 BOOL bIsMultiCastAndIBSS; /* used for the Ack policy */ 146 147 #ifdef TI_DBG 148 /* If queue number is invalid return ERROR. */ 149 if (aQueueId >= MAX_NUM_OF_TX_QUEUES) 150 { 151 WLAN_REPORT_ERROR(pTnetwDrv->hReport, TNETW_DRV_MODULE_LOG, 152 ("TnetwDrv_txXfer_sendPacket(): Invalid aQueueId = %d !!!\n", aQueueId)); 153 return SEND_PACKET_ERROR; 154 } 155 #endif 156 157 /*****************************************************************************************/ 158 /* 1) Allocates a Control-Block for the packet Tx parameters and descriptor. */ 159 /*****************************************************************************************/ 160 161 pPktCtrlBlk = TnetwDrv_txCtrlBlk_alloc(pTnetwDrv); 162 163 #ifdef TI_DBG 164 pTnetwDrv->dbgCountSentPackets[aQueueId]++; /* Count packets sent from upper driver. */ 165 #endif 166 /* If null entry (not expected to happen) return ERROR. */ 167 if (!pPktCtrlBlk) 168 { 169 #ifdef TI_DBG 170 WLAN_REPORT_ERROR(pTnetwDrv->hReport, TNETW_DRV_MODULE_LOG, 171 ("TnetwDrv_txXfer_sendPacket(): Tx Ctrl-Blk allocation failed!!!\n")); 172 #endif 173 return SEND_PACKET_ERROR; 174 } 175 176 /*****************************************************************************************/ 177 /* 2) Set the packet control block parameters (including descriptor structure). */ 178 /*****************************************************************************************/ 179 180 /* Note that the following params are currently not used: aMore, aPowerLevel, aReserved. */ 181 182 /* Note that the following descriptor params are for future use, so they are left zeroed: 183 pktType and xferPadding fields in txAttr, and tid. */ 184 185 /* Note that the other params are set later in the Tx process (e.g. fragThresh and numMemBlks). */ 186 187 /* aFrame points to the start of the data, but we need to reserve place for descriptor + TNETWIF_WRITE_OFFSET_BYTES */ 188 pPktCtrlBlk->txPktParams.pFrame = (void*)((UINT8 *)aFrame - TX_TOTAL_OFFSET_BEFORE_DATA); 189 190 pPktCtrlBlk->txDescriptor.length = aLength; 191 pPktCtrlBlk->txDescriptor.xmitQueue = aQueueId; 192 pPktCtrlBlk->txDescriptor.rate = aMaxTransmitRate; 193 pPktCtrlBlk->txPktParams.packetId = aPacketId; 194 pPktCtrlBlk->txDescriptor.expiryTime = aExpiryTime << SHIFT_BETWEEN_TU_AND_USEC; /* Convert TUs to microseconds. */ 195 196 pDot11Hdr = (dot11_header_t*)(aFrame); /* aFrame points to the start of the data */ 197 pPktCtrlBlk->txPktParams.headerFrameCtrl = pDot11Hdr->fc; /* Save frame-control field from MAC header. */ 198 199 /* Set descriptor control bit-mask fields and write the whole word to the descriptor. */ 200 *(uint16 *)pTxAttr = 0; /* Clear temporary union. */ 201 txAttr.ratePolicy = aTxRateClassId; 202 203 /* Configure the Ack policy */ 204 bIsMultiCastAndIBSS = ((BSS_INDEPENDENT == (bssType_e)(whal_ParamsGetReqBssType(pWhalParams))) 205 && (MAC_MULTICAST(GET_DA_FROM_DOT11_HEADER_T(pDot11Hdr)))); 206 txAttr.ackPolicy = TnetwDrv_txGetAckPolicy(pTnetwDrv, aQueueId , bIsMultiCastAndIBSS); 207 208 if (IS_QOS_FRAME(pDot11Hdr->fc)) /* Check if frame is QoS-Data or QoS-Null. */ 209 txAttr.qosFrame = 1; 210 211 /* if this is a management frame, request immediate TX complete indication */ 212 if ( (pDot11Hdr->fc & DOT11_FC_TYPE_MASK) == DOT11_FC_TYPE_MGMT ) 213 { 214 txAttr.txCmpltRequired = 1; 215 } 216 217 pPktCtrlBlk->txDescriptor.txAttr = *(uint16 *)pTxAttr; 218 219 pPktCtrlBlk->txPktParams.flags = 0; 220 221 222 /************************************************************************************************/ 223 /* 3) Call HwQueue for Hw resources allocation. If not available free CtrlBlk and return BUSY. */ 224 /************************************************************************************************/ 225 226 /* Note that the HwQueue calls first the fragThreshold and numMemBlks calculation. */ 227 228 if ( TnetwDrv_txHwQueue_alloc(pTnetwDrv, pPktCtrlBlk) != OK ) 229 { 230 TnetwDrv_txCtrlBlk_free(pTnetwDrv, pPktCtrlBlk); 231 return SEND_PACKET_BUSY; 232 } 233 234 #ifdef TI_DBG 235 /* Just for debug, write per queue sequence number to packet ctrl-blk (after allocation success!). */ 236 pTnetwDrv->dbgPktSeqNum[aQueueId]++; 237 pPktCtrlBlk->txPktParams.dbgPktSeqNum = pTnetwDrv->dbgPktSeqNum[aQueueId]; 238 239 pTnetwDrv->dbgCountQueueAvailable[aQueueId]++; /* Count packets sent and queue not busy. */ 240 #endif 241 242 243 /*****************************************************************************************/ 244 /* 4) Copy the descriptor to the frame . */ 245 /*****************************************************************************************/ 246 247 os_memoryCopy(pTnetwDrv->hOs, (void *)((UINT8*)aFrame - sizeof(DbTescriptor)), &(pPktCtrlBlk->txDescriptor), sizeof(DbTescriptor)); 248 249 250 /*****************************************************************************************/ 251 /* 5) Call the Tx-Xfer to start packet transfer to the FW and return its result. */ 252 /*****************************************************************************************/ 253 254 status = txXfer_sendPacket(pTnetwDrv->hTxXfer, pPktCtrlBlk); 255 256 /* If the packet was transfered in this context and Tx-complete already occured, free the ctrl-blk. */ 257 if (status == SEND_PACKET_XFER_DONE) 258 { 259 if (pPktCtrlBlk->txPktParams.flags & TX_CTRL_BLK_FLAGS_TX_COMPLETE_ISSUED) 260 TnetwDrv_txCtrlBlk_free(pTnetwDrv, pPktCtrlBlk); 261 else 262 pPktCtrlBlk->txPktParams.flags |= TX_CTRL_BLK_FLAGS_XFER_DONE_ISSUED; 263 } 264 265 #ifdef TI_DBG 266 if (status == SEND_PACKET_XFER_DONE) 267 pTnetwDrv->dbgCountXferDone[aQueueId]++; 268 else if (status == SEND_PACKET_SUCCESS) 269 pTnetwDrv->dbgCountXferSuccess[aQueueId]++; 270 else if (status == SEND_PACKET_PENDING) 271 pTnetwDrv->dbgCountXferPending[aQueueId]++; 272 else 273 pTnetwDrv->dbgCountXferError[aQueueId]++; 274 #endif 275 276 277 return status; 278 } 279 280 281 282 283 /**************************************************************************** 284 * Tx API functions needed for GWSI interface * 285 ****************************************************************************/ 286 287 UINT8 TnetwDrv_txGetAckPolicy(TI_HANDLE hTnetwDrv, int TxQid , BOOL bIsMultiCastAndIBSS) 288 { 289 TnetwDrv_t *pTnetwDrv = (TnetwDrv_t *)hTnetwDrv; 290 WhalParams_T *pWhalParams = (WhalParams_T *)(pTnetwDrv->hWhalParams); 291 292 /* If we are in IBSS and we are transmitting a Multicast/Broadcast frame -> we don't expect an Ack packet */ 293 if (bIsMultiCastAndIBSS) 294 { 295 return ACK_POLICY_NO_ACK; 296 } 297 298 return (pWhalParams->QueuesParams.queues[TxQid].ackPolicy); 299 } 300 301 /************************************************************************* 302 * TnetwDrv_TxXferDone * 303 ************************************************************************** 304 * DESCRIPTION: 305 ============ 306 Called upon Xfer-Done of transmitted packet. 307 Calls the upper driver's Xfer-Done handler. 308 309 * 310 * INPUT: hDummyHandle - Just to support the CB API. 311 * pPktCtrlBlk - The packet's control block pointer. 312 * 313 * OUTPUT: 314 * 315 * RETURN: 316 317 *************************************************************************/ 318 void TnetwDrv_TxXferDone(TI_HANDLE hTnetwDrv, txCtrlBlkEntry_t *pPktCtrlBlk) 319 { 320 /* Make a working copy of TNETDriver Handle */ 321 TnetwDrv_t *pTnetwDrv = (TnetwDrv_t *)hTnetwDrv; 322 323 324 #ifdef TI_DBG 325 pTnetwDrv->dbgCountXferDoneCB[pPktCtrlBlk->txDescriptor.xmitQueue]++; 326 #endif 327 /* If the pointed entry is already free, print error and exit (not expected to happen). */ 328 if (pPktCtrlBlk->pNextFreeEntry != NULL) 329 { 330 #ifdef TI_DBG 331 WLAN_REPORT_ERROR(pTnetwDrv->hReport, TNETW_DRV_MODULE_LOG, 332 ("TnetwDrv_TxXferDone(): Pkt already free!!, DescID=%d, dbgPktSeqNum=%d, flags=%d, packetId=0x%x, Queue=%d\n", 333 pPktCtrlBlk->txDescriptor.descID, pPktCtrlBlk->txPktParams.dbgPktSeqNum, pPktCtrlBlk->txPktParams.flags, 334 pPktCtrlBlk->txPktParams.packetId, pPktCtrlBlk->txDescriptor.xmitQueue)); 335 #endif 336 return; 337 } 338 339 /* If Tx-complete already occurred, free the ctrl-blk. */ 340 /* Note that this may happen when the Xfer-SM delays the Xfer-Done (for pipeline sequence). */ 341 if (pPktCtrlBlk->txPktParams.flags & TX_CTRL_BLK_FLAGS_TX_COMPLETE_ISSUED) 342 TnetwDrv_txCtrlBlk_free(pTnetwDrv, pPktCtrlBlk); 343 else 344 pPktCtrlBlk->txPktParams.flags |= TX_CTRL_BLK_FLAGS_XFER_DONE_ISSUED; 345 346 /* Call the upper driver's Xfer-Done handler with the packet-ID. */ 347 /* Note that depending on the type of compilation, the upper layers vary: */ 348 /* It may be either CoreAdaptTx or GWSIAdaptTx */ 349 /* Both functions are called the same */ 350 SendPacketTransfer (pTnetwDrv->hUser, pPktCtrlBlk->txPktParams.packetId); 351 } 352 353 354 355 /************************************************************************* 356 * TnetwDrv_TxComplete * 357 ************************************************************************** 358 * DESCRIPTION: 359 ============ 360 Called upon Tx-complete of transmitted packet. 361 Handles it as follows: 362 1) Update the HwQueue to free queue resources. 363 2) Call the upper driver's tx-complete handler. 364 3) Free the packet's Control-Block if Xfer-Done already occured. 365 366 * 367 * INPUT: hDummyHandle - Just to support the CB API. 368 * pTxResultInfo - The packet's Tx result information. 369 * 370 * OUTPUT: 371 * 372 * RETURN: 373 374 *************************************************************************/ 375 void TnetwDrv_TxComplete(TI_HANDLE hTnetwDrv, TxResultDescriptor_t *pTxResultInfo) 376 { 377 txCtrlBlkEntry_t *pPktCtrlBlk; 378 /* Make a working copy of TNETDriver Handle */ 379 TnetwDrv_t *pTnetwDrv = (TnetwDrv_t *)hTnetwDrv; 380 381 /* Get the packet's control block pointer by the descId index. */ 382 pPktCtrlBlk = TnetwDrv_txCtrlBlk_GetPointer(pTnetwDrv, pTxResultInfo->descID); 383 384 #ifdef TI_DBG 385 WLAN_REPORT_INFORMATION(pTnetwDrv->hReport, TNETW_DRV_MODULE_LOG, 386 ("TnetwDrv_TxComplete(): DescID=%d, dbgPktSeqNum=%d, flags=%d, packetId=0x%x, Queue=%d\n", 387 pTxResultInfo->descID, pPktCtrlBlk->txPktParams.dbgPktSeqNum, pPktCtrlBlk->txPktParams.flags, 388 pPktCtrlBlk->txPktParams.packetId, pPktCtrlBlk->txDescriptor.xmitQueue)); 389 390 pTnetwDrv->dbgCountTxCompleteCB[pPktCtrlBlk->txDescriptor.xmitQueue]++; 391 #endif 392 /* If the pointed entry is already free, print error and exit (not expected to happen). */ 393 if (pPktCtrlBlk->pNextFreeEntry != NULL) 394 { 395 #ifdef TI_DBG 396 WLAN_REPORT_ERROR(pTnetwDrv->hReport, TNETW_DRV_MODULE_LOG, 397 ("TnetwDrv_TxComplete(): Pkt already free!!, DescID=%d, dbgPktSeqNum=%d, flags=%d, packetId=0x%x, Queue=%d\n", 398 pTxResultInfo->descID, pPktCtrlBlk->txPktParams.dbgPktSeqNum, pPktCtrlBlk->txPktParams.flags, 399 pPktCtrlBlk->txPktParams.packetId, pPktCtrlBlk->txDescriptor.xmitQueue)); 400 #endif 401 return; 402 } 403 404 /* Update the HwQueue to free queue resources. */ 405 TnetwDrv_txHwQueue_free(pTnetwDrv, pPktCtrlBlk); 406 407 /* @@@ Note: Add Security Sequence Number handling. */ 408 /* Update the TKIP/AES sequence-number according to the Tx data packet security-seq-num. */ 409 /* Note: The FW always provides the last used seq-num so no need to check if the current 410 packet is data and WEP is on. */ 411 whalCtrl_updateSecuritySeqNum(pTnetwDrv->hHalCtrl, pTxResultInfo->lsbSecuritySequenceNumber); 412 413 /* Call the upper driver's tx-complete handler. */ 414 /* Note that depending on the type of compilation, the upper layeres varry: */ 415 /* It may be either CoreAdaptTx or GWSIAdaptTx */ 416 /* Both functions are called the same */ 417 SendPacketComplete (pTnetwDrv->hUser, 418 ConvertTxResultStatus((TxDescStatus_enum)pTxResultInfo->status), 419 pPktCtrlBlk->txPktParams.packetId, 420 pTxResultInfo->actualRate, 421 pTxResultInfo->ackFailures, 422 (UINT32)pTxResultInfo->mediumUsage, 423 pTxResultInfo->fwHandlingTime, 424 pTxResultInfo->mediumDelay); 425 426 /* If Xfer-Done already occured, free the ctrl-blk (otherwise Xfer-Done will do it). */ 427 /* Note that the Xfer-SM may delay the Xfer-Done (for pipeline sequence). */ 428 if (pPktCtrlBlk->txPktParams.flags & TX_CTRL_BLK_FLAGS_XFER_DONE_ISSUED) 429 TnetwDrv_txCtrlBlk_free(pTnetwDrv, pPktCtrlBlk); 430 else 431 pPktCtrlBlk->txPktParams.flags |= TX_CTRL_BLK_FLAGS_TX_COMPLETE_ISSUED; 432 } 433 434 435 /************************************************************************* 436 * TnetwDrv_RecoveryCtrlBlk * 437 ************************************************************************** 438 * DESCRIPTION: 439 ============ 440 Called upon recovery. 441 Handles it as follows: 442 1) Update the HwQueue to free queue resources. 443 3) Free the packet's Control-Block if Xfer-Done already occured. 444 445 * 446 * INPUT: hDummyHandle - Just to support the CB API. 447 * 448 * OUTPUT: 449 * 450 * RETURN: 451 452 *************************************************************************/ 453 void TnetwDrv_RecoveryCtrlBlk(TI_HANDLE hTnetwDrv) 454 { 455 txCtrlBlkEntry_t *pPktCtrlBlk; 456 /* Make a working copy of TNETDriver Handle */ 457 TnetwDrv_t *pTnetwDrv = (TnetwDrv_t *)hTnetwDrv; 458 UINT32 entry; 459 const UINT32 MAX_CTRL_BLK_ENTRY = 64; 460 461 for (entry = 0; entry < MAX_CTRL_BLK_ENTRY-1; entry++) 462 { 463 /* Get the packet's control block pointer by the descId index. */ 464 pPktCtrlBlk = TnetwDrv_txCtrlBlk_GetPointer(pTnetwDrv, entry); 465 if (pPktCtrlBlk->pNextFreeEntry == NULL) 466 { 467 TnetwDrv_txHwQueue_free(pTnetwDrv, pPktCtrlBlk); 468 TnetwDrv_txCtrlBlk_free(pTnetwDrv, pPktCtrlBlk); 469 } 470 } 471 } 472 473 474 /************************************************************************* 475 * TnetwDrv_TxXferDebug * 476 ************************************************************************** 477 * DESCRIPTION: 478 ============ 479 Called upon issuing interrupt to firmware. 480 Calls the upper driver's Xfer-Debug handler. 481 482 * 483 * INPUT: hDummyHandle - Just to support the CB API. 484 * pPktCtrlBlk - The packet's control block pointer. 485 uDebugInfo - Additional debug info 486 * 487 * OUTPUT: 488 * 489 * RETURN: 490 491 *************************************************************************/ 492 #ifdef TI_DBG 493 void TnetwDrv_TxXferDebug (TI_HANDLE hTnetwDrv, txCtrlBlkEntry_t *pPktCtrlBlk, UINT32 uDebugInfo) 494 { 495 TnetwDrv_t *pTnetwDrv = (TnetwDrv_t *)hTnetwDrv; 496 /* Call the upper driver's Xfer-Done handler with the packet-ID. */ 497 /* Note that depending on the type of compilation, the upper layeres varry: */ 498 /* It may be either CoreAdaptTx or GWSIAdaptTx */ 499 /* Both functions are called the same */ 500 SendPacketDebug (pTnetwDrv->hUser, pPktCtrlBlk->txPktParams.packetId, uDebugInfo); 501 } 502 #endif 503 504 505 /**************************************************************************** 506 * ConvertTxResultStatus 507 **************************************************************************** 508 * DESCRIPTION: Convert the status bit field in the TxDone descriptor, indexed 509 * by the given index, to a driver status bit field 510 * 511 * INPUTS: txResultStatus - Status value received from the FW 512 * 513 * OUTPUT: None 514 * 515 * RETURNS: The converted value 516 ****************************************************************************/ 517 systemStatus_e ConvertTxResultStatus(TxDescStatus_enum txResultStatus) 518 { 519 /* Convert Tx-Result from FW to GWSI values. */ 520 /* Note: only 1 bit in the entire status field should be set */ 521 switch (txResultStatus) 522 { 523 case TX_SUCCESS: 524 return SEND_COMPLETE_SUCCESS; 525 526 case TX_RETRY_EXCEEDED: 527 return SEND_COMPLETE_RETRY_EXCEEDED; 528 529 case TX_TIMEOUT: 530 return SEND_COMPLETE_LIFETIME_EXCEEDED; 531 532 default: 533 return SEND_COMPLETE_NO_LINK; 534 } 535 } 536 537 538 /**************************************************************************** 539 * TnetwDrv_printInfo() 540 **************************************************************************** 541 * DESCRIPTION: Print the txXfer object main fields. 542 ****************************************************************************/ 543 void TnetwDrv_printInfo(TI_HANDLE hTnetwDrv) 544 { 545 #ifdef TI_DBG 546 TnetwDrv_t *pTnetwDrv = (TnetwDrv_t *)hTnetwDrv; 547 int qIndex; 548 549 WLAN_OS_REPORT(("TNETW Driver Tx Counters per Queue:\n")); 550 WLAN_OS_REPORT(("===========================\n")); 551 552 WLAN_OS_REPORT(("-------------- packets sent from upper driver ---------------\n")); 553 for(qIndex = 0; qIndex < MAX_NUM_OF_TX_QUEUES; qIndex++) 554 WLAN_OS_REPORT(("Queue %d = %d\n",qIndex, pTnetwDrv->dbgCountSentPackets[qIndex])); 555 556 WLAN_OS_REPORT(("-------------- packets sent and queue not busy ---------------\n")); 557 for(qIndex = 0; qIndex < MAX_NUM_OF_TX_QUEUES; qIndex++) 558 WLAN_OS_REPORT(("Queue %d = %d\n",qIndex, pTnetwDrv->dbgCountQueueAvailable[qIndex])); 559 560 WLAN_OS_REPORT(("-------------- XferDone value returned from Xfer ---------------\n")); 561 for(qIndex = 0; qIndex < MAX_NUM_OF_TX_QUEUES; qIndex++) 562 WLAN_OS_REPORT(("Queue %d = %d\n",qIndex, pTnetwDrv->dbgCountXferDone[qIndex])); 563 564 WLAN_OS_REPORT(("-------------- Success value returned from Xfer ---------------\n")); 565 for(qIndex = 0; qIndex < MAX_NUM_OF_TX_QUEUES; qIndex++) 566 WLAN_OS_REPORT(("Queue %d = %d\n",qIndex, pTnetwDrv->dbgCountXferSuccess[qIndex])); 567 568 WLAN_OS_REPORT(("-------------- Pending value returned from Xfer ---------------\n")); 569 for(qIndex = 0; qIndex < MAX_NUM_OF_TX_QUEUES; qIndex++) 570 WLAN_OS_REPORT(("Queue %d = %d\n",qIndex, pTnetwDrv->dbgCountXferPending[qIndex])); 571 572 WLAN_OS_REPORT(("-------------- Error value returned from Xfer ---------------\n")); 573 for(qIndex = 0; qIndex < MAX_NUM_OF_TX_QUEUES; qIndex++) 574 WLAN_OS_REPORT(("Queue %d = %d\n",qIndex, pTnetwDrv->dbgCountXferError[qIndex])); 575 576 WLAN_OS_REPORT(("-------------- XferDone callback calls ---------------\n")); 577 for(qIndex = 0; qIndex < MAX_NUM_OF_TX_QUEUES; qIndex++) 578 WLAN_OS_REPORT(("Queue %d = %d\n",qIndex, pTnetwDrv->dbgCountXferDoneCB[qIndex])); 579 580 WLAN_OS_REPORT(("-------------- TxComplete callback calls ---------------\n")); 581 for(qIndex = 0; qIndex < MAX_NUM_OF_TX_QUEUES; qIndex++) 582 WLAN_OS_REPORT(("Queue %d = %d\n",qIndex, pTnetwDrv->dbgCountTxCompleteCB[qIndex])); 583 #endif /* TI_DBG */ 584 } 585