测试在MT7620A上跑openwrt;router模式下,手机连接MT7620A板子就是失败。
经过分析发现:
在ralink的wifi driver中WPA成对密钥的四次握手,以及组密钥协商信令过程,
如果AP未及时收到client回复的信令,可能会主动踢掉client,或者很快重发WPA成对密钥的第一个信令;
如果使用iwpriv ra0 set Debug=3 输出更多log信息的话,会看到client反复不停连接AP,log中有很多如下的信息
WPARetryExec---> ReTryCounter
因此确实因为某些原因处理速度慢的话,可以考虑修改AP这边的以下代码。 不过也可能是其他原因造成的wifi driver处理速度太慢,需要进一步深究。
VOID WPARetryExec(
IN PVOID SystemSpecific1,
IN PVOID FunctionContext,
IN PVOID SystemSpecific2,
IN PVOID SystemSpecific3)
{
MAC_TABLE_ENTRY *pEntry = (MAC_TABLE_ENTRY *)FunctionContext;
if ((pEntry) && IS_ENTRY_CLIENT(pEntry))
{
PRTMP_ADAPTER pAd = (PRTMP_ADAPTER)pEntry->pAd;
pEntry->ReTryCounter++;
DBGPRINT(RT_DEBUG_TRACE, ("WPARetryExec---> ReTryCounter=%d, WpaState=%d \n", pEntry->ReTryCounter, pEntry->WpaState));
switch (pEntry->AuthMode)
{
case Ndis802_11AuthModeWPA:
case Ndis802_11AuthModeWPAPSK:
case Ndis802_11AuthModeWPA2:
case Ndis802_11AuthModeWPA2PSK:
/* 1. GTK already retried, give up and disconnect client. */
if (pEntry->ReTryCounter > (GROUP_MSG1_RETRY_TIMER_CTR + 1))
{
/* send wireless event - for group key handshaking timeout */
RTMPSendWirelessEvent(pAd, IW_GROUP_HS_TIMEOUT_EVENT_FLAG, pEntry->Addr, pEntry->apidx, 0);
DBGPRINT(RT_DEBUG_TRACE, ("WPARetryExec::Group Key HS exceed retry count, Disassociate client, pEntry->ReTryCounter %d\n", pEntry->ReTryCounter));
MlmeDeAuthAction(pAd, pEntry, REASON_GROUP_KEY_HS_TIMEOUT, FALSE);
}
/* 2. Retry GTK. */
else if (pEntry->ReTryCounter > GROUP_MSG1_RETRY_TIMER_CTR)
{
DBGPRINT(RT_DEBUG_TRACE, ("WPARetryExec::ReTry 2-way group-key Handshake \n"));
if (pEntry->GTKState == REKEY_NEGOTIATING)
{
WPAStart2WayGroupHS(pAd, pEntry);
RTMPSetTimer(&pEntry->RetryTimer, PEER_MSG3_RETRY_EXEC_INTV);
}
}
/* 3. 4-way message 1 retried more than three times. Disconnect client */
else if (pEntry->ReTryCounter > (PEER_MSG1_RETRY_TIMER_CTR + 3))
{
/* send wireless event - for pairwise key handshaking timeout */
RTMPSendWirelessEvent(pAd, IW_PAIRWISE_HS_TIMEOUT_EVENT_FLAG, pEntry->Addr, pEntry->apidx, 0);
DBGPRINT(RT_DEBUG_TRACE, ("WPARetryExec::MSG1 timeout, pEntry->ReTryCounter = %d\n", pEntry->ReTryCounter));
MlmeDeAuthAction(pAd, pEntry, REASON_4_WAY_TIMEOUT, FALSE);
}
/* 4. Retry 4 way message 1, the last try, the timeout is 3 sec for EAPOL-Start */
else if (pEntry->ReTryCounter == (PEER_MSG1_RETRY_TIMER_CTR + 3))
{
DBGPRINT(RT_DEBUG_TRACE, ("WPARetryExec::Retry MSG1, the last try\n"));
WPAStart4WayHS(pAd , pEntry, PEER_MSG3_RETRY_EXEC_INTV);
}
/* 4. Retry 4 way message 1 */
else if (pEntry->ReTryCounter < (PEER_MSG1_RETRY_TIMER_CTR + 3))
{
if ((pEntry->WpaState == AS_PTKSTART) || (pEntry->WpaState == AS_INITPSK) || (pEntry->WpaState == AS_INITPMK))
{
DBGPRINT(RT_DEBUG_TRACE, ("WPARetryExec::ReTry MSG1 of 4-way Handshake\n"));
WPAStart4WayHS(pAd, pEntry, PEER_MSG1_RETRY_EXEC_INTV);
}
}
break;
default:
break;
}
}
尝试做的一些修改,简单试了一下,可以解决一些问题,供参考:
/* 3. 4-way message 1 retried more than three times. Disconnect client */
//else if (pEntry->ReTryCounter > (PEER_MSG1_RETRY_TIMER_CTR + 3))
else if (
( (pEntry->ReTryCounter > (PEER_MSG1_RETRY_TIMER_CTR + 3))
&& (pEntry->ReTryCounter < PEER_MSG3_RETRY_TIMER_CTR) )
||
( (pEntry->ReTryCounter > (PEER_MSG3_RETRY_TIMER_CTR + 3))
&& (pEntry->ReTryCounter < GROUP_MSG1_RETRY_TIMER_CTR) )
)
{
/* send wireless event - for pairwise key handshaking timeout */
RTMPSendWirelessEvent(pAd, IW_PAIRWISE_HS_TIMEOUT_EVENT_FLAG, pEntry->Addr, pEntry->apidx, 0);
DBGPRINT(RT_DEBUG_TRACE, ("WPARetryExec::MSG1 or MSG3 timeout, pEntry->ReTryCounter = %d\n", pEntry->ReTryCounter));
MlmeDeAuthAction(pAd, pEntry, REASON_4_WAY_TIMEOUT, FALSE);
}
/* 4. Retry 4 way message 1 */
else if (pEntry->ReTryCounter < (PEER_MSG1_RETRY_TIMER_CTR + 3))
{
if ((pEntry->WpaState == AS_PTKSTART) || (pEntry->WpaState == AS_INITPSK) || (pEntry->WpaState == AS_INITPMK))
{
//DBGPRINT(RT_DEBUG_TRACE, ("WPARetryExec::ReTry MSG1 of 4-way Handshake\n"));
//WPAStart4WayHS(pAd, pEntry, PEER_MSG1_RETRY_EXEC_INTV);
}
}