Files
Linux_Drivers/osdrv/extdrv/wireless/mediatek/mt7603/common/mt_ps.c
forum_service 213c880673 add driver of tp、wiegand-gpio and wireless
Change-Id: Ie3c11d9d85cf1a05042f5690ac711856fe8b1ad7
2023-12-22 09:56:05 +08:00

609 lines
17 KiB
C

/****************************************************************************
* Ralink Tech Inc.
* Taiwan, R.O.C.
*
* (c) Copyright 2010, Ralink Technology, Inc.
*
* All rights reserved. Ralink's source code is an unpublished work and the
* use of a copyright notice does not imply otherwise. This source code
* contains confidential trade secret material of Ralink Tech. Any attemp
* or participation in deciphering, decoding, reverse engineering or in any
* way altering the source code is stricitly prohibited, unless the prior
* written consent of Ralink Technology, Inc. is obtained.
***************************************************************************/
/****************************************************************************
Abstract:
All related POWER SAVE function body.
***************************************************************************/
#include "rt_config.h"
#ifdef MT_PS
static VOID MtReadPseRdTabAccessReg(
RTMP_ADAPTER *pAd,
UCHAR wcid,
UINT32 *p_rPseRdTabAccessReg)
{
*p_rPseRdTabAccessReg = PSE_RTA_RD_KICK_BUSY | PSE_RTA_TAG(wcid);
RTMP_IO_WRITE32(pAd, PSE_RTA, *p_rPseRdTabAccessReg);
do
{
RTMP_IO_READ32(pAd,PSE_RTA, p_rPseRdTabAccessReg);
}
while ( GET_PSE_RTA_RD_KICK_BUSY(*p_rPseRdTabAccessReg) == 1 );
DBGPRINT(RT_DEBUG_INFO | DBG_FUNC_PS, ("%s: *p_rPseRdTabAccessReg = 0x%x\n",
__FUNCTION__, *p_rPseRdTabAccessReg));
}
VOID MtSetIgnorePsm(
RTMP_ADAPTER *pAd,
MAC_TABLE_ENTRY *pEntry,
UCHAR value)
{
#ifdef RTMP_PCI_SUPPORT
ULONG IrqFlags = 0;
#endif /* RTMP_PCI_SUPPORT */
struct wtbl_entry tb_entry;
union WTBL_1_DW3 *dw3 = (union WTBL_1_DW3 *)&tb_entry.wtbl_1.wtbl_1_d3.word;
NdisZeroMemory(&tb_entry, sizeof(tb_entry));
if (mt_wtbl_get_entry234(pAd, pEntry->wcid, &tb_entry) == FALSE)
{
DBGPRINT(RT_DEBUG_INFO | DBG_FUNC_PS, ("%s():Cannot found WTBL2/3/4\n",__FUNCTION__));
return;
}
#ifdef RTMP_PCI_SUPPORT
RTMP_IRQ_LOCK(&pAd->irq_lock, IrqFlags);
#endif /* RTMP_PCI_SUPPORT */
pEntry->i_psm = value;
RTMP_IO_READ32(pAd, tb_entry.wtbl_addr[0]+12, &dw3->word);
dw3->field.du_i_psm = value; /* I_PSM changed by HW automatically is enabled. */
dw3->field.i_psm = value; /* follow PSM value. */
RTMP_IO_WRITE32(pAd, tb_entry.wtbl_addr[0] + 12, dw3->word);
#ifdef RTMP_PCI_SUPPORT
RTMP_IRQ_UNLOCK(&pAd->irq_lock, IrqFlags);
#endif /* RTMP_PCI_SUPPORT */
}
VOID CheckSkipTX(
RTMP_ADAPTER *pAd,
MAC_TABLE_ENTRY *pEntry)
{
struct wtbl_entry tb_entry;
union WTBL_1_DW3 *dw3 = (union WTBL_1_DW3 *)&tb_entry.wtbl_1.wtbl_1_d3.word;
STA_TR_ENTRY *tr_entry;
CHAR isChange = FALSE;
NdisZeroMemory(&tb_entry, sizeof(tb_entry));
if (mt_wtbl_get_entry234(pAd, pEntry->wcid, &tb_entry) == FALSE)
{
DBGPRINT(RT_DEBUG_INFO | DBG_FUNC_PS, ("%s():Cannot found WTBL2/3/4\n",__FUNCTION__));
return;
}
tr_entry = &pAd->MacTab.tr_entry[pEntry->wcid];
RTMP_IO_READ32(pAd, tb_entry.wtbl_addr[0]+12, &dw3->word);
if ((tr_entry->ps_state != APPS_RETRIEVE_START_PS) && (dw3->field.skip_tx == 1))
{
dw3->field.skip_tx = 0;
isChange = TRUE;
}
if ((tr_entry->ps_state < APPS_RETRIEVE_DONE) && (dw3->field.du_i_psm == 1))
{
dw3->field.du_i_psm = 0;
dw3->field.i_psm = 0;
isChange = TRUE;
}
if (isChange == TRUE) {
pAd->SkipTxRCount++;
RTMP_IO_WRITE32(pAd, tb_entry.wtbl_addr[0]+12, dw3->word);
}
return;
}
#endif /* MT_PS */
#ifdef MT7603
INT MtPSDummyCR(RTMP_ADAPTER *pAd)
{
INT value;
RTMP_IO_READ32(pAd, 0x817c, &value);
value &= 0xff;
return value;
}
#ifdef RTMP_MAC_PCI
VOID MtTriggerMCUINT(RTMP_ADAPTER *pAd)
{
INT value;
INT restore_remap_addr;
RTMP_IO_READ32(pAd, 0x2504, &restore_remap_addr);
RTMP_IO_WRITE32(pAd, 0x2504, 0x81000000);
RTMP_IO_READ32(pAd, 0xc00c0, &value);
value |= 0x100;
RTMP_IO_WRITE32(pAd, 0xc00c0, value); //Trigger INT to MCU, 0x810400c0
RTMP_IO_WRITE32(pAd, 0x2504, restore_remap_addr);
}
#endif /* RTMP_MAC_PCI */
BOOLEAN MtStartPSRetrieve(RTMP_ADAPTER *pAd, USHORT wcid)
{
if (MtPSDummyCR(pAd) != 0) {
return FALSE;
}
RTMP_IO_WRITE32(pAd, 0x817c, wcid);
#ifdef RTMP_MAC_PCI
// MtTriggerMCUINT(pAd);
#endif /* RTMP_MAC_PCI */
return TRUE;
}
#endif
/*
========================================================================
Description:
This routine frees all packets in PSQ that's destined to a specific DA.
BCAST/MCAST in DTIMCount=0 case is also handled here, just like a PS-POLL
is received from a WSTA which has MAC address FF:FF:FF:FF:FF:FF
========================================================================
*/
VOID MtHandleRxPsPoll(RTMP_ADAPTER *pAd, UCHAR *pAddr, USHORT wcid, BOOLEAN isActive)
{
#ifdef CONFIG_AP_SUPPORT
#if defined(MT_PS) || defined(UAPSD_SUPPORT)
MAC_TABLE_ENTRY *pMacEntry;
#endif
STA_TR_ENTRY *tr_entry;
BOOLEAN IsDequeu= FALSE;
INT DequeuAC = QID_AC_BE;
INT DequeuCOUNT;
#ifdef MT_PS
INT i, Total_Packet_Number = 0;
#endif /* MT_PS */
//struct tx_swq_fifo *fifo_swq;
ASSERT(wcid < MAX_LEN_OF_MAC_TABLE);
#if defined(MT_PS) || defined(UAPSD_SUPPORT)
pMacEntry = &pAd->MacTab.Content[wcid];
#endif
tr_entry = &pAd->MacTab.tr_entry[wcid];
if (isActive == FALSE) /* ps poll */
{
#ifdef MT_PS
if (tr_entry->ps_state == APPS_RETRIEVE_DONE) /*state is finish(sleep)*/
{
if (pMacEntry->i_psm == I_PSM_DISABLE)
{
MT_SET_IGNORE_PSM(pAd, pMacEntry, I_PSM_ENABLE);
}
}
if(tr_entry->ps_state == APPS_RETRIEVE_DONE || tr_entry->ps_state == APPS_RETRIEVE_IDLE)
{
for (i = 0; i < WMM_QUE_NUM; i++)
Total_Packet_Number = Total_Packet_Number + tr_entry->tx_queue[i].Number;
if (Total_Packet_Number > 0)
{
{
DBGPRINT(RT_DEBUG_TRACE | DBG_FUNC_PS, ("RtmpHandleRxPsPoll fetch tx queue tr_entry->ps_queue.Number= %x tr_entry->tx_queue[0].Number=%x Total_Packet_Number=%x\n",
tr_entry->ps_queue.Number, tr_entry->tx_queue[QID_AC_BE].Number, Total_Packet_Number));
for (i = (WMM_QUE_NUM - 1); i >=0; i--)
{
if (tr_entry->tx_queue[i].Head)
{
if (Total_Packet_Number > 1)
{
RTMP_SET_PACKET_MOREDATA(RTPKT_TO_OSPKT(tr_entry->tx_queue[i].Head), TRUE);
}
RTMP_SET_PACKET_TXTYPE(RTPKT_TO_OSPKT(tr_entry->tx_queue[i].Head), TX_LEGACY_FRAME);
DequeuAC = i;
IsDequeu = TRUE;
DequeuCOUNT = 1;
tr_entry->PsQIdleCount = 0;
break;
}
}
}
}
else /* Recieve ps_poll but no packet==>send NULL Packet */
{
BOOLEAN bQosNull = FALSE;
DBGPRINT(RT_DEBUG_INFO | DBG_FUNC_PS, ("RtmpHandleRxPsPoll no packet tr_entry->ps_queue.Number= %x tr_entry->tx_queue[0].Number=%x Total_Packet_Number=%x\n"
,tr_entry->ps_queue.Number, tr_entry->tx_queue[QID_AC_BE].Number, Total_Packet_Number));
if (CLIENT_STATUS_TEST_FLAG(pMacEntry, fCLIENT_STATUS_WMM_CAPABLE))
bQosNull = TRUE;
RtmpEnqueueNullFrame(pAd, pMacEntry->Addr, tr_entry->CurrTxRate,
pMacEntry->Aid, pMacEntry->func_tb_idx,
bQosNull, TRUE, 0);
}
if (Total_Packet_Number >1)
{
WLAN_MR_TIM_BIT_SET(pAd, tr_entry->func_tb_idx, tr_entry->wcid);
}
else
{
WLAN_MR_TIM_BIT_CLEAR(pAd, tr_entry->func_tb_idx, tr_entry->wcid);
}
} else
tr_entry->PsDeQWaitCnt = 0;
#else
/*
Need to check !! @20140212
New architecture has per AC sw-Q for per entry.
We should check packets by ACs priority --> 1. VO, 2. VI, 3. BE, 4. BK
*/
DequeuAC = QID_AC_BE;
IsDequeu = TRUE;
DequeuCOUNT = 1;
tr_entry->PsQIdleCount = 0;
#endif /* Ps_poll and ifndef MT_PS */
}
else /* Receive Power bit 0 frame */
{
WLAN_MR_TIM_BIT_CLEAR(pAd, tr_entry->func_tb_idx, tr_entry->wcid);
#ifdef MT_PS
if (pMacEntry->i_psm == I_PSM_ENABLE)
{
MT_SET_IGNORE_PSM(pAd, pMacEntry, I_PSM_DISABLE);
}
#endif /*Power bit is 1 and ifndef MT_PS */
DBGPRINT(RT_DEBUG_INFO | DBG_FUNC_PS, ("RtmpHandleRxPsPoll null0/1 wcid = %x mt_ps_queue.Number = %d\n",
tr_entry->wcid,
tr_entry->ps_queue.Number));
DBGPRINT(RT_DEBUG_INFO | DBG_FUNC_PS, ("%s(%d) tx_queue.Number = BE:%d, BK:%d, VI:%d, VO:%d, ps_state:%x, tx_queue.TokenCount = BE:%d, BK:%d, VI:%d, VO:%d\n",
__FUNCTION__, __LINE__,
tr_entry->tx_queue[QID_AC_BE].Number,
tr_entry->tx_queue[QID_AC_BK].Number,
tr_entry->tx_queue[QID_AC_VI].Number,
tr_entry->tx_queue[QID_AC_VO].Number,
tr_entry->ps_state,
tr_entry->TokenCount[QID_AC_BE],
tr_entry->TokenCount[QID_AC_BK],
tr_entry->TokenCount[QID_AC_VI],
tr_entry->TokenCount[QID_AC_VO]));
#ifdef UAPSD_SUPPORT
if (CLIENT_STATUS_TEST_FLAG(pMacEntry, fCLIENT_STATUS_APSD_CAPABLE))
{
/* deliver all queued UAPSD packets */
UAPSD_AllPacketDeliver(pAd, pMacEntry);
/* end the SP if exists */
UAPSD_MR_ENTRY_RESET(pAd, pMacEntry);
}
#endif /* UAPSD_SUPPORT */
if (tr_entry->enqCount > 0)
{
IsDequeu = TRUE;
DequeuAC = NUM_OF_TX_RING;
if (tr_entry->enqCount > MAX_TX_PROCESS)
{
DequeuCOUNT = MAX_TX_PROCESS;
rtmp_ps_enq(pAd,tr_entry);
}
else
{
DequeuCOUNT = tr_entry->enqCount;
}
}
}
if (IsDequeu == TRUE)
{
RTMPDeQueuePacket(pAd, FALSE, (UCHAR)DequeuAC, tr_entry->wcid, DequeuCOUNT);
DBGPRINT(RT_DEBUG_INFO | DBG_FUNC_PS, ("RtmpHandleRxPsPoll IsDequeu == TRUE tr_entry->wcid=%x DequeuCOUNT=%d, ps_state=%d\n",tr_entry->wcid, DequeuCOUNT, tr_entry->ps_state));
}
return;
#endif /* CONFIG_AP_SUPPORT */
}
/*
==========================================================================
Description:
Update the station current power save mode. Calling this routine also
prove the specified client is still alive. Otherwise AP will age-out
this client once IdleCount exceeds a threshold.
==========================================================================
*/
BOOLEAN MtPsIndicate(RTMP_ADAPTER *pAd, UCHAR *pAddr, UCHAR wcid, UCHAR Psm)
{
MAC_TABLE_ENTRY *pEntry;
UCHAR old_psmode;
STA_TR_ENTRY *tr_entry;
if (wcid >= MAX_LEN_OF_MAC_TABLE)
{
return PWR_ACTIVE;
}
pEntry = &pAd->MacTab.Content[wcid];
tr_entry = &pAd->MacTab.tr_entry[wcid];
/*
Change power save mode first because we will call
RTMPDeQueuePacket() in RtmpHandleRxPsPoll().
Or when Psm = PWR_ACTIVE, we will not do Aggregation in
RTMPDeQueuePacket().
*/
old_psmode = pEntry->PsMode;
pEntry->NoDataIdleCount = 0;
pEntry->PsMode = Psm;
pAd->MacTab.tr_entry[wcid].PsMode = Psm;
if ((old_psmode == PWR_SAVE) && (Psm == PWR_ACTIVE))
{
/*
STA wakes up.
*/
if(tr_entry->ps_state == APPS_RETRIEVE_DONE)
{
tr_entry->ps_state = APPS_RETRIEVE_IDLE;
DBGPRINT(RT_DEBUG_INFO | DBG_FUNC_PS, ("%s(%d): STA wakes up!\n", __FUNCTION__, __LINE__));
MtHandleRxPsPoll(pAd, pAddr, wcid, TRUE);
}
else
DBGPRINT(RT_DEBUG_INFO | DBG_FUNC_PS, ("%s(%d):wcid=%d, old_psmode=%d, now_psmode=%d, wrong ps_state=%d ???\n",
__FUNCTION__, __LINE__, wcid, old_psmode, Psm, tr_entry->ps_state));
}
else if ((old_psmode == PWR_ACTIVE) && (Psm == PWR_SAVE))
{
/*
STA goes to sleep.
*/
if (tr_entry->ps_state == APPS_RETRIEVE_IDLE)
{
#ifdef MT_PS
DBGPRINT(RT_DEBUG_INFO | DBG_FUNC_PS, ("%s(%d):wcid=%d, old_psmode=%d, now_psmode=%d, ps_state=%d start retrieving!!\n",
__FUNCTION__, __LINE__, wcid, old_psmode, Psm, tr_entry->ps_state));
#if defined(MT7603) && defined(RTMP_PCI_SUPPORT)
if (MtStartPSRetrieve(pAd, wcid) == TRUE) {
tr_entry->ps_state = APPS_RETRIEVE_START_PS;
} else {
struct tx_swq_fifo *ps_fifo_swq;
INT enq_idx;
ps_fifo_swq = &pAd->apps_cr_q;
enq_idx = ps_fifo_swq->enqIdx;
if (ps_fifo_swq->swq[enq_idx] == 0)
{
ps_fifo_swq->swq[enq_idx] = wcid;
INC_RING_INDEX(ps_fifo_swq->enqIdx, TX_SWQ_FIFO_LEN);
tr_entry->ps_state = APPS_RETRIEVE_CR_PADDING;
} else {
INT idx;
tr_entry->ps_state = APPS_RETRIEVE_DONE;
DBGPRINT(RT_DEBUG_ERROR, ("%s: ERROR!! ps_fifo_swq->deqIdx=%d, ps_fifo_swq->enqIdx=%d\n", __FUNCTION__,ps_fifo_swq->deqIdx,ps_fifo_swq->enqIdx));
for (idx =0; idx < TX_SWQ_FIFO_LEN;idx++) {
DBGPRINT(RT_DEBUG_ERROR, (",[%d] =%d\n", idx, ps_fifo_swq->swq[idx]));
if ((idx % 16) == 0)
DBGPRINT(RT_DEBUG_ERROR, ("\n"));
}
DBGPRINT(RT_DEBUG_ERROR, ("\n"));
}
}
#else /* !MT7603 && RTMP_PCI_SUPPORT */
RTEnqueueInternalCmd(pAd, CMDTHREAD_PS_RETRIEVE_START, pEntry, sizeof(MAC_TABLE_ENTRY));
#endif /* MT7603 && RTMP_PCI_SUPPORT */
#else /* MT_PS */
tr_entry->ps_state = APPS_RETRIEVE_DONE;
#endif /* !MT_PS */
}
else
DBGPRINT(RT_DEBUG_INFO | DBG_FUNC_PS, ("%s(%d):wcid=%d, old_psmode=%d, now_psmode=%d, wrong ps_state=%d ???\n",
__FUNCTION__, __LINE__, wcid, old_psmode, Psm, tr_entry->ps_state));
}
else
{
DBGPRINT(RT_DEBUG_INFO | DBG_FUNC_PS, ("%s(%d): ps state is not changed, do nothing here.\n",
__FUNCTION__, __LINE__));
}
return old_psmode;
}
#ifdef MT_PS
VOID MtPsRedirectDisableCheck(
RTMP_ADAPTER *pAd,
UCHAR wcid)
{
//UINT32 Reg = 0, wlan_idx = 0;
//BOOLEAN pfgForce = 0;
if (pAd->chipCap.hif_type != HIF_MT)
{
return;
}
#if 0 //snowpin test
MtReadPseRdTabAccessReg(pAd, wcid, &Reg);
pfgForce = ( BOOLEAN ) GET_PSE_RTA_RD_RULE_F(Reg);
if (pfgForce)
{
wlan_idx = (UINT32)wcid;
DBGPRINT(RT_DEBUG_ERROR | DBG_FUNC_PS, ("%s(%d): [wlan_idx=0x%x] PS Redirect mode(pfgForce = %d) is enabled. Send PC Clear command to FW.\n",
__FUNCTION__, __LINE__, wlan_idx, pfgForce));
RTEnqueueInternalCmd(pAd, CMDTHREAD_PS_CLEAR, (VOID *)&wlan_idx, sizeof(UINT32));
}
#endif
}
VOID MtPsSendToken(
RTMP_ADAPTER *pAd,
UINT32 WlanIdx)
{
MAC_TABLE_ENTRY *pEntry = NULL;
STA_TR_ENTRY *tr_entry;
NDIS_STATUS token_status;
struct wtbl_entry tb_entry;
union WTBL_1_DW3 *dw3;
UINT32 Reg = 0;
BOOLEAN pfgForce = 0;
unsigned char q_idx;
if (pAd->chipCap.hif_type != HIF_MT)
{
return;
}
DBGPRINT(RT_DEBUG_ERROR | DBG_FUNC_PS, ("%s(wcid=%d): Driver didn't receive PsRetrieveStartRsp from FW.\n",__FUNCTION__, WlanIdx));
pEntry = &pAd->MacTab.Content[WlanIdx];
tr_entry = &pAd->MacTab.tr_entry[WlanIdx];
NdisZeroMemory(&tb_entry, sizeof(tb_entry));
dw3 = (union WTBL_1_DW3 *)&tb_entry.wtbl_1.wtbl_1_d3.word;
if (mt_wtbl_get_entry234(pAd, WlanIdx, &tb_entry) == FALSE)
{
DBGPRINT(RT_DEBUG_ERROR | DBG_FUNC_PS, ("%s():Cannot found WTBL2/3/4, wcid=%d\n",__FUNCTION__, WlanIdx));
return;
}
RTMP_IO_READ32(pAd, tb_entry.wtbl_addr[0]+12, &dw3->word);
MtReadPseRdTabAccessReg(pAd, pEntry->wcid, &Reg);
pfgForce = ( BOOLEAN ) GET_PSE_RTA_RD_RULE_F(Reg);
if (pfgForce == 0)
{
DBGPRINT(RT_DEBUG_WARN | DBG_FUNC_PS, ("%s(ps_state = %d): PS Redirect mode didn't be enabled. Driver doesn't need to send token.\n",__FUNCTION__, tr_entry->ps_state));
DBGPRINT(RT_DEBUG_WARN | DBG_FUNC_PS, ("%s: Reset ps_state to IDLE.\n",__FUNCTION__));
tr_entry->ps_state = APPS_RETRIEVE_IDLE;
return;
}
DBGPRINT(RT_DEBUG_INFO | DBG_FUNC_PS, ("---->%s: Start to send TOKEN frames.\n", __FUNCTION__));
tr_entry->ps_state = APPS_RETRIEVE_GOING;
tr_entry->ps_qbitmap = 0;
for (q_idx = 0; q_idx < NUM_OF_TX_RING; q_idx++)
{
token_status = RtmpEnqueueTokenFrame(pAd, &(pEntry->Addr[0]), 0, WlanIdx, 0, q_idx);
if (!token_status)
tr_entry->ps_qbitmap |= (1 << q_idx);
else
DBGPRINT(RT_DEBUG_ERROR | DBG_FUNC_PS, ("%s(%d) Fail: Send TOKEN Frame, AC=%d\n", __FUNCTION__, __LINE__, q_idx));
}
if (tr_entry->ps_qbitmap == 0)
{
tr_entry->ps_state = APPS_RETRIEVE_WAIT_EVENT;
RTEnqueueInternalCmd(pAd, CMDTHREAD_PS_CLEAR, (VOID *)&WlanIdx, sizeof(UINT32));
DBGPRINT(RT_DEBUG_WARN | DBG_FUNC_PS, ("(ps_state = %d) token enqueue failed for all queues ==> send CMDTHREAD_PS_CLEAR cmd.\n", tr_entry->ps_state));
}
}
VOID MtEnqTxSwqFromPsQueue(RTMP_ADAPTER *pAd, UCHAR qidx, STA_TR_ENTRY *tr_entry)
{
ULONG IrqFlags = 0;
//struct tx_swq_fifo *fifo_swq;
QUEUE_ENTRY *pQEntry;
QUEUE_HEADER *pAcPsQue;
QUEUE_HEADER *pAcTxQue;
#ifdef UAPSD_SUPPORT
MAC_TABLE_ENTRY *pEntry = &pAd->MacTab.Content[tr_entry->wcid];
#endif /* UAPSD_SUPPORT */
//fifo_swq = &pAd->tx_swq[qidx];
#if 1
pAcPsQue = &tr_entry->ps_queue;
#else
pAcPsQue = &tr_entry->mt_ps_queue[qidx];
#endif
pAcTxQue = &tr_entry->tx_queue[qidx];
RTMP_IRQ_LOCK(&pAd->irq_lock, IrqFlags);
#ifdef UAPSD_SUPPORT
if (UAPSD_MR_IS_UAPSD_AC(pEntry, qidx))
{
while(pAcPsQue->Head)
{
pQEntry = RemoveTailQueue(pAcPsQue);
UAPSD_PacketEnqueue(pAd, pEntry, PACKET_TO_QUEUE_ENTRY(pQEntry), qidx, TRUE);
}
}
else
#endif /* UAPSD_SUPPORT */
{
/*check and insert PS Token queue*/
if(pAcPsQue->Number > 0 && tr_entry->wcid > 0 && tr_entry->wcid < MAX_LEN_OF_TR_TABLE)
{
rtmp_ps_enq(pAd,tr_entry);
DBGPRINT(RT_DEBUG_WARN,
("pAcPsQue->Number=%d,PS:%d\n", pAcPsQue->Number, tr_entry->PsTokenFlag));
}
while(pAcPsQue->Head)
{
pQEntry = RemoveTailQueue(pAcPsQue);
if(tr_entry->enqCount > SQ_ENQ_NORMAL_MAX) {
RELEASE_NDIS_PACKET(pAd, QUEUE_ENTRY_TO_PACKET(pQEntry), NDIS_STATUS_FAILURE);
continue;
}
InsertHeadQueue(pAcTxQue, pQEntry);
TR_ENQ_COUNT_INC(tr_entry);
}
}
RTMP_IRQ_UNLOCK(&pAd->irq_lock, IrqFlags);
return;
}
VOID MtPsClearErrorHandle(RTMP_ADAPTER *pAd, UINT wcid)
{
MAC_TABLE_ENTRY *pEntry = NULL;
STA_TR_ENTRY *tr_entry;
pEntry = &pAd->MacTab.Content[wcid];
tr_entry = &pAd->MacTab.tr_entry[wcid];
if (tr_entry->PsMode == PWR_ACTIVE)
{
tr_entry->ps_state = APPS_RETRIEVE_IDLE;
}
else
{
tr_entry->ps_state = APPS_RETRIEVE_DONE;
}
if (tr_entry->ps_state == APPS_RETRIEVE_IDLE)
{
MtHandleRxPsPoll(pAd, &pEntry->Addr[0], wcid, TRUE);
}
}
#endif /* MT_PS */