📄 ms_bot.c
字号:
// ----------------------------------------------------------------------------
// ATMEL Microcontroller Software Support - ROUSSET -
// ----------------------------------------------------------------------------
// DISCLAIMER: CONDITIONS AS PER SIGNED LIMITED LICENSE AGREEMENT (AT91
// SOFTWARE AND USER DOCUMENTATION)
// ALL SOFTWARE IS PROVIDED AS IS, WITH ALL FAULTS, AND WITH NO WARRANTY
// WHATSOEVER. ATMEL EXPRESSLY DISCLAIMS ALL WARRANTIES, EXPRESS, IMPLIED,
// OR STATUTORY, INCLUDING WITHOUT LIMITATION ANY WARRANTIES OF MERCHANTABILITY,
// FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT.
// ----------------------------------------------------------------------------
// File Name : ms_bot.c
// Object : bot commandes (BOT: Bulk Only Transport)
// Creation : JCB 15/apr/2005
// Modif :
// ----------------------------------------------------------------------------
#include "po_types.h"
#include "trace.h"
#include "bfsa_flash.h"
#include "fw_usb.h"
#include "po_kernel.h"
#include "ms_device.h"
#include "ms_rbc.h"
USBMS_CONTEXT usbms_context;
USBMS_REQUEST_SENSE_DATA usbms_request_sense_data;
#ifdef TR_ERROR
UCHAR DBG_EVT ;
#endif
/*****************************************************************
*
* ROUTINE : ms_stallPipe
*
*-----------------------------------------------------------------
*
* Purpose : Stall the endpoind (IN, OUT, or CTRL)
*
* Input parameters : endpoint: FW_EP_CTRL, FW_EP_BULK_IN, FW_EP_BULK_OUT
*
* Output parameters : none
*
* Global data : none
*
*****************************************************************/
void ms_stallPipe( EPx ep )
{
fw_setEndpointStatus(ep, 1);
}
/*****************************************************************
*
* ROUTINE : ms_computeCSW
*
*-----------------------------------------------------------------
*
* Purpose : formats and send the BOT status
* Command Status Wrapper (CSW)
*
* Input Parameters :
* command_block_status : Status of the BOT
* data_residue : amount of data that have not been processed
*
* Output Parameters : none
*
*****************************************************************/
void ms_computeCSW( COMMAND_BLOCK_STATUS command_block_status,
ULONG data_residue )
{
/* TRACE_DEBUG_H( "ms_computeCSW\n\r");
TRACE_DEBUG_H( "Status =%d \n\r",command_block_status);
TRACE_DEBUG_H( "data residue =%d \n\r",data_residue);
*/
/* build the CSW structure */
usbms_context.csw.dCSWSignature_0 = (UCHAR)(CSW_SIGNATURE); /* 0x55; */
usbms_context.csw.dCSWSignature_1 = (UCHAR)(CSW_SIGNATURE>>8); /* 0x53; */
usbms_context.csw.dCSWSignature_2 = (UCHAR)(CSW_SIGNATURE>>16); /* 0x42; */
usbms_context.csw.dCSWSignature_3 = (UCHAR)(CSW_SIGNATURE>>24); /* 0x53; */
usbms_context.csw.dCSWDataResidue_0 = (UCHAR)(data_residue);
usbms_context.csw.dCSWDataResidue_1 = (UCHAR)(data_residue>>8);
usbms_context.csw.dCSWDataResidue_2 = (UCHAR)(data_residue>>16);
usbms_context.csw.dCSWDataResidue_3 = (UCHAR)(data_residue>>24);
usbms_context.csw.bCSWStatus = command_block_status;
/* reset the bot state */
usbms_context.usb_lun[usbms_context.current_lun].fail_reason = GOOD_STATUS;
usbms_context.usb_lun[usbms_context.current_lun].fail_request = FALSE;
}
/*****************************************************************
*
* ROUTINE : ms_send_bot_status
*
*-----------------------------------------------------------------
*
* Purpose : formats and send the BOT status
*
* Input Parameters :
* command_block_status : Status of the BOT
* data_residue : amount of data that have not been processed
*
* Output Parameters : none
*
*****************************************************************/
void ms_send_bot_status( COMMAND_BLOCK_STATUS command_block_status,
ULONG data_residue )
{
ms_computeCSW( command_block_status, data_residue );
/* sends the BOT status */
usb_send((char*)&usbms_context.csw, sizeof(USBMS_CSW));
}
/******************************************************************
*
* SUB-ROUTINE : ms_plugInit
*
*------------------------------------------------------------------
*
* purpose : Init the data structure specific to the Mass Storage driver
*
* input parameters : none
*
* output parameters : none
*
* global data :
* usbms_context
* usbms_request_sense_data
*
******************************************************************/
void ms_plugInit( void )
{
UCHAR _counter = 0;
usbms_context.usb_lun[usbms_context.current_lun].TotBlockNumber = (ULONG)NB_BLOCK;
usbms_context.usb_lun[usbms_context.current_lun].BlockSize = SIZEONESECTOR;
usbms_context.usb_lun[usbms_context.current_lun].fail_reason = 0;
usbms_context.usb_lun[usbms_context.current_lun].media_state = 0;
usbms_context.usb_lun[usbms_context.current_lun].fail_request = 0;
for( _counter=0; _counter<MAX_LUN_NUM; _counter++ )
{
usbms_context.usb_lun[_counter].media_state = 0;
}
usbms_context.state = IDLE;
/* Initialize the sense data */
usbms_request_sense_data.response_code = 0x70; /* response code : set to 0x70 */
usbms_request_sense_data.valid = 0x01; /* set to one; specifies the infirmation fields contains valid informations as defined in the scp3 standard or a command set standard*/
usbms_request_sense_data.segmentNum = 0x00; /* */
usbms_request_sense_data.sense_key = 0x00; /* generic error specified in enum T_SENSE_KEY */
usbms_request_sense_data.wrongLenIndicator = 0x00; /* */
usbms_request_sense_data.endOfMedia = 0x00; /* */
usbms_request_sense_data.filemark = 0x00; /* */
usbms_request_sense_data.information_0 = 0x00; /* */
usbms_request_sense_data.information_1 = 0x00; /* */
usbms_request_sense_data.information_2 = 0x00; /* */
usbms_request_sense_data.information_3 = 0x00; /* */
usbms_request_sense_data.additional_sense_length = sizeof(USBMS_REQUEST_SENSE_DATA)-8; /* Must be set to sizeof(T_REQUEST_SENSE_DATA)-8 */
usbms_request_sense_data.command_specific_information_0 = 0x00; /* */
usbms_request_sense_data.command_specific_information_1 = 0x00; /* */
usbms_request_sense_data.command_specific_information_2 = 0x00; /* */
usbms_request_sense_data.command_specific_information_3 = 0x00; /* */
usbms_request_sense_data.additional_sense_code = 0x00; /* ASC */
usbms_request_sense_data.additional_sense_code_qualifier = 0x00; /* ASCQ */
usbms_request_sense_data.field_replaceable_unit_code = 0x00; /* */
usbms_request_sense_data.sense_key_specific_0 = 0x00; /* */
usbms_request_sense_data.sksv = 0x00; /* sense key specific valid; set to one */
usbms_request_sense_data.sense_key_specific_1 = 0x00; /* for an accurate definition of the content */
usbms_request_sense_data.sense_key_specific_2 = 0x00; /* of this fields please refer to spc3r17, chapter 4.5.2.4 */
/* Standart INQUIRY data */
/* Fill the inquiry structure */
usbms_context.inquiry_data.device_type = 0x00; /* SBC Direct-access device (e.g., UHD Floppy disk) */
usbms_context.inquiry_data.version = 0x05; /* */
usbms_context.inquiry_data.removable = 0x01; /* We pretend that the Device is Removable, in order to get the "TEST_UNIT_READY" */
usbms_context.inquiry_data.NACA = 0x00;
usbms_context.inquiry_data.AERC = 0x00;
usbms_context.inquiry_data.Linked = 0x00;
usbms_context.inquiry_data.Synch = 0x00;
usbms_context.inquiry_data.Wide16 = 0x00;
po_memcpy( usbms_context.inquiry_data.vendor_id, VENDOR_ID, VENDOR_ID_LENGTH);
po_memcpy( usbms_context.inquiry_data.product_id, PRODUCT_ID, PRODUCT_ID_LENGTH);
po_memcpy( usbms_context.inquiry_data.product_revision_level, PRODUCT_REVISION_LEVEL, PRODUCT_REVISION_LEVEL_LENGTH);
po_memcpy( usbms_context.inquiry_data.vendor_specific, VENDOR_SPECIFIC, VENDOR_SPECIFIC_LENGTH);
po_memcpy( usbms_context.inquiry_data.version_descriptor, VERSION_DESCRIPTOR, VERSION_DESCRIPTOR_LENGTH);
}
/******************************************************************
*
* SUB-ROUTINE : ms_goToInit
*
*------------------------------------------------------------------
*
* purpose : Go to state INIT
*
* input parameters : none
*
* output parameters : none
*
* global data : usbms_context.state
*
******************************************************************/
void ms_goToInit( void )
{
/* Set state to INIT */
usbms_context.state = INIT;
}
/******************************************************************
*
* SUB-ROUTINE : ms_rstProgStallIn
*
*------------------------------------------------------------------
*
* purpose : Stall of endpoint BULK IN
*
* input parameters : none
*
* output parameters : none
*
* global data : usbms_context.state
*
******************************************************************/
void ms_rstProgStallIn( void )
{
TRACE_DEBUG_H( "St In\n\r");
/* Send the CSW using usb_send() and set state to PROCESS_CSW */
usb_send((char*)&usbms_context.csw, sizeof(USBMS_CSW));
usbms_context.state = PROCESS_CSW;
}
/******************************************************************
*
* SUB-ROUTINE : ms_rstProgStallOut
*
*------------------------------------------------------------------
*
* purpose : Stall of endpoint BULK OUT
*
* input parameters : none
*
* output parameters : none
*
* global data : usbms_context.state
*
******************************************************************/
void ms_rstProgStallOut( void )
{
TRACE_DEBUG_H( "St Out\n\r");
usbms_context.state = PROCESS_CSW;
}
/******************************************************************
*
* SUB-ROUTINE spc_update_sense_data
*
*------------------------------------------------------------------
*
* purpose : Update the sense data structure
*
* input parameters : SenseKey : Sensekey value for the Sense data.
* ASC : ASC value for the Sense data.
* ASCQ : ASCQ value for the Sense data.
*
* output parameters : none
*
* global data :
* usbms_request_sense_data.sense_key
* usbms_request_sense_data.additional_sense_code
* usbms_request_sense_data.additional_sense_code_qualifier
*
******************************************************************/
void ms_update_sense_data(UCHAR SenseKey,UCHAR ASC,UCHAR ASCQ)
{
usbms_request_sense_data.sense_key = SenseKey;
usbms_request_sense_data.additional_sense_code = ASC;
usbms_request_sense_data.additional_sense_code_qualifier = ASCQ;
}
/******************************************************************
*
* SUB-ROUTINE : ms_idleRx
*
*------------------------------------------------------------------
*
* purpose : Treatment of RBC command
*
* input parameters : none
*
* output parameters : none
*
* global data :
*
******************************************************************/
void ms_idleRx( void )
{
char _buff[CBW_SIZE];
USBMS_CBW *_cbw = NULL;
USBMS_BOT_CDB *_bot_cdb = NULL;
USBMS_RETURN _status;
if( CBW_SIZE == ms_retreiveTb( _buff, CBW_SIZE ) )
{
_cbw = (USBMS_CBW*)_buff;
usbms_context.csw.dCSWTag_0 = _cbw->dCBWTag_0;
usbms_context.csw.dCSWTag_1 = _cbw->dCBWTag_1;
usbms_context.csw.dCSWTag_2 = _cbw->dCBWTag_2;
usbms_context.csw.dCSWTag_3 = _cbw->dCBWTag_3;
_bot_cdb = (USBMS_BOT_CDB*)&_cbw->CBWCB;
usbms_context.current_lun = _cbw->bCBWLUN;
TRACE_DEBUG_H( "RBC:0x%X ",_bot_cdb->generic_rbc.operation_code);
/* Process the RBC request */
switch (_bot_cdb->generic_rbc.operation_code)
{
case RBC_WRITE_10:
/* Process the RBC WRITE_10 command */
TRACE_DEBUG_H( "WRITE_10\n\r");
usbms_context.usb_lun[usbms_context.current_lun].cur_request.transferred_size = 0L;
usbms_context.usb_lun[usbms_context.current_lun].cur_request.buffer_size = (_cbw->dCBWDataTransferLength_3<<24)
|(_cbw->dCBWDataTransferLength_2<<16)
|(_cbw->dCBWDataTransferLength_1<<8)
|(_cbw->dCBWDataTransferLength_0);
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -