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

📄 rtusb_bulk.c

📁 台湾RALink公司的 rt2570无线 802.11g 网卡的 驱动的源代码 ,支持linux2.4以上的 内河
💻 C
📖 第 1 页 / 共 3 页
字号:
/*
 ***************************************************************************
 * Ralink Tech Inc.
 * 4F, No. 2 Technology 5th Rd.
 * Science-based Industrial Park
 * Hsin-chu, Taiwan, R.O.C.
 *
 * (c) Copyright 2002-2004, 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.             * 
 *                                                                       * 
 ************************************************************************
	Module Name:
	rtusb_bulk.c

	Abstract:

	Revision History:
	Who			When			What
	--------	----------		----------------------------------------------
	Name		Date			Modification logs
	Jan Lee		2005-06-01		Release
*/
#include	"rt_config.h"
#ifndef URB_ASYNC_UNLINK
#define URB_ASYNC_UNLINK	0
#endif
//typedef VOID (*STATE_MACHINE_FUNC)(VOID *Adaptor, MLME_QUEUE_ELEM *Elem);

void RTusb_fill_bulk_urb (struct urb *pUrb,
	struct usb_device *usb,
	unsigned int bulkpipe,
	void *TransferBuf,
	int BufSize,
	usb_complete_t Complete,
	void *Context)
{

#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,5,0)
usb_fill_bulk_urb(pUrb, usb, bulkpipe, TransferBuf, BufSize, Complete, Context);	


#else
FILL_BULK_URB(pUrb, usb, bulkpipe, TransferBuf, BufSize, Complete, Context);	
#endif

}

/*
	========================================================================
	
	Routine Description:

	Arguments:

	Return Value:

	IRQL = 
	
	Note:
	
	========================================================================
*/
VOID	RTUSBBulkOutDataPacket(
	IN	PRT2570ADAPTER	pAdapter,
	IN	UCHAR	Index)
{
	PTX_CONTEXT pTxContext;
	PURB			pUrb;
	int ret = 0;
					
	NdisAcquireSpinLock(&pAdapter->BulkOutLock);
	if (pAdapter->BulkOutPending == TRUE)
	{
		NdisReleaseSpinLock(&pAdapter->BulkOutLock);
		return;
	}
	pAdapter->BulkOutPending = TRUE;
	NdisReleaseSpinLock(&pAdapter->BulkOutLock);
	pTxContext = &(pAdapter->TxContext[Index]);

	// Increase Total transmit byte counter
	pAdapter->RalinkCounters.TransmittedByteCount +=  pTxContext->BulkOutSize;

	// Clear Data flag
	RTUSB_CLEAR_BULK_FLAG(pAdapter, fRTUSB_BULK_OUT_DATA_FRAG);
	//The Data Bulk out protection is to Test InUse flag, temporarily not CLEAR DATA_NORMAL flag to test
	//RTUSB_CLEAR_BULK_FLAG(pAdapter, fRTUSB_BULK_OUT_DATA_NORMAL);
	pUrb = pTxContext->pUrb;
	if (pTxContext->InUse != TRUE)
	{
		DBGPRINT(RT_DEBUG_ERROR, "RTUSBBulkOutDataPacket failed, pTxContext->InUse != TRUE, Index %d, NextBulkOutIndex %d\n", Index, pAdapter->NextBulkOutIndex);
		NdisAcquireSpinLock(&pAdapter->BulkOutLock);
		pAdapter->BulkOutPending = FALSE;
		NdisReleaseSpinLock(&pAdapter->BulkOutLock);
		return;
	}
	else if (pAdapter->MediaState == NdisMediaStateDisconnected)
	{
		//
		// Since there is no connection, so we need to empty the Tx Bulk out Ring.
		//
		while (atomic_read(&pAdapter->TxCount) > 0)
		{
			DBGPRINT(RT_DEBUG_ERROR, "RTUSBBulkOutDataPacket failed, snice NdisMediaStateDisconnected discard NextBulkOutIndex %d, NextIndex = %d\n", pAdapter->NextBulkOutIndex, pAdapter->NextTxIndex);
			FREE_TX_RING(pAdapter, pTxContext);			
			pTxContext = &(pAdapter->TxContext[pAdapter->NextBulkOutIndex]);
		}

		NdisAcquireSpinLock(&pAdapter->BulkOutLock);
		pAdapter->BulkOutPending = FALSE;
		NdisReleaseSpinLock(&pAdapter->BulkOutLock);
		
		return;
	}
		
	pTxContext->IRPPending = TRUE;

	RTusb_fill_bulk_urb(pUrb,
		pAdapter->usb,
		usb_sndbulkpipe(pAdapter->usb, 1),
		pTxContext->TransferBuffer,
		pTxContext->BulkOutSize,
		RTUSBBulkOutDataPacketComplete,
		pTxContext);

	if((ret = rtusb_submit_urb(pUrb))!=0)
	{
		DBGPRINT(RT_DEBUG_ERROR,"Submit Tx URB failed %d\n", ret);
		return;
	}
	DBGPRINT(RT_DEBUG_INFO,"<==RTUSBBulkOutDataPacket BulkOutSize = %d\n", pTxContext->BulkOutSize);

	return;
}

/*
	========================================================================
	
	Routine Description:

	Arguments:

	Return Value:

	IRQL = 
	
	Note:
	
	========================================================================
*/
VOID	RTUSBBulkOutNullFrame(
	IN	PRT2570ADAPTER	pAdapter)
{
	PTX_CONTEXT	pNullContext = &(pAdapter->NullContext);
	PURB			pUrb;
	int ret = 0;

	NdisAcquireSpinLock(&pAdapter->BulkOutLock);
	if (pAdapter->BulkOutPending == TRUE)
	{
		NdisReleaseSpinLock(&pAdapter->BulkOutLock);
		return;
	}
	pAdapter->BulkOutPending = TRUE;
	NdisReleaseSpinLock(&pAdapter->BulkOutLock);
	// Increase Total transmit byte counter
	pAdapter->RalinkCounters.TransmittedByteCount +=  pNullContext->BulkOutSize;

	DBGPRINT_RAW(RT_DEBUG_INFO, "--->RTUSBBulkOutNullFrame \n");
	
	pUrb = pNullContext->pUrb;
	RTusb_fill_bulk_urb(pUrb,
		pAdapter->usb,
		usb_sndbulkpipe(pAdapter->usb, 1),
		pNullContext->TransferBuffer,
		pNullContext->BulkOutSize,
		RTUSBBulkOutNullFrameComplete,
		pNullContext);

	if((ret = rtusb_submit_urb(pUrb))!=0)
	{
		DBGPRINT(RT_DEBUG_ERROR,"Submit Tx URB failed %d\n", ret);
		return;
	}
	DBGPRINT(RT_DEBUG_INFO,"<==RTUSBBulkOutDataPacket\n");

	return;
}

/*
	========================================================================
	
	Routine Description:

	Arguments:

	Return Value:

	IRQL = 
	
	Note:
	
	========================================================================
*/
VOID	RTUSBBulkOutMLMEPacket(
	IN	PRT2570ADAPTER	pAdapter,
	IN	UCHAR			Index)
{
	PTX_CONTEXT		pMLMEContext;
	PURB			pUrb;
	int ret = 0;
					
	pMLMEContext = &pAdapter->MLMEContext[Index];
	NdisAcquireSpinLock(&pAdapter->BulkOutLock);
	if (pAdapter->BulkOutPending == TRUE)
	{
		NdisReleaseSpinLock(&pAdapter->BulkOutLock);
		return;
	}
	pAdapter->BulkOutPending = TRUE;
	NdisReleaseSpinLock(&pAdapter->BulkOutLock);

	// Increase Total transmit byte counter
	pAdapter->RalinkCounters.TransmittedByteCount +=  pMLMEContext->BulkOutSize;

	// Clear MLME bulk flag
	RTUSB_CLEAR_BULK_FLAG(pAdapter, fRTUSB_BULK_OUT_MLME);

	DBGPRINT(RT_DEBUG_INFO, "RTUSBBulkOutMLMEPacket::PrioRingFirstIndex = %d, PrioRingTxCnt = %d, PopMgmtIndex = %d, PushMgmtIndex = %d, NextMLMEIndex = %d\n", 
			pAdapter->PrioRingFirstIndex, 
			pAdapter->PrioRingTxCnt, pAdapter->PopMgmtIndex, pAdapter->PushMgmtIndex, pAdapter->NextMLMEIndex);

	pMLMEContext->IRPPending = TRUE;

	pUrb = pMLMEContext->pUrb;
		
	RTusb_fill_bulk_urb(pUrb,
		pAdapter->usb,
		usb_sndbulkpipe(pAdapter->usb, 1),
		pMLMEContext->TransferBuffer,
		pMLMEContext->BulkOutSize,
		RTUSBBulkOutMLMEPacketComplete,
		pMLMEContext);
	
	if((ret = rtusb_submit_urb(pUrb))!=0)
	{
		DBGPRINT(RT_DEBUG_ERROR,"Submit MLME URB failed %d\n", ret);
		return;
	}
	DBGPRINT(RT_DEBUG_INFO,"<==RTUSBBulkOutMLMEPacket\n");

	return;
}








#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,5,0)

VOID RTUSBBulkOutDataPacketComplete(purbb_t pUrb,struct pt_regs *pt_regs)
{
	PTX_CONTEXT 	pTxContext;
	PRT2570ADAPTER	pAdapter;
	NTSTATUS		status;

	DBGPRINT_RAW(RT_DEBUG_INFO, "--->RTUSBBulkOutDataPacketComplete\n");
	pTxContext= (PTX_CONTEXT)pUrb->context;
	pAdapter = pTxContext->pAdapter;
	status = pUrb->status;
	if (status == USB_ST_NOERROR)
 	{
		if (pTxContext->LastOne == TRUE)
		{
			pAdapter->Counters.GoodTransmits++;
			FREE_TX_RING(pAdapter, pTxContext);

			if (pAdapter->SendTxWaitQueue.Number > 0)
			{
				RTUSBDeQueuePacket(pAdapter);
			}
		}
		else
		{
			if ((!RTMP_TEST_FLAG(pAdapter, fRTMP_ADAPTER_RESET_IN_PROGRESS)) &&
				(!RTMP_TEST_FLAG(pAdapter, fRTMP_ADAPTER_HALT_IN_PROGRESS)) &&
				(!RTMP_TEST_FLAG(pAdapter, fRTMP_ADAPTER_REMOVE_IN_PROGRESS)) &&
				(!RTMP_TEST_FLAG(pAdapter, fRTMP_ADAPTER_BULKOUT_RESET)))
			{
				FREE_TX_RING(pAdapter, pTxContext);
				// Indicate next one is frag data which has highest priority
				RTUSB_SET_BULK_FLAG(pAdapter, fRTUSB_BULK_OUT_DATA_FRAG);
			}
			else
			{
				while (pTxContext->LastOne != TRUE)
				{
					FREE_TX_RING(pAdapter, pTxContext);
					pTxContext = &(pAdapter->TxContext[pAdapter->NextBulkOutIndex]);
				}
				
				FREE_TX_RING(pAdapter, pTxContext);
			}
		}
 	}
	NdisAcquireSpinLock(&pAdapter->BulkOutLock);
	pAdapter->BulkOutPending = FALSE;
	NdisReleaseSpinLock(&pAdapter->BulkOutLock);
	// Always call Bulk routine, even reset bulk.
	// The protectioon of rest bulk should be in BulkOut routine
	RTUSBKickBulkOut(pAdapter);

	
}

VOID  RTUSBBulkOutNullFrameComplete(purbb_t pUrb,struct pt_regs *pt_regs)
{
	PRT2570ADAPTER	pAdapter;
	PTX_CONTEXT	pNullContext;
	NTSTATUS		status;
	
	pNullContext= (PTX_CONTEXT)pUrb->context;
	pAdapter = pNullContext->pAdapter;

	DBGPRINT_RAW(RT_DEBUG_INFO, "--->RTUSBBulkOutNullFrameComplete\n");

	// Reset Null frame context flags
	pNullContext->IRPPending = FALSE;
	pNullContext->InUse = FALSE;
	// Clear Null frame bulk flag
	RTUSB_CLEAR_BULK_FLAG(pAdapter, fRTUSB_BULK_OUT_DATA_NULL);

	status = pUrb->status;
	if (status == USB_ST_NOERROR)
	{
		// Don't worry about the queue is empty or not, this function will check itself
		RTUSBDeQueuePacket(pAdapter);
	}
	else
	{
		if ((!RTMP_TEST_FLAG(pAdapter, fRTMP_ADAPTER_RESET_IN_PROGRESS)) &&
			(!RTMP_TEST_FLAG(pAdapter, fRTMP_ADAPTER_HALT_IN_PROGRESS)) &&
			(!RTMP_TEST_FLAG(pAdapter, fRTMP_ADAPTER_REMOVE_IN_PROGRESS)) &&
			(!RTMP_TEST_FLAG(pAdapter, fRTMP_ADAPTER_BULKOUT_RESET)))
		{
			DBGPRINT_RAW(RT_DEBUG_ERROR, "Bulk Out Null Frame Failed\n");
			RTMP_SET_FLAG(pAdapter, fRTMP_ADAPTER_BULKOUT_RESET);
			RTUSBEnqueueInternalCmd(pAdapter, RT_OID_USB_RESET_BULK_OUT);
		}
	}

	NdisAcquireSpinLock(&pAdapter->BulkOutLock);
	pAdapter->BulkOutPending = FALSE;
	NdisReleaseSpinLock(&pAdapter->BulkOutLock);

	// Always call Bulk routine, even reset bulk.
	// The protectioon of rest bulk should be in BulkOut routine
	RTUSBKickBulkOut(pAdapter);

	DBGPRINT_RAW(RT_DEBUG_INFO, "<---RTUSBBulkOutNullFrameComplete\n");

}

VOID	RTUSBBulkOutMLMEPacketComplete(purbb_t pUrb,struct pt_regs *pt_regs)
{
	PTX_CONTEXT			pMLMEContext;
	PRT2570ADAPTER		pAdapter;
	NTSTATUS		status;

	pMLMEContext= (PTX_CONTEXT)pUrb->context;
	pAdapter = pMLMEContext->pAdapter;
	status = pUrb->status;

	pAdapter->PrioRingTxCnt--;
	pAdapter->PrioRingFirstIndex++;
	if (pAdapter->PrioRingFirstIndex >= PRIO_RING_SIZE)
	{
		pAdapter->PrioRingFirstIndex = 0;
	}	

	DBGPRINT(RT_DEBUG_TRACE, ":: = %d,  = %d,   = %d,   = %d,   = %d\n", 
			pAdapter->PrioRingFirstIndex, 
			pAdapter->PrioRingTxCnt, pAdapter->PopMgmtIndex, pAdapter->PushMgmtIndex, pAdapter->NextMLMEIndex);
	
	// Reset MLME context flags
	pMLMEContext->IRPPending 	= FALSE;
	pMLMEContext->InUse 		= FALSE;
	
	if (status == STATUS_SUCCESS)
	{
		// Don't worry about the queue is empty or not, this function will check itself
		RTUSBDequeueMLMEPacket(pAdapter);
	}
#if 0
	else if (status != STATUS_CANCELLED)
	{
		if ((!RTMP_TEST_FLAG(pAdapter, fRTMP_ADAPTER_RESET_IN_PROGRESS)) &&
			(!RTMP_TEST_FLAG(pAdapter, fRTMP_ADAPTER_HALT_IN_PROGRESS)) &&
			(!RTMP_TEST_FLAG(pAdapter, fRTMP_ADAPTER_REMOVE_IN_PROGRESS)) &&
			(!RTMP_TEST_FLAG(pAdapter, fRTMP_ADAPTER_BULKOUT_RESET)))
		{
			DBGPRINT_RAW(RT_DEBUG_ERROR, "Bulk Out MLME Failed\n");
			RTMP_SET_FLAG(pAdapter, fRTMP_ADAPTER_BULKOUT_RESET);
			RTUSBEnqueueInternalCmd(pAdapter, RT_OID_USB_RESET_BULK_OUT);
		}
	}
#endif
	NdisAcquireSpinLock(&pAdapter->BulkOutLock);
	pAdapter->BulkOutPending = FALSE;
	NdisReleaseSpinLock(&pAdapter->BulkOutLock);

	// Always call Bulk routine, even reset bulk.
	// The protectioon of rest bulk should be in BulkOut routine
	RTUSBKickBulkOut(pAdapter);

	DBGPRINT_RAW(RT_DEBUG_INFO, "<---RTUSBBulkOutMLMEPacketComplete\n");

}

/*
	========================================================================

	Routine Description:
		This routine process Rx Irp and call rx complete function.
		
	Arguments:
		DeviceObject	Pointer to the device object for next lower
						device. DeviceObject passed in here belongs to
						the next lower driver in the stack because we
						were invoked via IoCallDriver in USB_RxPacket
						AND it is not OUR device object
	  Irp				Ptr to completed IRP
	  Context			Ptr to our Adapter object (context specified
						in IoSetCompletionRoutine
		
	Return Value:
		Always returns STATUS_MORE_PROCESSING_REQUIRED

	Note:
		Always returns STATUS_MORE_PROCESSING_REQUIRED
	========================================================================
*/
VOID	RTUSBBulkRxComplete(purbb_t pUrb,struct pt_regs *pt_regs)
{

	PRX_CONTEXT 	pRxContext;
	PRT2570ADAPTER	pAdapter;
	NTSTATUS		status;
	
	pRxContext= (PRX_CONTEXT)pUrb->context;
	pAdapter = pRxContext->pAdapter;

	//
	// We have a number of cases:
	//		1) The USB read timed out and we received no data.
	//		2) The USB read timed out and we received some data.
	//		3) The USB read was successful and fully filled our irp buffer.
	//		4) The irp was cancelled.
	//		5) Some other failure from the USB device object.
	//
	
	//
	// Free the IRP  and its mdl because they were	alloced by us
	//
#if 0
	if ( (atomread = (atomic_read(&pRxContext->IrpLock))) == IRPLOCK_CANCE_START)
	{
		atomic_dec(&pAdapter->PendingRx);
		atomic_set(&pRxContext->IrpLock, IRPLOCK_CANCE_COMPLETE);	

⌨️ 快捷键说明

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