⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 cmm_data.c

📁 Linux下的RT系列无线网卡驱动,可以直接在x86平台上编译
💻 C
📖 第 1 页 / 共 5 页
字号:
/* ************************************************************************* * Ralink Tech Inc. * 4F, No. 2 Technology 5th Rd. * Science-based Industrial Park * Hsin-chu, Taiwan, R.O.C. * * (c) Copyright 2002-2007, Ralink Technology, Inc. * * This program is free software; you can redistribute it and/or modify  *  * it under the terms of the GNU General Public License as published by  *  * the Free Software Foundation; either version 2 of the License, or     *  * (at your option) any later version.                                   *  *                                                                       *  * This program is distributed in the hope that it will be useful,       *  * but WITHOUT ANY WARRANTY; without even the implied warranty of        *  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the         *  * GNU General Public License for more details.                          *  *                                                                       *  * You should have received a copy of the GNU General Public License     *  * along with this program; if not, write to the                         *  * Free Software Foundation, Inc.,                                       *  * 59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.             *  *                                                                       *  **************************************************************************/ #include "rt_config.h"#define MAX_TX_IN_TBTT		(16)#define GET_TXRING_FREENO(_pAd, _QueIdx) \	(_pAd->TxRing[_QueIdx].TxSwFreeIdx > _pAd->TxRing[QueIdx].TxCpuIdx)	? \			(_pAd->TxRing[_QueIdx].TxSwFreeIdx - _pAd->TxRing[_QueIdx].TxCpuIdx - 1) \			 :	\			(_pAd->TxRing[_QueIdx].TxSwFreeIdx + TX_RING_SIZE - _pAd->TxRing[_QueIdx].TxCpuIdx - 1);#define GET_MGMTRING_FREENO(_pAd) \	(_pAd->MgmtRing.TxSwFreeIdx > _pAd->MgmtRing.TxCpuIdx)	? \			(_pAd->MgmtRing.TxSwFreeIdx - _pAd->MgmtRing.TxCpuIdx - 1) \			 :	\			(_pAd->MgmtRing.TxSwFreeIdx + MGMT_RING_SIZE - _pAd->MgmtRing.TxCpuIdx - 1);UCHAR	SNAP_802_1H[] = {0xaa, 0xaa, 0x03, 0x00, 0x00, 0x00};UCHAR	SNAP_BRIDGE_TUNNEL[] = {0xaa, 0xaa, 0x03, 0x00, 0x00, 0xf8};// Add Cisco Aironet SNAP heade for CCX2 supportUCHAR	SNAP_AIRONET[] = {0xaa, 0xaa, 0x03, 0x00, 0x40, 0x96, 0x00, 0x00};UCHAR	CKIP_LLC_SNAP[] = {0xaa, 0xaa, 0x03, 0x00, 0x40, 0x96, 0x00, 0x02};UCHAR	EAPOL_LLC_SNAP[]= {0xaa, 0xaa, 0x03, 0x00, 0x00, 0x00, 0x88, 0x8e};UCHAR	EAPOL[] = {0x88, 0x8e};UCHAR   TPID[] = {0x81, 0x00}; /* VLAN related */UCHAR	IPX[] = {0x81, 0x37};UCHAR	APPLE_TALK[] = {0x80, 0xf3};UCHAR	RateIdToPlcpSignal[12] = { 	 0, /* RATE_1 */	1, /* RATE_2 */ 	2, /* RATE_5_5 */	3, /* RATE_11 */	// see BBP spec	11, /* RATE_6 */   15, /* RATE_9 */    10, /* RATE_12 */   14, /* RATE_18 */	// see IEEE802.11a-1999 p.14	 9, /* RATE_24 */  13, /* RATE_36 */	8, /* RATE_48 */   12  /* RATE_54 */ }; // see IEEE802.11a-1999 p.14UCHAR	 OfdmSignalToRateId[16] = {	RATE_54,  RATE_54,	RATE_54,  RATE_54,	// OFDM PLCP Signal = 0,  1,  2,  3 respectively	RATE_54,  RATE_54,	RATE_54,  RATE_54,	// OFDM PLCP Signal = 4,  5,  6,  7 respectively	RATE_48,  RATE_24,	RATE_12,  RATE_6,	// OFDM PLCP Signal = 8,  9,  10, 11 respectively	RATE_54,  RATE_36,	RATE_18,  RATE_9,	// OFDM PLCP Signal = 12, 13, 14, 15 respectively};UCHAR	 OfdmRateToRxwiMCS[12] = {	0,  0,	0,  0,	 	0,  1,	2,  3,	// OFDM rate 6,9,12,18 = rxwi mcs 0,1,2,3	4,  5,	6,  7,	// OFDM rate 24,36,48,54 = rxwi mcs 4,5,6,7};UCHAR	 RxwiMCSToOfdmRate[12] = {	RATE_6,  RATE_9,	RATE_12,  RATE_18,	 	RATE_24,  RATE_36,	RATE_48,  RATE_54,	// OFDM rate 6,9,12,18 = rxwi mcs 0,1,2,3	4,  5,	6,  7,	// OFDM rate 24,36,48,54 = rxwi mcs 4,5,6,7};char*   MCSToMbps[] = {"1Mbps","2Mbps","5.5Mbps","11Mbps","06Mbps","09Mbps","12Mbps","18Mbps","24Mbps","36Mbps","48Mbps","54Mbps","MM-0","MM-1","MM-2","MM-3","MM-4","MM-5","MM-6","MM-7","MM-8","MM-9","MM-10","MM-11","MM-12","MM-13","MM-14","MM-15","MM-32","ee1","ee2","ee3"};UCHAR default_cwmin[]={CW_MIN_IN_BITS, CW_MIN_IN_BITS, CW_MIN_IN_BITS-1, CW_MIN_IN_BITS-2};UCHAR default_cwmax[]={CW_MAX_IN_BITS, CW_MAX_IN_BITS, CW_MIN_IN_BITS, CW_MIN_IN_BITS-1};UCHAR default_sta_aifsn[]={3,7,2,2};UCHAR MapUserPriorityToAccessCategory[8] = {QID_AC_BE, QID_AC_BK, QID_AC_BK, QID_AC_BE, QID_AC_VI, QID_AC_VI, QID_AC_VO, QID_AC_VO};/*	========================================================================	Routine Description:		API for MLME to transmit management frame to AP (BSS Mode)	or station (IBSS Mode)			Arguments:		pAd Pointer to our adapter		pData		Pointer to the outgoing 802.11 frame		Length		Size of outgoing management frame			Return Value:		NDIS_STATUS_FAILURE		NDIS_STATUS_PENDING		NDIS_STATUS_SUCCESS	IRQL = PASSIVE_LEVEL	IRQL = DISPATCH_LEVEL		Note:		========================================================================*/NDIS_STATUS MiniportMMRequest(	IN	PRTMP_ADAPTER	pAd,	IN	UCHAR			QueIdx,	IN	PUCHAR			pData,	IN	UINT			Length){	PNDIS_PACKET	pPacket;	NDIS_STATUS  Status = NDIS_STATUS_SUCCESS;	ULONG	 FreeNum;	TXWI_STRUC		TXWI;	ULONG	SW_TX_IDX; //TEMP, SW_TX_IDX;	PTXD_STRUC		pTxD;	unsigned long	IrqFlags = 0;	UCHAR			IrqState;		QueIdx=3;		ASSERT(Length <= MGMT_DMA_BUFFER_SIZE);	// 2860C use Tx Ring		IrqState = pAd->irq_disabled;	if ((pAd->MACVersion == 0x28600100) && (!IrqState))		RTMP_IRQ_LOCK(&pAd->irq_lock, IrqFlags);	do 	{		// Reset is in progress, stop immediately		if ( RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_RESET_IN_PROGRESS) ||			 RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_HALT_IN_PROGRESS)||			 !RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_START_UP))	{			Status = NDIS_STATUS_FAILURE;			break;	}		// Check Free priority queue		// Since we use PBF Queue2 for management frame.  Its corresponding DMA ring should be using TxRing.		// 2860C use Tx Ring	if (pAd->MACVersion == 0x28600100)	{		FreeNum = GET_TXRING_FREENO(pAd, QueIdx);		SW_TX_IDX = pAd->TxRing[QueIdx].TxCpuIdx;		pTxD  = (PTXD_STRUC) pAd->TxRing[QueIdx].Cell[SW_TX_IDX].AllocVa;	}	else	{		FreeNum = GET_MGMTRING_FREENO(pAd);				SW_TX_IDX = pAd->MgmtRing.TxCpuIdx;		pTxD  = (PTXD_STRUC) pAd->MgmtRing.Cell[SW_TX_IDX].AllocVa;	}		if ((FreeNum > 0))			{			NdisZeroMemory(&TXWI, TXWI_SIZE);			Status = RTMPAllocateNdisPacket(pAd, &pPacket, (PUCHAR)&TXWI, TXWI_SIZE, pData, Length);			if (Status != NDIS_STATUS_SUCCESS)				{									DBGPRINT(RT_DEBUG_WARN, ("MiniportMMRequest (error:: can't allocate NDIS PACKET)\n"));					break;				}			//pAd->CommonCfg.MlmeTransmit.field.MODE = MODE_CCK;			//pAd->CommonCfg.MlmeRate = RATE_2; 						Status = MlmeHardTransmit(pAd, QueIdx, pPacket);				if (Status != NDIS_STATUS_SUCCESS)				RTMPFreeNdisPacket(pAd, pPacket);			}		else			{			pAd->RalinkCounters.MgmtRingFullCount++;			DBGPRINT(RT_DEBUG_ERROR, ("Qidx(%d), not enough space in MgmtRing\n", QueIdx));		}	} while (FALSE);	// 2860C use Tx Ring	if ((pAd->MACVersion == 0x28600100) && (!IrqState))		RTMP_IRQ_UNLOCK(&pAd->irq_lock, IrqFlags);	return Status;}NDIS_STATUS MiniportMMRequestUnlock(	IN	PRTMP_ADAPTER	pAd,	IN	UCHAR			QueIdx,	IN	PUCHAR			pData,	IN	UINT			Length){	PNDIS_PACKET	pPacket;	NDIS_STATUS  Status = NDIS_STATUS_SUCCESS;	ULONG	 FreeNum;	TXWI_STRUC		TXWI;	ULONG	SW_TX_IDX; //TEMP, SW_TX_IDX;	PTXD_STRUC		pTxD;	//ULONG			IrqFlags = 0;	QueIdx = 3;	ASSERT(Length <= MGMT_DMA_BUFFER_SIZE);	do 	{		// Reset is in progress, stop immediately		if ( RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_RESET_IN_PROGRESS) ||			 RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_HALT_IN_PROGRESS)||			 !RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_START_UP))		{			Status = NDIS_STATUS_FAILURE;			break;		}		// Check Free priority queue		// Since we use PBF Queue2 for management frame.  Its corresponding DMA ring should be using TxRing.		// 2860C use Tx Ring		if (pAd->MACVersion == 0x28600100)		{				FreeNum = GET_TXRING_FREENO(pAd, QueIdx);			SW_TX_IDX = pAd->TxRing[QueIdx].TxCpuIdx;			pTxD  = (PTXD_STRUC) pAd->TxRing[QueIdx].Cell[SW_TX_IDX].AllocVa;		}		else		{			FreeNum = GET_MGMTRING_FREENO(pAd);					SW_TX_IDX = pAd->MgmtRing.TxCpuIdx;			pTxD  = (PTXD_STRUC) pAd->MgmtRing.Cell[SW_TX_IDX].AllocVa;		}		if ((FreeNum > 0))			{			NdisZeroMemory(&TXWI, TXWI_SIZE);			Status = RTMPAllocateNdisPacket(pAd, &pPacket, (PUCHAR)&TXWI, TXWI_SIZE, pData, Length);			if (Status != NDIS_STATUS_SUCCESS)				{									DBGPRINT(RT_DEBUG_WARN, ("MiniportMMRequest (error:: can't allocate NDIS PACKET)\n"));					break;				}			//pAd->CommonCfg.MlmeTransmit.field.MODE = MODE_CCK;			//pAd->CommonCfg.MlmeRate = RATE_2; 						Status = MlmeHardTransmit(pAd, QueIdx, pPacket);				if (Status != NDIS_STATUS_SUCCESS)				RTMPFreeNdisPacket(pAd, pPacket);			}			else			{			pAd->RalinkCounters.MgmtRingFullCount++;			DBGPRINT(RT_DEBUG_ERROR, ("Qidx(%d), not enough space in MgmtRing\n", QueIdx));		}	} while (FALSE);	return Status;}/*	========================================================================	Routine Description:		Copy frame from waiting queue into relative ring buffer and set 	appropriate ASIC register to kick hardware transmit function		Arguments:		pAd Pointer to our adapter		pBuffer 	Pointer to	memory of outgoing frame		Length		Size of outgoing management frame			Return Value:		NDIS_STATUS_FAILURE		NDIS_STATUS_PENDING		NDIS_STATUS_SUCCESS	IRQL = PASSIVE_LEVEL	IRQL = DISPATCH_LEVEL		Note:		========================================================================*/NDIS_STATUS MlmeHardTransmit(	IN	PRTMP_ADAPTER	pAd,	IN	UCHAR	QueIdx,	IN	PNDIS_PACKET	pPacket){		if ((pAd->CommonCfg.RadarDetect.RDMode != RD_NORMAL_MODE)#ifdef CARRIER_DETECTION_SUPPORT		||(isCarrierDetectExist(pAd) == TRUE)#endif // CARRIER_DETECTION_SUPPORT //		)	{		return NDIS_STATUS_FAILURE;	}	if ( pAd->MACVersion == 0x28600100 )		return MlmeHardTransmitTxRing(pAd,QueIdx,pPacket);	else		return MlmeHardTransmitMgmtRing(pAd,QueIdx,pPacket);}NDIS_STATUS MlmeHardTransmitTxRing(	IN	PRTMP_ADAPTER	pAd,	IN	UCHAR	QueIdx,	IN	PNDIS_PACKET	pPacket){	PACKET_INFO 	PacketInfo;	PUCHAR			pSrcBufVA;	UINT			SrcBufLen;	PTXD_STRUC		pTxD;#ifdef BIG_ENDIAN    PTXD_STRUC      pDestTxD;    TXD_STRUC       TxD;#endif	PHEADER_802_11	pHeader_802_11;	BOOLEAN 		bAckRequired, bInsertTimestamp;	ULONG			SrcBufPA;	//UCHAR			TxBufIdx;	UCHAR			MlmeRate;	ULONG			SwIdx = pAd->TxRing[QueIdx].TxCpuIdx;	PTXWI_STRUC 	pFirstTxWI;	//ULONG	i;	//HTTRANSMIT_SETTING	MlmeTransmit;   //Rate for this MGMT frame.	ULONG	 FreeNum;	RTMP_QueryPacketInfo(pPacket, &PacketInfo, &pSrcBufVA, &SrcBufLen);		if (pSrcBufVA == NULL)	{		// The buffer shouldn't be NULL		return NDIS_STATUS_FAILURE;	}	// Make sure MGMT ring resource won't be used by other threads	//NdisAcquireSpinLock(&pAd->TxRingLock);	FreeNum = GET_TXRING_FREENO(pAd, QueIdx);	if (FreeNum == 0)	{		//NdisReleaseSpinLock(&pAd->TxRingLock);		return NDIS_STATUS_FAILURE;	}	SwIdx = pAd->TxRing[QueIdx].TxCpuIdx;#ifndef BIG_ENDIAN		pTxD  = (PTXD_STRUC) pAd->TxRing[QueIdx].Cell[SwIdx].AllocVa;#else    pDestTxD  = (PTXD_STRUC)pAd->TxRing[QueIdx].Cell[SwIdx].AllocVa;    TxD = *pDestTxD;    pTxD = &TxD;    RTMPDescriptorEndianChange((PUCHAR)pTxD, TYPE_TXD);#endif	if (pAd->TxRing[QueIdx].Cell[SwIdx].pNdisPacket)	{		printk("MlmeHardTransmit Error\n");		//NdisReleaseSpinLock(&pAd->TxRingLock);		return NDIS_STATUS_FAILURE;	}	// outgoing frame always wakeup PHY to prevent frame lost 	// if (pAd->StaCfg.Psm == PWR_SAVE)	if (OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_DOZE))		AsicForceWakeup(pAd);	pFirstTxWI	=(PTXWI_STRUC)pSrcBufVA;		pHeader_802_11			 = (PHEADER_802_11) (pSrcBufVA + TXWI_SIZE);	if (pHeader_802_11->Addr1[0] & 0x01)	{		MlmeRate = pAd->CommonCfg.BasicMlmeRate;	}	else	{		MlmeRate = pAd->CommonCfg.MlmeRate;	}		// Verify Mlme rate for a / g bands.		if ((pAd->LatchRfRegs.Channel > 14) && (MlmeRate < RATE_6)) // 11A band		MlmeRate = RATE_6;	//	// Should not be hard code to set PwrMgmt to 0 (PWR_ACTIVE)	// Snice it's been set to 0 while on MgtMacHeaderInit	// By the way this will cause frame to be send on PWR_SAVE failed.	// 	// pHeader_802_11->FC.PwrMgmt = 0; // (pAd->StaCfg.Psm == PWR_SAVE);	//	// In WMM-UAPSD, mlme frame should be set psm as power saving but probe request frame#ifdef CONFIG_STA_SUPPORT    // Data-Null packets alse pass through MMRequest in RT2860, however, we hope control the psm bit to pass APSD	if (pHeader_802_11->FC.Type != BTYPE_DATA)            {#endif // CONFIG_STA_SUPPORT //        	if ((pHeader_802_11->FC.SubType == SUBTYPE_PROBE_REQ) || !(pAd->CommonCfg.bAPSDCapable && pAd->CommonCfg.APEdcaParm.bAPSDCapable))    	{    		pHeader_802_11->FC.PwrMgmt = PWR_ACTIVE;    	}    	else    	{    		pHeader_802_11->FC.PwrMgmt = pAd->CommonCfg.bAPSDForcePowerSave;    	}#ifdef CONFIG_STA_SUPPORT            }#endif // CONFIG_STA_SUPPORT //		bInsertTimestamp = FALSE;	if (pHeader_802_11->FC.Type == BTYPE_CNTL) // must be PS-POLL	{		bAckRequired = FALSE;	}	else // BTYPE_MGMT or BTYPE_DATA(must be NULL frame)	{		if (pHeader_802_11->Addr1[0] & 0x01) // MULTICAST, BROADCAST		{			bAckRequired = FALSE;			pHeader_802_11->Duration = 0;		}		else		{			bAckRequired = TRUE;			pHeader_802_11->Duration = RTMPCalcDuration(pAd, MlmeRate, 14);			if (pHeader_802_11->FC.SubType == SUBTYPE_PROBE_RSP)			{				bInsertTimestamp = TRUE;			}		}	}	pHeader_802_11->Sequence = pAd->Sequence++;	if (pAd->Sequence > 0xfff)		pAd->Sequence = 0;	// Before radar detection done, mgmt frame can not be sent but probe req	// Because we need to use probe req to trigger driver to send probe req in passive scan	if ((pHeader_802_11->FC.SubType != SUBTYPE_PROBE_REQ)		&& (pAd->CommonCfg.bIEEE80211H == 1)		&& (pAd->CommonCfg.RadarDetect.RDMode != RD_NORMAL_MODE))	{		DBGPRINT(RT_DEBUG_ERROR,("MlmeHardTransmit --> radar detect not in normal mode !!!\n"));		//NdisReleaseSpinLock(&pAd->TxRingLock);		return (NDIS_STATUS_FAILURE);	}#ifdef BIG_ENDIAN	RTMPFrameEndianChange(pAd, (PUCHAR)pHeader_802_11, DIR_WRITE, FALSE);#endif	//	// fill scatter-and-gather buffer list into TXD. Internally created NDIS PACKET	// should always has only one ohysical buffer, and the whole frame size equals

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -