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

📄 rndis.c

📁 三星2410的BSP开发包
💻 C
📖 第 1 页 / 共 4 页
字号:
//	Return Value:
//
//		TRUE if successful, FALSE otherwise.
//
void
RndisSendRndisMessage(
	DWORD		dwRndisMessageType,
	DWORD		dwRequestId,
	NDIS_STATUS	NdisStatus,
	PUCHAR		pucInBuffer,
	DWORD		dwBufferLength,
	DWORD		dwUnspecified1)
{
	UINT			uiMessageSize;
	PRNDIS_MESSAGE	pRndisMessage;
	DATA_WRAPPER	* pDataWrapper;
//	BOOL bReturn;

	CELOGMSG (ZONE_RNDIS,
		(TEXT("RNdis:: Create [%s] InBuff[0x%x] Size[%d] Unspec[%d]\r\n"),
		dwRndisMessageType == REMOTE_NDIS_INITIALIZE_CMPLT	? 
			TEXT("INIT-CMPLT") :
		dwRndisMessageType == REMOTE_NDIS_QUERY_CMPLT		? 
			TEXT("QUERY-CMPLT"):
		dwRndisMessageType == REMOTE_NDIS_SET_CMPLT			? 
			TEXT("SET-CMPLT")  :
		dwRndisMessageType == REMOTE_NDIS_RESET_CMPLT		? 
			TEXT("RESET-CMPLT"):
		dwRndisMessageType == REMOTE_NDIS_KEEPALIVE_CMPLT	? 
			TEXT("KEEPALIVE-CMPLT") : TEXT("UNKNOWN!"),
		pucInBuffer,
		dwBufferLength,
		dwUnspecified1));
/*
	pDataWrapper = ALLOCATE_DATA_WRAPPER();
	if (pDataWrapper == NULL)
	{
		//
		//	We run out of memory, so can't reply.  Just return.
		//	

		CELOGMSG (ZONE_ERROR, 
			(TEXT("RNdis:: No mem in RndisSendRndisMessage()\r\n")));
		return;
	}
*/	
	switch (dwRndisMessageType)
	{
		////////////////////////////////////////////////////////////////////////

		case REMOTE_NDIS_INITIALIZE_CMPLT:
		{
			PRNDIS_INITIALIZE_COMPLETE	pInitComplete;

			uiMessageSize = RNDIS_MESSAGE_SIZE(RNDIS_INITIALIZE_COMPLETE);	
			if (!(uiMessageSize<=MAX_PACKET_SIZE))
				EdbgOutputDebugString("ASSERT Fail at uiMessageSize(%d)<=MAX_PACKET_SIZE(%d)\r\n",
					uiMessageSize,MAX_PACKET_SIZE);
			//
			//	No extra buffer needed.
			//	AFListOffset and AFListSize don't seem to be needed.
			//	so let's just create the buffer and have it sent..
			//

			pDataWrapper = (DATA_WRAPPER *)AllocBuffer (&MsgBufferDesc, (WORD)(uiMessageSize+sizeof(DATA_WRAPPER))) ;//LocalAlloc(0, uiMessageSize);
			if (pDataWrapper == NULL)
			{
				EdbgOutputDebugString("RNdis:: No mem for INITIALIZE_COMPLETE.\r\n");			
				return;
			}
			pRndisMessage = (PRNDIS_MESSAGE)(pDataWrapper+1);
			//
			//	Have the buffer, fill it in now..
			//

			pRndisMessage->NdisMessageType = dwRndisMessageType;
			pRndisMessage->MessageLength   = uiMessageSize;		

			pInitComplete = &(pRndisMessage->Message.InitializeComplete);
			
			pInitComplete->RequestId			 = dwRequestId;
			pInitComplete->Status				 = NdisStatus;
			pInitComplete->MajorVersion			 = SUPPORTED_RNDIS_MAJOR_VER;
			pInitComplete->MinorVersion			 = SUPPORTED_RNDIS_MINOR_VER;
			pInitComplete->DeviceFlags			 = RNDIS_DF_CONNECTIONLESS;
			pInitComplete->Medium				 = 0x00;	
			pInitComplete->MaxPacketsPerMessage	 = RNDIS_MAX_PACKETS_PER_MESSAGE;			
			pInitComplete->AFListOffset			 = 0x00;	
			pInitComplete->AFListSize			 = 0x00;			
			pInitComplete->MaxTransferSize		 = RndisMdd.dwDeviceMaxRx;

			//
			//	 8 byte alignment, to cater for non x86 devices..
			//
			
			pInitComplete->PacketAlignmentFactor = 0x03;	

			CELOGMSG(1,
				(TEXT("RndisSendRndisMessage():: RNDIS_INIT_COMPLETE..\r\n")));

			break;
		}
		
		
		////////////////////////////////////////////////////////////////////////
		
		case REMOTE_NDIS_QUERY_CMPLT:
		{
			PRNDIS_QUERY_COMPLETE	pQueryComplete;
			PUCHAR					pucBuffer;			
			UINT					uiRndisQuerySize;

			uiRndisQuerySize = RNDIS_MESSAGE_SIZE(RNDIS_QUERY_COMPLETE);			
			uiMessageSize	 = uiRndisQuerySize + dwBufferLength;
			if (!(uiMessageSize<=MAX_PACKET_SIZE))
				EdbgOutputDebugString("ASSERT Fail at uiMessageSize(%d)<=MAX_PACKET_SIZE(%d)\r\n",
					uiMessageSize,MAX_PACKET_SIZE);
			
			//
			//	Extra space for queried information to be returned.
			//

			pDataWrapper = (DATA_WRAPPER *)AllocBuffer (&MsgBufferDesc, (WORD)(sizeof(DATA_WRAPPER)+uiMessageSize)) ;//LocalAlloc(0, uiMessageSize);
			if (pDataWrapper == NULL)
			{
				EdbgOutputDebugString("RNdis:: No mem for INITIALIZE_COMPLETE.\r\n");			
				return;
			}
			pRndisMessage = (PRNDIS_MESSAGE)(pDataWrapper+1);

			pucBuffer = (PUCHAR)pRndisMessage + uiRndisQuerySize;

//			CELOGMSG (0, 
//				(TEXT("uiMessageSize = [%d] - dwBufferLength = [%d]\r\n"),
//				uiMessageSize,
//				dwBufferLength));


			//
			//	Have the buffer will fill now..
			//

			pRndisMessage->NdisMessageType = dwRndisMessageType;
			pRndisMessage->MessageLength   = uiMessageSize;		

			pQueryComplete = &(pRndisMessage->Message.QueryComplete);
			
			pQueryComplete->RequestId				= dwRequestId;			
			pQueryComplete->Status					= NdisStatus;
			pQueryComplete->InformationBufferLength	= dwUnspecified1;			

//			CELOGMSG (0, (TEXT("dwBufferLength = [%d]\r\n"),
//				dwBufferLength));

			pQueryComplete->InformationBufferOffset	= 
				(dwBufferLength == 0) ? 
					(0) : 
					(pucBuffer - (PUCHAR)pQueryComplete);			

			if (dwBufferLength)				
				memcpy(pucBuffer, pucInBuffer, dwUnspecified1);

			break;
		}

		////////////////////////////////////////////////////////////////////////		
		//	Both messages have same entries..
		//	They are only interested in NdisStatus..
		//

		case REMOTE_NDIS_KEEPALIVE_CMPLT:
		case REMOTE_NDIS_SET_CMPLT:
		{
			PRNDIS_KEEPALIVE_COMPLETE	pKeepAliveOrSetComplete;

			uiMessageSize = RNDIS_MESSAGE_SIZE(RNDIS_KEEPALIVE_COMPLETE);	
			if (!(uiMessageSize<=MAX_PACKET_SIZE))
				EdbgOutputDebugString("ASSERT Fail at uiMessageSize(%d)<=MAX_PACKET_SIZE(%d)\r\n",
					uiMessageSize,MAX_PACKET_SIZE);

			pDataWrapper = (DATA_WRAPPER *)AllocBuffer (&MsgBufferDesc, (WORD)(sizeof(DATA_WRAPPER)+uiMessageSize)) ;//LocalAlloc(0, uiMessageSize);
			if (pDataWrapper == NULL)
			{
				EdbgOutputDebugString("RNdis:: No mem for INITIALIZE_COMPLETE.\r\n");			
				return;
			}
			pRndisMessage = (PRNDIS_MESSAGE)(pDataWrapper+1);

			pRndisMessage->NdisMessageType = dwRndisMessageType;
			pRndisMessage->MessageLength   = uiMessageSize;

			pKeepAliveOrSetComplete = &(pRndisMessage->Message.KeepaliveComplete);

			pKeepAliveOrSetComplete->RequestId = dwRequestId;
			pKeepAliveOrSetComplete->Status    = NdisStatus;
			break;
		}


		////////////////////////////////////////////////////////////////////////

		case REMOTE_NDIS_RESET_CMPLT:
		{
			PRNDIS_RESET_COMPLETE	pResetComplete;

			uiMessageSize = RNDIS_MESSAGE_SIZE(RNDIS_KEEPALIVE_COMPLETE);	
			if (!(uiMessageSize<=MAX_PACKET_SIZE))
				EdbgOutputDebugString("ASSERT Fail at uiMessageSize(%d)<=MAX_PACKET_SIZE(%d)\r\n",
					uiMessageSize,MAX_PACKET_SIZE);
			pDataWrapper = (DATA_WRAPPER *)AllocBuffer (&MsgBufferDesc, (WORD)(sizeof(DATA_WRAPPER)+uiMessageSize)) ;//LocalAlloc(0, uiMessageSize);
			if (pDataWrapper == NULL)
			{
				EdbgOutputDebugString("RNdis:: No mem for INITIALIZE_COMPLETE.\r\n");			
				return;
			}
			pRndisMessage = (PRNDIS_MESSAGE)(pDataWrapper+1);

			pRndisMessage->NdisMessageType = dwRndisMessageType;
			pRndisMessage->MessageLength   = uiMessageSize;

			pResetComplete = &(pRndisMessage->Message.ResetComplete);

			//
			//	Reset is always successful..
			//	We always require host to return the multicast list etc..
			//

			pResetComplete->Status			= NDIS_STATUS_SUCCESS;			
			pResetComplete->AddressingReset = 0x01;						
			break;
		}
		
		////////////////////////////////////////////////////////////////////////

		default:
			EdbgOutputDebugString("RNdis:: Should not happen!\r\n");			
			//ASSERT(0);
			//FREE_DATA_WRAPPER(pDataWrapper);
			return;
	}


	//
	//	Send it out..
	//	Buffer will return back to us and freed in 
	//	MddSendRndisMessageComplete()
	//
	pDataWrapper->Link.Flink= pDataWrapper->Link.Blink=NULL;
	pDataWrapper->pucData	 = (PUCHAR)pRndisMessage;
	pDataWrapper->dwDataSize = uiMessageSize;
	//PDD_SendRndisMessage(pDataWrapper);
	RndisMdd.PddCharacteristics.SendRndisMessageHandler(pDataWrapper);
//	CELOGMSG (ZONE_MEM,
//		(TEXT("**> RndisMsg send        :: buff[0x%x] l[%d] Wrap[0x%x]\r\n"),
//		pDataWrapper->pucData,
//		pDataWrapper->dwDataSize,
//		pDataWrapper));
/*
	{
		DWORD dwStartSec=OEMEthGetSecs();
		bReturn=FALSE;
		do
		{	
			//
			//	PDD is idling, kick start the sending process..
			//
			if (PDD_SendRndisMessage(&DataWrapper)) {
				bReturn = TRUE;

			}
			PDD_ISR();
		}while (!bReturn && (OEMEthGetSecs()- dwStartSec <1));

		if (bReturn) { //
			while (!PDD_IsMessageSend() && (OEMEthGetSecs()- dwStartSec <1));
				PDD_ISR();
		}
	};
	if (!bReturn)
		EdbgOutputDebugString("ASSERT Return(%d)\r\n",bReturn);
*/
//	ASSERT(bReturn);

}	//	RndisSendRndisMessage()



////////////////////////////////////////////////////////////////////////////////
//	RndisProcessMessage()
//	
//	Routine Description:
//
//		This function process RNDIS message received.  
//	
//	Arguments:
//
//		None.
//
//	Return Value:
//
//		TRUE if successful, FALSE otherwise.
//
void
RndisProcessMessage(PDATA_WRAPPER pDataWrapper)
{
	PRNDIS_MESSAGE	pRndisMessage;

//	CELOGMSG(0, 
//		(TEXT("RNdis:: RndisProcessOneMessage().\r\n")));

	#if 0
		DumpMemory(	
			pDataWrapper->pucData,
			pDataWrapper->dwDataSize);
	#endif

	pRndisMessage = (PRNDIS_MESSAGE) pDataWrapper->pucData;
	
	CELOGMSG (ZONE_RNDIS,
		(TEXT("RNdis:: Processing RndisMessage [%s] - Length [%d]\r\n"),
		pRndisMessage->NdisMessageType == REMOTE_NDIS_INITIALIZE_MSG	  ? 
				TEXT("RNDIS_INITIALIZE") : 
		pRndisMessage->NdisMessageType == REMOTE_NDIS_HALT_MSG			  ? 
				TEXT("RNDIS_HALT")       :
		pRndisMessage->NdisMessageType == REMOTE_NDIS_QUERY_MSG			  ? 
				TEXT("RNDIS_QUERY")      :
		pRndisMessage->NdisMessageType == REMOTE_NDIS_SET_MSG			  ?
				TEXT("RNDIS_SET")		 :
		pRndisMessage->NdisMessageType == REMOTE_NDIS_RESET_MSG			  ? 
				TEXT("RNDIS_RESET")      :
		pRndisMessage->NdisMessageType == REMOTE_NDIS_PACKET_MSG		  ? 
				TEXT("RNDIS_PACKET")   :
		pRndisMessage->NdisMessageType == REMOTE_NDIS_INDICATE_STATUS_MSG ? 
				TEXT("RNDIS_INDICATE")   :
		pRndisMessage->NdisMessageType == REMOTE_NDIS_KEEPALIVE_MSG		  ? 
			TEXT("RNDIS_KEEPALIVE")		 : 		
		TEXT("UNKNOWN!"),
		pRndisMessage->MessageLength));

/*	
	CELOGMSG (0, 
		(TEXT("RNdis:: Wrapper[0x%x] - Buffer[0x%x] l=[%d]!\r\n"),		
		pDataWrapper,
		pDataWrapper->pucData,
		pDataWrapper->dwDataSize));	
*/	

	switch (pRndisMessage->NdisMessageType)
	{
		case REMOTE_NDIS_INITIALIZE_MSG:
		{
			PRNDIS_INITIALIZE_REQUEST	pInitializeRequest;
			NDIS_STATUS					NdisStatus;
//			HANDLE						hThread;

			pInitializeRequest = &pRndisMessage->Message.InitializeRequest;

			CELOGMSG (ZONE_RNDIS,
				(TEXT("RNdis:: ReqID[0x%x] - Ver[%d-%d] - MaxXfer[%d]\r\n"),
				pInitializeRequest->RequestId,
				pInitializeRequest->MajorVersion,
				pInitializeRequest->MinorVersion,
				pInitializeRequest->MaxTransferSize));

			//
			//	We support SUPPORTED_RNDIS_MAJOR_VERSION, so bail out if 
			//	it's not.			
			//

			if (pInitializeRequest->MajorVersion > SUPPORTED_RNDIS_MAJOR_VER  ||
				(pInitializeRequest->MajorVersion == SUPPORTED_RNDIS_MAJOR_VER &&
				 pInitializeRequest->MinorVersion > SUPPORTED_RNDIS_MINOR_VER))
			{
				CELOGMSG (ZONE_RNDIS,
					(TEXT("RNdisMini Err!! unsupported RNDIS host ver.\r\n")));
				
				EdbgOutputDebugString("RNDISMINI Err!! unsupported RNDIS host ver.\r\n");

				NdisStatus = NDIS_STATUS_FAILURE;				
			}
			else
			{
				ULONG	ulRequiredLength;				

				//
				//	The very first business is to make sure we are all in the 
				//	INIT state (i.e MDD & PDD).
				//	The reason is we may get this message at anytime even during
				//	initialized stated.
				//	For example this may happen when PDD stalls one of the end 
				//	point when it encounters error..  
				//  or when RNDIS host does not receive KEEP_ALIVE return within
				//	a specified period of time..
				//				

				if (RndisMdd.dwDeviceState != RNDIS_UNINITIALIZED)
				{
					//
					//	This will put us back to RNDIS_UNINITIALIZED state.
					//
					CELOGMSG (ZONE_RNDIS,(TEXT("ERROR! RndisInitialize msg received!!! \r\n")));
					
					EdbgOutputDebugString("ERROR! RndisInitialize msg received!!! \r\n");

					//
					//	Well, DeInitialize RNDISMINI1 if necessary, but don't 
					//	hard reset PDD..
					//

					RndisRestart(FALSE);
				}

				//ASSERT(RndisMdd.dwDeviceState == RNDIS_UNINITIALIZED);
				if (!(RndisMdd.dwDeviceState == RNDIS_UNINITIALIZED))
					EdbgOutputDebugString("ASSERT at File(%s) line (%d)\r\n",__THIS_FILE__, __LINE__);

				//
				//	Okay, we are in business.
				//	Initialize all we need, and return a reply..
				//

				NdisStatus = NDIS_STATUS_SUCCESS;				


				//
				//	Remember HOST's MAX RX.				
				//			

				RndisMdd.dwHostMaxRx = pInitializeRequest->MaxTransferSize;

				//
				//	Alloc memory for it, free the previous allocated chunk..
				//
/*
				if (RndisMdd.pucTxBuffer)
					LocalFree(RndisMdd.pucTxBuffer);

				RndisMdd.pucTxBuffer = LocalAlloc(0, RndisMdd.dwHostMaxRx);

				if (RndisMdd.pucTxBuffer == NULL)
				{
					CELOGMSG (ZONE_ERROR, 
						(TEXT("RNdis:: Error, No mem for TX buff..\r\n")));				

					NdisStatus = NDIS_STATUS_FAILURE;
				}
*/				

				//
				//	Get PDD's maximum RX buffer.
				//	

				if (NdisStatus == NDIS_STATUS_SUCCESS &&
					//!PDD_Get(
					!RndisMdd.PddCharacteristics.GetHandler(
						REQ_ID_DEVICE_MAX_RX,
						&(RndisMdd.dwDeviceMaxRx),
						sizeof(RndisMdd.dwDeviceMaxRx),
						&ulRequiredLength))
				{
					//
					//	This should never happen!!
					//	a DWORD should be enough..
					//

					EdbgOutputDebugString("ASSERT at File(%s) line (%d)\r\n",__THIS_FILE__, __LINE__);
					NdisStatus = NDIS_STATUS_FAILURE;
				}


				EdbgOutputDebugString("RndisMdd:: PDD's max RX buffer = [%d] bytes.\r\n",RndisMdd.dwDeviceMaxRx);				
			}


			//
			//	Send the reply out..
			//

			CELOGMSG (ZONE_RNDIS, 
				(TEXT("Send InitializeComplete Status[0x%x] ID[0x%x]\r\n"),
				NdisStatus,
				pInitializeRequest->RequestId));
			
			RndisSendRndisMessage(
				REMOTE_NDIS_INITIALIZE_CMPLT,
				pInitializeRequest->RequestId,					
				NdisStatus,
				NULL,
				0x00,
				0x00);

			RndisMdd.dwDeviceState = RNDIS_INITIALIZED;

⌨️ 快捷键说明

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