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

📄 mass_bulktrance.c

📁 ARM读写U盘驱动软件包源程序
💻 C
字号:
/****************************************Copyright (c)**************************************************
**                               Guangzou ZLG-MCU Development Co.,LTD.
**                                     graduate school
**                                 http://www.zlgmcu.com
**
**--------------File Info-------------------------------------------------------------------------------
** File Name:
** Last modified Date: 2005-04-22
** Last Version: V1.0 
** Description: 
**
**------------------------------------------------------------------------------------------------------
** Created By: Lishan Zhou
** Created date: 2005-04-22
** Version: V1.0 
** Description:
**
**------------------------------------------------------------------------------------------------------
** Modified by:
** Modified date:
** Version:
** Description:
**
********************************************************************************************************/

#include "HostStack.h"

uint8 BulkGetCSWStatus(transfer_instance *Bulk_tr_In_Ptr,  uint8 *CBW_BuffPtr);
void BulkCBWSet(	uint8 *CBW_BuffPtr,
					uint32 DataTransferLength,
					uint8 CBWFlags, 
					uint8 bCBW_LUN,
					uint8 CBWCBLength,
					uint8 *RBC_BuffPtr);
uint8 BulkCommand_handle(	MassStorageClass *MSC_ptr,
								uint8		*CBW_BuffPtr,
								uint8		*Data_BuffPtr,
								uint8		Tr_Direction,
								uint16		*transfer_size);



unsigned char MassStorageReset(device_instance * DevicePtr)
{
	unsigned char None 		=0;
	USB_Device_Request		req;		
	unsigned short			err;

	req.bmRequestType		= 0x21;				
	req.bRequest			= 0xff;
	req.wValue				= 0;
	req.wIndex				= 0;
	req.wLength			= 0;
	err = control_transfer( &req, DevicePtr, &None );		
	return 	(err ? FALSE : TRUE);
}


unsigned char GetMaxLUN(device_instance * DevicePtr)
{
	unsigned char MaxLUN	 =0;
	USB_Device_Request	req;						
	req.bmRequestType	= 0xa1;					
	req.bRequest			= 0xfe;
	req.wValue			= 0;
	req.wIndex			= 0;
	req.wLength			= 1;
	if ( control_transfer( &req, DevicePtr, &MaxLUN ) )		
		return 	( 0xff );
	return 	(MaxLUN);
}


uint8 ResetRecovery(device_instance * dvi_ptr)
{
	endpoint_info *epi_ptr;
	if(FALSE == MassStorageReset(dvi_ptr))			
		return FALSE;
	epi_ptr = find_endport_type(dvi_ptr, Ep_TransferType_Bulk, Ep_Direction_IN_ENDPOINT, 1);
	if(FALSE == ClearEndpointSTALL( dvi_ptr,  epi_ptr))	
		return FALSE;
	epi_ptr = find_endport_type(dvi_ptr, Ep_TransferType_Bulk, Ep_Direction_OUT_ENDPOINT, 1);		
	if(FALSE == ClearEndpointSTALL( dvi_ptr,  epi_ptr))	
		return FALSE;
	return TRUE;
}





uint8 BulkOnlyComHandle(TR_With_RBC *tr_with_rbc_ptr)
{
	uint8		CSWStatus;

	BulkCBWSet(	tr_with_rbc_ptr->MSC->CBW_BuffPtr,
				tr_with_rbc_ptr->DataTransferLength,
				tr_with_rbc_ptr->TrDirection,
				tr_with_rbc_ptr->LUN,
				tr_with_rbc_ptr->CBLength,
				tr_with_rbc_ptr->MSC->RBC_BuffPtr
				);
	CSWStatus = BulkCommand_handle( tr_with_rbc_ptr->MSC,
									  tr_with_rbc_ptr->MSC->CBW_BuffPtr, 
									  tr_with_rbc_ptr->Data_BuffPtr, 
									  tr_with_rbc_ptr->TrDirection, 
									  &tr_with_rbc_ptr->DataTransferLength);

	if( CSWStatus == FALSE )
		return PERSISTENT_FAILURE;


	CSWStatus = BulkGetCSWStatus(	tr_with_rbc_ptr->MSC->tr_bulk_in_ptr, 
									tr_with_rbc_ptr->MSC->CBW_BuffPtr);


	if(CSWStatus == COMMAND_PASSED)
		return COMMAND_PASSED;

	if((CSWStatus == 0xff)||(CSWStatus == PHASE_ERROR))
	{	
		if( FALSE == ResetRecovery(tr_with_rbc_ptr->MSC->dvi_ptr))
			return PERSISTENT_FAILURE;			
		
		return PHASE_ERROR;
	}

	if(CSWStatus == COMMAND_FAILED)
		return COMMAND_FAILED;
		
	return PERSISTENT_FAILURE;
}



uint8 BulkCommand_handle(	MassStorageClass *MSC_ptr,
								uint8		*CBW_BuffPtr,
								uint8		*Data_BuffPtr,
								uint8		Tr_Direction,
								uint16		*transfer_size)
{
	uint8			Completion_Code;
	uint16			CBW_size;
	device_instance 	*dvi_ptr;
	endpoint_info 		*epi_ptr;


	CBW_size = 31;				
	Completion_Code = bulk_transaction( DirectionPID_OUT, CBW_BuffPtr, &CBW_size, MSC_ptr->tr_bulk_out_ptr);
	if(Completion_Code)
		return FALSE;			
	if(Tr_Direction == IN_DATA)
		Completion_Code = bulk_transaction(DirectionPID_IN,Data_BuffPtr, transfer_size, MSC_ptr->tr_bulk_in_ptr);
	if(Tr_Direction ==OUT_DATA)
		Completion_Code = bulk_transaction(DirectionPID_OUT,Data_BuffPtr, transfer_size, MSC_ptr->tr_bulk_out_ptr);
	if(Completion_Code)
	{
		if(Completion_Code == 0x04)		
		{
			if(Tr_Direction == IN_DATA)	
			{
				epi_ptr = MSC_ptr->tr_bulk_in_ptr->epi_ptr;			
				dvi_ptr = MSC_ptr->dvi_ptr;	
				return ClearEndpointSTALL( dvi_ptr, epi_ptr);
			}

			if(Tr_Direction ==OUT_DATA)	
			{
				epi_ptr = MSC_ptr->tr_bulk_out_ptr->epi_ptr;			
				dvi_ptr = MSC_ptr->dvi_ptr;	
				return ClearEndpointSTALL( dvi_ptr, epi_ptr);
			}
		}
		if(Completion_Code == 0x09)	
			return TRUE;			
	}
	return TRUE;					
}


uint8 BulkGetCSWStatus(transfer_instance *Bulk_tr_In_Ptr,  uint8 *CBW_BuffPtr)
{
	#define CSW_LENGTH		13
	COMMAND_STATUS_WRAPPER	CSWB;
	uint8	CSWStatus;
	uint16	transfer_size = CSW_LENGTH;
	uint32	dCSWDataResidue;
	uint32	dCBW_DataXferLen;
	COMMAND_BLOCK_WRAPPER *CBW_ptr;

	CBW_ptr = (COMMAND_BLOCK_WRAPPER *) CBW_BuffPtr;
	CSWStatus = bulk_transaction(DirectionPID_IN, (uint8 *)&CSWB, 
							     &transfer_size,  Bulk_tr_In_Ptr);
	
	if(CSWStatus==NULL)
	{
		
		if(transfer_size == CSW_LENGTH)
			if((CSWB.dCSW_Signature_0==0x55)&&
				(CSWB.dCSW_Signature_1==0x53)&&
				(CSWB.dCSW_Signature_2==0x42)&&
				(CSWB.dCSW_Signature_3==0x53)&&
				(CSWB.dCSW_Tag == CBW_ptr->dCBW_Tag))
			{	
				if(CSWB.bCSW_Status==PHASE_ERROR)
					return (PHASE_ERROR);
				if(CSWB.bCSW_Status < PHASE_ERROR)
				{
					dCSWDataResidue = CSWB.dCSW_DataResidue_0+
									   CSWB.dCSW_DataResidue_1*0x100+
									   CSWB.dCSW_DataResidue_2*0x10000+
									   CSWB.dCSW_DataResidue_3*0x1000000;
					dCBW_DataXferLen =  CBW_ptr->dCBW_DataXferLen_0+
									     CBW_ptr->dCBW_DataXferLen_1*0x100+
									     CBW_ptr->dCBW_DataXferLen_2*0x10000+
									     CBW_ptr->dCBW_DataXferLen_3*0x1000000;
					if(dCSWDataResidue <= dCBW_DataXferLen)
						return CSWB.bCSW_Status;
				}	
				
			}
	}
	return (0xff);
}
	

void BulkCBWSet(	uint8 *CBW_BuffPtr,
					uint32 DataTransferLength,
					uint8 CBWFlags, 
					uint8 bCBW_LUN,
					uint8 CBWCBLength,
					uint8 *RBC_BuffPtr)
{
	COMMAND_BLOCK_WRAPPER *CBW_ptr;
	uint8 *RBC_in_CBW_ptr;
	CBW_ptr = (COMMAND_BLOCK_WRAPPER *) CBW_BuffPtr;
	
	CBW_ptr->dCBW_Tag ++;
	CBW_ptr->dCBW_DataXferLen_0 = (uint8)DataTransferLength;
	CBW_ptr->dCBW_DataXferLen_1 = (uint8)(DataTransferLength/0x100);
	CBW_ptr->dCBW_DataXferLen_2 = (uint8)(DataTransferLength/0x10000);
	CBW_ptr->dCBW_DataXferLen_3 = (uint8)(DataTransferLength/0x1000000);
	CBW_ptr->bCBW_Flag = (CBWFlags == OUT_DATA)? 0x00 :0x80 ;
	CBW_ptr->bCBW_LUN = bCBW_LUN;
	CBW_ptr->bCBW_CDBLength = CBWCBLength;

	RBC_in_CBW_ptr = &CBW_ptr->bCBW_CDBLength +1;
	memset(RBC_in_CBW_ptr,0,16);
	memcpy( RBC_in_CBW_ptr , RBC_BuffPtr, CBWCBLength );
}




⌨️ 快捷键说明

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