📄 soft_ap.c
字号:
}
VOID SendSingalToDaemon(
IN PRTMP_ADAPTER pAd,
IN INT sig)
{
DBGPRINT(RT_DEBUG_TRACE, "SendSingalToDaemon - ApdPid=%d\n", pAd->ApdPid);
if (pAd->ApdPid != 0)
{
kill_proc(pAd->ApdPid, sig, 0);
}
}
VOID ApStop(
IN PRTMP_ADAPTER pAd,
IN BOOLEAN bDFSRestart)
{
DBGPRINT(RT_DEBUG_TRACE, "!!! ApStop !!!\n");
if (bDFSRestart == TRUE)
{
RadarDetectionStop(pAd);
AsicSendCommandToMcu(pAd, 0x60, 0xff, 0x00, 0x00); // send stop-RD command to MCU
//delay to get H2M_MAILBOX ownership again before next RTMPSetLED().
mdelay(1000);
}
AsicDisableSync(pAd);
RTMPSetLED(pAd, LED_RADIO_OFF);
//delay to get H2M_MAILBOX ownership again before next RTMPSetLED().
mdelay(1000);
RTMPSetLED(pAd, LED_LINK_DOWN);
if(pAd->PortCfg.REKEYTimerRunning==TRUE)
{
RTMPCancelTimer(&pAd->PortCfg.REKEYTimer);
pAd->PortCfg.REKEYTimerRunning=FALSE;
}
if(pAd->PortCfg.CMTimerRunning==TRUE)
{
RTMPCancelTimer(&pAd->PortCfg.CounterMeasureTimer);
pAd->PortCfg.CMTimerRunning = FALSE;
}
MacTableReset(pAd, bDFSRestart);
}
/*
==========================================================================
Description:
This routine is used to clean up a specified power-saving queue. It's
used whenever a wireless client is deleted.
==========================================================================
*/
VOID CleanupPsQueue(
IN PRTMP_ADAPTER pAd,
IN PQUEUE_HEADER pQueue)
{
struct sk_buff *pSkb;
while (pQueue->Head)
{
pSkb = (struct sk_buff *)RemoveHeadQueue(pQueue);
if(pSkb)
#ifdef RTL865X_FAST_PATH
rtl865x_extDev_kfree_skb(pSkb, FALSE);
#else
RELEASE_NDIS_PACKET(pAd, pSkb);
#endif
}
}
/*
==========================================================================
Description:
This routine reset the entire MAC table. All packets pending in
the power-saving queues are freed here.
==========================================================================
*/
VOID MacTableReset(
IN PRTMP_ADAPTER pAd,
IN BOOLEAN bDFSRestart)
{
INT i;
ULONG IrqFlags;
PCHAR pOutBuffer = NULL;
ULONG FrameLen = 0;
HEADER_802_11 DisassocHdr;
USHORT Reason;
#ifndef THREAD_ISR
RTMP_SEM_LOCK(&pAd->MacTabLock, IrqFlags);
#endif
for (i=0; i<MAX_LEN_OF_MAC_TABLE; i++)
{
if (pAd->MacTab.Content[i].Valid)
{
if (pAd->MacTab.Content[i].RetryTimerRunning == TRUE)
{
DBGPRINT(RT_DEBUG_TRACE, "pAd->MacTab.Content[%d] Cancel Retry Timer !\n",i);
del_timer_sync(&pAd->MacTab.Content[i].RetryTimer);
pAd->MacTab.Content[i].RetryTimerRunning = FALSE;
}
#ifdef THREAD_ISR
RTMP_IRQ_LOCK(IrqFlags);
#endif
CleanupPsQueue(pAd, &pAd->MacTab.Content[i].PsQueue);
#ifdef THREAD_ISR
RTMP_IRQ_UNLOCK(IrqFlags);
#endif
// Before reset MacTable, send disassociation packet to client.
if ((!bDFSRestart) && (pAd->MacTab.Content[i].Sst == SST_ASSOC))
{
// send out a DISASSOC request frame
pOutBuffer = kmalloc(MAX_LEN_OF_MLME_BUFFER, MEM_ALLOC_FLAG);
if(pOutBuffer == NULL) {
#ifndef THREAD_ISR
RTMP_SEM_UNLOCK(&pAd->MacTabLock, IrqFlags);
#endif
return;
}
Reason = REASON_DISASSOC_INACTIVE;
DBGPRINT(RT_DEBUG_ERROR, "ASSOC - Send DISASSOC Reason = %d frame TO %x %x %x %x %x %x \n",Reason,pAd->MacTab.Content[i].Addr[0],
pAd->MacTab.Content[i].Addr[1],pAd->MacTab.Content[i].Addr[2],pAd->MacTab.Content[i].Addr[3],pAd->MacTab.Content[i].Addr[4],pAd->MacTab.Content[i].Addr[5]);
MgtMacHeaderInit(pAd, &DisassocHdr, SUBTYPE_DISASSOC, 0, pAd->MacTab.Content[i].Addr, pAd->PortCfg.MBSSID[pAd->MacTab.Content[i].ApIdx].Bssid);
MakeOutgoingFrame(pOutBuffer, &FrameLen, sizeof(HEADER_802_11), (CHAR *)&DisassocHdr, 2, (char*)&Reason, END_OF_ARGS);
MiniportMMRequest(pAd, pOutBuffer, FrameLen);
kfree(pOutBuffer);
RTMPusecDelay(2000);
}
}
}
#ifdef THREAD_ISR
RTMP_IRQ_LOCK(IrqFlags);
#endif
CleanupPsQueue(pAd, &pAd->MacTab.McastPsQueue);
NdisZeroMemory(&pAd->MacTab, sizeof(MAC_TABLE));
InitializeQueueHeader(&pAd->MacTab.McastPsQueue);
#ifdef THREAD_ISR
RTMP_IRQ_UNLOCK(IrqFlags);
#endif
#ifndef THREAD_ISR
RTMP_SEM_UNLOCK(&pAd->MacTabLock, IrqFlags);
#endif
}
/*
==========================================================================
Description:
Add and new entry into MAC table
==========================================================================
*/
MAC_TABLE_ENTRY *MacTableInsertEntry(
IN PRTMP_ADAPTER pAd,
IN PUCHAR pAddr,
IN UCHAR apidx)
{
UCHAR HashIdx;
int i;
MAC_TABLE_ENTRY *pEntry = NULL, *pCurrEntry;
ULONG IrqFlags;
// if FULL, return
if (pAd->MacTab.Size >= MAX_LEN_OF_MAC_TABLE)
return NULL;
// allocate one MAC entry
RTMP_SEM_LOCK(&pAd->MacTabLock, IrqFlags);
for (i = 1; i< MAX_LEN_OF_MAC_TABLE; i++) // skip entry#0 so that "entry index == AID" for fast lookup
{
// pick up the first available vacancy
if (pAd->MacTab.Content[i].Valid == FALSE)
{
pEntry = &pAd->MacTab.Content[i];
NdisZeroMemory(pEntry, sizeof(MAC_TABLE_ENTRY));
pEntry->Valid = TRUE;
// Move init entry retry timer to where it first created
init_timer(&pEntry->RetryTimer);
pEntry->bDot1xDynamicWep = FALSE;
pEntry->RetryTimerRunning = FALSE;
pEntry->CMTimerRunning = FALSE;
pEntry->RSNIE_Len = 0;
NdisMoveMemory(pEntry->R_Counter, pAd->PortCfg.R_Counter, sizeof(pEntry->R_Counter));
pEntry->ReTryCounter = PEER_MSG1_RETRY_TIMER_CTR;
pEntry->AuthMode = pAd->PortCfg.MBSSID[apidx].AuthMode;
pEntry->WepStatus = pAd->PortCfg.MBSSID[apidx].WepStatus;
pEntry->pAd = (unsigned long)pAd;
pEntry->PMKID_CacheIdx = ENTRY_NOT_FOUND;
if (pEntry->AuthMode < Ndis802_11AuthModeWPA)
pEntry->WpaState = AS_NOTUSE;
else
pEntry->WpaState = AS_INITIALIZE;
pEntry->GTKState = REKEY_NEGOTIATING;
pEntry->PrivacyFilter = Ndis802_11PrivFilterAcceptAll;
pEntry->PairwiseKey.KeyLen = 0;
pEntry->PortSecured = WPA_802_1X_PORT_NOT_SECURED;
AsicRemovePairwiseKeyEntry(pAd, (UCHAR)i);
COPY_MAC_ADDR(pEntry->Addr, pAddr);
pEntry->Sst = SST_NOT_AUTH;
pEntry->AuthState = AS_NOT_AUTH;
pEntry->Aid = 0;
pEntry->CapabilityInfo = 0;
pEntry->PsMode = PWR_ACTIVE;
pEntry->MaxSupportedRate = RATE_11;
pEntry->CurrTxRate = RATE_11;
pEntry->LastTxRate = pEntry->CurrTxRate;//for initial value
pEntry->PsQIdleCount = 0;
pEntry->NoDataIdleCount = 0;
InitializeQueueHeader(&pEntry->PsQueue);
pEntry->MaxSPLength = 0;
pEntry->bDlsInit = FALSE;
pEntry->ApIdx = apidx;
pAd->MacTab.Size ++;
DBGPRINT(RT_DEBUG_TRACE, "MacTableInsertEntry -IF(ra%d) allocate entry #%d, Total= %d\n",apidx, i, pAd->MacTab.Size);
break;
}
}
// add this MAC entry into HASH table
if (pEntry)
{
HashIdx = MAC_ADDR_HASH_INDEX(pAddr);
if (pAd->MacTab.Hash[HashIdx] == NULL)
{
pAd->MacTab.Hash[HashIdx] = pEntry;
}
else
{
pCurrEntry = pAd->MacTab.Hash[HashIdx];
while (pCurrEntry->pNext != NULL)
pCurrEntry = pCurrEntry->pNext;
pCurrEntry->pNext = pEntry;
}
}
RTMP_SEM_UNLOCK(&pAd->MacTabLock, IrqFlags);
return pEntry;
}
/*
==========================================================================
Description:
Delete a specified client from MAC table
==========================================================================
*/
BOOLEAN MacTableDeleteEntry(
IN PRTMP_ADAPTER pAd,
IN PUCHAR pAddr)
{
USHORT HashIdx;
MAC_TABLE_ENTRY *pEntry, *pPrevEntry;
ULONG IrqFlags;
RTMP_SEM_LOCK(&pAd->MacTabLock, IrqFlags);
HashIdx = MAC_ADDR_HASH_INDEX(pAddr);
pEntry = pAd->MacTab.Hash[HashIdx];
if (pEntry)
{
if (MAC_ADDR_EQUAL(pEntry->Addr, pAddr))
{
if(pEntry->RetryTimerRunning==TRUE)
{
DBGPRINT(RT_DEBUG_TRACE, "MacTableDeleteEntry : Cancel Retry Timer !\n");
del_timer_sync(&pEntry->RetryTimer);
pEntry->RetryTimerRunning=FALSE;
}
pAd->MacTab.Hash[HashIdx] = pEntry->pNext;
CleanupPsQueue(pAd, &pEntry->PsQueue); // return all skb buffer in PSQ
AsicRemovePairwiseKeyEntry(pAd, (UCHAR)(((ULONG)pEntry - (ULONG)&pAd->MacTab.Content[0])/sizeof(MAC_TABLE_ENTRY)));
NdisZeroMemory(pEntry, sizeof(MAC_TABLE_ENTRY));
pAd->MacTab.Size --;
DBGPRINT(RT_DEBUG_TRACE, "MacTableDeleteEntry 1 - Total= %d\n", pAd->MacTab.Size);
}
else
{
while (pEntry->pNext)
{
pPrevEntry = pEntry;
pEntry = pEntry->pNext;
if (MAC_ADDR_EQUAL(pEntry->Addr, pAddr))
{
if(pEntry->RetryTimerRunning==TRUE)
{
DBGPRINT(RT_DEBUG_TRACE, "MacTableDeleteEntry : Cancel Retry Timer !\n");
del_timer_sync(&pEntry->RetryTimer);
pEntry->RetryTimerRunning=FALSE;
}
pPrevEntry->pNext = pEntry->pNext;
CleanupPsQueue(pAd, &pEntry->PsQueue); // return all skb buffer in PSQ
AsicRemovePairwiseKeyEntry(pAd, (UCHAR)(((ULONG)pEntry - (ULONG)&pAd->MacTab.Content[0])/sizeof(MAC_TABLE_ENTRY)));
NdisZeroMemory(pEntry, sizeof(MAC_TABLE_ENTRY));
pAd->MacTab.Size --;
DBGPRINT(RT_DEBUG_TRACE, "MacTableDeleteEntry 2 - Total= %d\n", pAd->MacTab.Size);
break;
}
}
}
}
RTMP_SEM_UNLOCK(&pAd->MacTabLock, IrqFlags);
ApUpdateCapabilityAndErpIe(pAd);
return TRUE;
}
/*
==========================================================================
Description:
Look up the MAC address in the MAC table. Return NULL if not found.
Return:
pEntry - pointer to the MAC entry; NULL is not found
==========================================================================
*/
MAC_TABLE_ENTRY *MacTableLookup(
IN PRTMP_ADAPTER pAd,
IN PUCHAR pAddr)
{
ULONG HashIdx;
MAC_TABLE_ENTRY *pEntry = NULL;
HashIdx = MAC_ADDR_HASH_INDEX(pAddr);
pEntry = pAd->MacTab.Hash[HashIdx];
while (pEntry && pEntry->Valid)
{
if (MAC_ADDR_EQUAL(pEntry->Addr, pAddr))
{
break;
}
else
pEntry = pEntry->pNext;
}
return pEntry;
}
/*
==========================================================================
Description:
This routine is called by MlmePeriodicExec() every second to check if
1. any associated client in PSM. If yes, then TX MCAST/BCAST should be
out in DTIM only
2. any client being idle for too long and should be aged-out from MAC table
3. garbage collect PSQ
==========================================================================
*/
VOID MacTableMaintenance(
IN PRTMP_ADAPTER pAd)
{
INT i;
ULONG IrqFlags;
pAd->MacTab.fAnyStationInPsm = FALSE;
for (i = 0; i < MAX_LEN_OF_MAC_TABLE; i++)
{
MAC_TABLE_ENTRY *pEntry = &pAd->MacTab.Content[i];
if (pEntry->Valid == FALSE)
continue;
pEntry->NoDataIdleCount ++;
DBGPRINT(RT_DEBUG_INFO, "(ra%d)%02x:%02x:%02x:%02x:%02x:%02x,TxByte=%d,RxByte=%d,LastDataTime=%d\n", pEntry->ApIdx,
pEntry->Addr[0],pEntry->Addr[1],pEntry->Addr[2],pEntry->Addr[3],
pEntry->Addr[4],pEntry->Addr[5],pEntry->HSCounter.TotalTxByteCount,
pEntry->HSCounter.TotalRxByteCount,pEntry->HSCounter.LastDataPacketTime);
// 0. STA failed to complete association should be removed to save MAC table space.
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -