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

📄 cmdproc.c

📁 Windows CE 6.0 BSP for VOIP sample phone. Intel PXA270 platform.
💻 C
📖 第 1 页 / 共 2 页
字号:
//
// Copyright (c) Microsoft Corporation.  All rights reserved.
//
//
// Use of this sample source code is subject to the terms of the Microsoft
// license agreement under which you licensed this sample source code. If
// you did not accept the terms of the license agreement, you are not
// authorized to use this sample source code. For the terms of the license,
// please see the license agreement between you and Microsoft or, if applicable,
// see the LICENSE.RTF on your install media or the root of your tools installation.
// THE SAMPLE SOURCE CODE IS PROVIDED "AS IS", WITH NO WARRANTIES OR INDEMNITIES.
//
/** @file cmdproc.c
 *  @This module provides implementaion of host command 
 *   processing routines
 *
 *  Copyright (c) Marvell Semiconductor, Inc. 
 */
 
#include "precomp.h"

/******************************************************************************
 *
 *  Name: AllocateCmdBuffer()
 *
 *  Description: Allocate command buffer
 *
 *  Arguments:  PMRVDRV_ADAPTER Adapter
 *    
 *  Return Value: NDIS_STATUS_SUCCESS or NDIS_STATUS_RESOURCES
 * 
 *  Notes:        
 *
 *****************************************************************************/
NDIS_STATUS AllocateCmdBuffer(
	IN PMRVDRV_ADAPTER Adapter
	)
{
	NDIS_STATUS Status;
	ULONG ulBufSize;
	CmdCtrlNode *TempCmdArray;
	PUCHAR pTempVirtualAddr;
	UINT i;

	Status = NDIS_STATUS_SUCCESS;

       // return Status;

	// initialize free queue
	NdisAcquireSpinLock(&Adapter->FreeQSpinLock);
	InitializeQKeeper(&Adapter->CmdFreeQ);
	NdisReleaseSpinLock(&Adapter->FreeQSpinLock);
	
	// initialize priority queue
	NdisAcquireSpinLock(&Adapter->PriorityQSpinLock);
 
    InitializeQKeeper(&Adapter->CmdPendQ);

	NdisReleaseSpinLock(&Adapter->PriorityQSpinLock);

       // allocate the command array space  
	ulBufSize = sizeof(CmdCtrlNode) * MRVDRV_NUM_OF_CMD_BUFFER;
	//Status = MRVDRV_ALLOC_MEM((PVOID *)(&(Adapter->CmdArray)), ulBufSize);
	if( Status != NDIS_STATUS_SUCCESS )
		return Status;
	NdisZeroMemory(Adapter->CmdArray, ulBufSize);

	//DBGPRINT(DBG_LOAD, ("CmdArray = 0x%x \n", Adapter->CmdArray));
	//DBGPRINT(DBG_LOAD, ("CmdBufferArray = 0x%x \n", &(Adapter->CmdBufferArray[0][0])));

	// Allocate shared memory buffers 
	for ( i=0; i<MRVDRV_NUM_OF_CMD_BUFFER; i++ )
	{
		TempCmdArray = (CmdCtrlNode *)(&(Adapter->CmdArray[i]));
		
		//DBGPRINT(DBG_LOAD, ("CmdArray[%d] = 0x%x \n", i, TempCmdArray));

		//DBGPRINT(DBG_NEWCMD,("TempCmdArray %d 0x%x ****\n", 
		//						i, TempCmdArray));
 
              //NdisAllocateMemoryWithTag(&pTempVirtualAddr, MRVDRV_SIZE_OF_CMD_BUFFER, 'LVRM');
		//if ( !pTempVirtualAddr )
		//{	
		//	DBGPRINT(DBG_NEWCMD, ("return NDIS_STATUS_RESOURCES\n"));
		//	return NDIS_STATUS_RESOURCES;
		//}

		pTempVirtualAddr = &(Adapter->CmdBufferArray[i][0]);

		//DBGPRINT(DBG_LOAD, ("CmdBufferArray[%d] = 0x%x \n", i, pTempVirtualAddr));
		
		NdisZeroMemory(pTempVirtualAddr, MRVDRV_SIZE_OF_CMD_BUFFER);

		//DBGPRINT(DBG_LOAD, ("CmdBufferArray- 1 \n"));
		
		TempCmdArray->BufVirtualAddr	  = pTempVirtualAddr;
		TempCmdArray->BufPhyAddr.LowPart  = 0xffffffff;
		TempCmdArray->BufPhyAddr.HighPart = 0xffffffff;

		//DBGPRINT(DBG_LOAD, ("CmdBufferArray- 2 \n"));

		// insert command to free queue
		NdisAcquireSpinLock(&Adapter->FreeQSpinLock);
		CleanUpCmdCtrlNode(TempCmdArray);
		InsertQNodeAtTail(&Adapter->CmdFreeQ,(PQ_NODE) TempCmdArray);
		NdisReleaseSpinLock(&Adapter->FreeQSpinLock);

		//DBGPRINT(DBG_LOAD, ("CmdBufferArray- 3 \n"));
	}

	return Status;
}

/******************************************************************************
 *
 *  Name: FreeCmdBuffer()
 *
 *  Description: Free command buffer
 *
 *  Arguments:  PMRVDRV_ADAPTER Adapter
 *    
 *  Return Value: NDIS_STATUS_SUCCESS
 * 
 *  Notes:        
 *
 *****************************************************************************/
NDIS_STATUS FreeCmdBuffer(
	IN PMRVDRV_ADAPTER Adapter
	)
{
	//CmdCtrlNode *TempCmdArray;
  //     ULONG ulBufSize;
	//UINT i;

	// Need to check if cmd array is allocated or not
	//if ( Adapter->CmdArray == NULL )
	//	return NDIS_STATUS_SUCCESS;

	// Release shared memory buffers
	//for (i=0; i<MRVDRV_NUM_OF_CMD_BUFFER; i++)
	//{
	//	TempCmdArray = ((CmdCtrlNode*)(Adapter->CmdArray) + i);
       // 
	//	if ( TempCmdArray->BufVirtualAddr ) 
	//	{
	//		NdisFreeMemory ((PVOID)TempCmdArray->BufVirtualAddr, 
	//				MRVDRV_SIZE_OF_CMD_BUFFER, 
	//				0);
	//	}	
	//}

	//  Release CmdCtrlNode
	//if ( Adapter->CmdArray ) 
	//{
	//    ulBufSize = sizeof(CmdCtrlNode) * MRVDRV_NUM_OF_CMD_BUFFER;
	//	NdisFreeMemory((PVOID *)Adapter->CmdArray, ulBufSize, 0);
	//}

    	return NDIS_STATUS_SUCCESS;
}

/******************************************************************************
 *
 *  Name: ResetCmdBuffer()
 *
 *  Description: Reset command buffers
 *
 *  Arguments:  PMRVDRV_ADAPTER Adapter
 *    
 *  Return Value: NDIS_STATUS_SUCCESS
 * 
 *  Notes:        
 *
 *****************************************************************************/
NDIS_STATUS ResetCmdBuffer(
	IN PMRVDRV_ADAPTER Adapter
	)
{
	CmdCtrlNode *TempCmdArray;
	UINT i;
       BOOLEAN  timerStatus;
	PPENDING_OID pPending;

       DBGPRINT(DBG_CMDRESP, ("Reset CMD Buffer\n"));

	EnterCriticalSection(&Adapter->CmdQueueExeSection);

       NdisAcquireSpinLock(&Adapter->FreeQSpinLock);
		
	// Cancel command timer
	if (Adapter->CommandTimerSet)
       {		
		NdisMCancelTimer(&Adapter->MrvDrvCommandTimer, &timerStatus);
		Adapter->CommandTimerSet = FALSE;
		Adapter->isCommandTimerExpired = FALSE;	
	}

	// Reset CmdFreeQ and CmdPendingQ
	InitializeQKeeper(&Adapter->CmdFreeQ);

    InitializeQKeeper(&Adapter->CmdPendQ);

	for(i=0; i<MRVDRV_NUM_OF_CMD_BUFFER; i++)
	{
		TempCmdArray = (CmdCtrlNode*)(&(Adapter->CmdArray[i]));

		if (Adapter->bIsFreeNow == FALSE)
		{
			// If this is a pending command, return failure
			if ( TempCmdArray->PendingInfo == HostCmd_PENDING_ON_SET_OID ) 
			{
				NdisMSetInformationComplete(
					Adapter->MrvDrvAdapterHdl,
						NDIS_STATUS_SUCCESS);
			}
			else if ( TempCmdArray->PendingInfo == HostCmd_PENDING_ON_GET_OID )
			{
				NdisMQueryInformationComplete(
					Adapter->MrvDrvAdapterHdl, 
					NDIS_STATUS_SUCCESS);
			}
			
		}
		// Clean up node content
		TempCmdArray->Next = NULL;

		CleanUpCmdCtrlNode(TempCmdArray);
    
		// Append node to the end of CmdFreeQ
		InsertQNodeAtTail(&Adapter->CmdFreeQ, (PQ_NODE)(TempCmdArray));
	}

    	Adapter->CurCmd = NULL;
	Adapter->SeqNum = 0;

	if (Adapter->bIsFreeNow == FALSE)
	{
    		// return pending OIDs 
    		pPending = &(Adapter->PendingSetSssidOid);
		if (pPending->bIsPendingOID)
		{	
			pPending->bIsPendingOID = FALSE;
                	*(pPending->BytesReadWrite) = 0;
			NdisMSetInformationComplete(
						Adapter->MrvDrvAdapterHdl,
						NDIS_STATUS_SUCCESS);
		}
	}

	NdisReleaseSpinLock(&Adapter->FreeQSpinLock);

	LeaveCriticalSection(&Adapter->CmdQueueExeSection); 
	 
    	return NDIS_STATUS_SUCCESS;
}

/******************************************************************************
 *
 *  Name: GetFreeCmdCtrlNode()
 *
 *  Description: to get next available CmdCtrlNode
 *
 *  Arguments:	PMRVDRV_ADAPTER Adapter, 
 * 				ULONG CurrentPacketFilter
 *    
 *  Return Value:        
 * 
 *  Notes: 
 *
 *****************************************************************************/
CmdCtrlNode *
GetFreeCmdCtrlNode(
	IN PMRVDRV_ADAPTER Adapter
	)
{
	CmdCtrlNode *TempNode;

	if ( !Adapter )
		return NULL;

	NdisAcquireSpinLock(&Adapter->FreeQSpinLock);
	TempNode = (CmdCtrlNode *)PopFirstQNode(&Adapter->CmdFreeQ);    
	CleanUpCmdCtrlNode(TempNode);
	NdisReleaseSpinLock(&Adapter->FreeQSpinLock);

	return TempNode;
}

VOID
ReturnCmdNode(
	IN PMRVDRV_ADAPTER Adapter,
	CmdCtrlNode *TempNode
	)
{
        if ( !TempNode )
                return;
	
        NdisAcquireSpinLock(&Adapter->FreeQSpinLock);
	CleanUpCmdCtrlNode(TempNode);
	InsertQNodeAtTail(&Adapter->CmdFreeQ, (PQ_NODE)TempNode);
	NdisReleaseSpinLock(&Adapter->FreeQSpinLock);

	return;
}

/******************************************************************************
 *
 *  Name: SetCmdCtrlNode()
 *
 *  Description: to set up CmdCtrlNode
 *
 *  Arguments:	CmdCtrlNode *pTempNode
 *				NDIS_OID PendingOID
 *				USHORT PendingInfo
 *				USHORT INTOption
 *				USHORT BatchQNum
 *				BOOLEAN IsLastBatchCmd
 *				PULONG BytesWritten
 *				PULONG BytesRead
 *				PULONG BytesNeeded
 *				PVOID InformationBuffer
 *    
 *  Return Value:        
 * 
 *  Notes: 
 *
 *****************************************************************************/
VOID SetCmdCtrlNode(
	IN	PMRVDRV_ADAPTER Adapter,
	IN  CmdCtrlNode *pTempNode,
	IN  NDIS_OID PendingOID,
	IN  USHORT PendingInfo,
	IN  USHORT INTOption,
	IN  USHORT BatchQNum,
	IN  BOOLEAN IsLastBatchCmd,
	IN  PULONG BytesWritten,
	IN  PULONG BytesRead,
	IN  PULONG BytesNeeded,
	IN  PVOID InformationBuffer
	)
{
	if( !pTempNode )
		return;
	
	pTempNode->PendingOID		 = PendingOID;
	pTempNode->PendingInfo		 = PendingInfo;
	pTempNode->INTOption		 = INTOption;
	pTempNode->BatchQNum		 = BatchQNum;
	pTempNode->IsLastBatchCmd	 = IsLastBatchCmd;
	pTempNode->BytesWritten		 = BytesWritten;
	pTempNode->BytesRead		 = BytesRead;
	pTempNode->BytesNeeded	 	 = BytesNeeded;
	pTempNode->InformationBuffer 	 = InformationBuffer;
	
	return;
}
/******************************************************************************
 *
 *  Name: GetExpectedRetCode()
 *
 *  Description: 
 *
 *  Arguments:	
 *    
 *  Return Value:        
 * 
 *  Notes: 
 *
 *****************************************************************************/
USHORT 
GetExpectedRetCode(USHORT Cmd)
{
	USHORT RetCode;


	if (Cmd==HostCmd_CMD_802_11_ASSOCIATE_EXT)
		RetCode = HostCmd_RET_802_11_ASSOCIATE;
	else
		RetCode = (Cmd | 0x8000); 
   
	return RetCode;
}

/******************************************************************************
 *
 *  Name: CleanUpCmdCtrlNode()
 *
 *  Description: to clean up CmdCtrlNode
 *
 *  Arguments:	CmdCtrlNode *pTempNode
 *    
 *  Return Value:        
 * 
 *  Notes: 
 *
 *****************************************************************************/
VOID CleanUpCmdCtrlNode(
	IN  CmdCtrlNode *pTempNode
	)
{
	if( !pTempNode )
		return;

	pTempNode->Status			 = HostCmd_STATE_IDLE;
	pTempNode->PendingOID		 = (NDIS_OID)0;
	pTempNode->ExpectedRetCode	 = HostCmd_CMD_NONE;
	pTempNode->PendingInfo		 = HostCmd_PENDING_ON_NONE;
	pTempNode->INTOption		 = HostCmd_OPTION_USE_INT; // Default
	pTempNode->BatchQNum		 = 0;
	pTempNode->IsLastBatchCmd	 = FALSE;
	pTempNode->BytesWritten		 = NULL;
	pTempNode->BytesRead		 = NULL;
	pTempNode->BytesNeeded		 = NULL;
	pTempNode->InformationBuffer 	 = NULL;
    	pTempNode->Pad[0]            	 = 0;
    	pTempNode->Pad[1]            	 = 0;
    	pTempNode->Pad[2]            	 = 0;
	pTempNode->PadExt[0] 		 = 0;
	pTempNode->PadExt[0] 		 = 0;
	pTempNode->PadExt[0] 		 = 0;
	pTempNode->PadExt[0] 		 = 0;

	if( pTempNode->BufVirtualAddr != NULL )
	    NdisZeroMemory(pTempNode->BufVirtualAddr, MRVDRV_SIZE_OF_CMD_BUFFER);
	
	return;
}


VOID
InsertCmdToQueue(
	IN PMRVDRV_ADAPTER Adapter,
	IN CmdCtrlNode *pTempCmd
	)
{
  	USHORT Command;
	USHORT PsSubCommand;
       USHORT AddToQueue = 0xFFFF;

       DBGPRINT(DBG_NEWCMD, ("InsertCmdToQueue() \n"));
	//RETAILMSG(1, (TEXT("InsertCmdToQueue \r\n")));
	
  	if (!pTempCmd)
		return;
	
	EnterCriticalSection(&Adapter->CmdQueueExeSection);
	
  	Command = ((PHostCmd_DS_GEN)(pTempCmd->BufVirtualAddr))->Command;
       if ((Command == HostCmd_CMD_802_11_PS_MODE))
                PsSubCommand = ((PHostCmd_DS_802_11_PS_MODE)pTempCmd->BufVirtualAddr)->SubCommand;
       else
                PsSubCommand = 0;
    
       switch (Adapter->psState)
	{
	case PS_STATE_FULL_POWER:
                
                if ((PsSubCommand == HostCmd_SubCmd_Enter_PS) ||
                    (PsSubCommand == 0))
                    AddToQueue = 0;          
                break;

        case PS_STATE_WAKEUP:
        case PS_STATE_SLEEP:
                
                if (PsSubCommand == HostCmd_SubCmd_Exit_PS)
                    AddToQueue = 1;          
                else if (PsSubCommand == 0)
                    AddToQueue = 0;
                break;

        case PS_STATE_SLEEP_PENDING:
            
                if ((PsSubCommand == HostCmd_SubCmd_Sleep_Confirmed) ||
                    (PsSubCommand == HostCmd_SubCmd_Exit_PS))
                    AddToQueue = 1;
                else if (PsSubCommand == 0)
                    AddToQueue = 0;
		break;
    	} 

    	if (Command == HostCmd_CMD_802_11_HOST_SLEEP_AWAKE_CONFIRM)
    	{
       	AddToQueue = 1;
    	}
				
    	switch(AddToQueue)
    	{
       case 0:
	    
	    	NdisAcquireSpinLock(&Adapter->PriorityQSpinLock);
            	InsertQNodeAtTail(&(Adapter->CmdPendQ),(PQ_NODE)pTempCmd);
	    	NdisReleaseSpinLock(&Adapter->PriorityQSpinLock);
	    	break;

       case 1:
				
	    	NdisAcquireSpinLock(&Adapter->PriorityQSpinLock);
            	InsertQNodeFromHead(&(Adapter->CmdPendQ),(PQ_NODE)pTempCmd);
	    	NdisReleaseSpinLock(&Adapter->PriorityQSpinLock);
	    	break;

	default:

            	ReturnCmdNode(Adapter, pTempCmd);
		break;
    	}

    	LeaveCriticalSection(&Adapter->CmdQueueExeSection); 
	
    	return;
}

	
VOID
GetCmdFromQueueToExecute(	
	IN PMRVDRV_ADAPTER Adapter
	)
{
    CmdCtrlNode *pTempNode=NULL;
    CmdCtrlNode *pPsEnterCmd;
    CmdCtrlNode *pPsExitCmd;

    NDIS_STATUS  status;
	
    USHORT 	Command;
    USHORT 	PsSubCommand;
    USHORT      IsDownloadCmdToFW;

    DBGPRINT(DBG_NEWCMD, ("GetCmdFromQueueToExecute() \n"));
	//RETAILMSG(1, (TEXT("GetCmdFromQueueToExecute \r\n")));

    if (Adapter->CurCmd)
        return;

⌨️ 快捷键说明

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