//==========================================================================
//####ECOSGPLCOPYRIGHTBEGIN####
// -------------------------------------------
//==========================================================================
//####ECOSGPLCOPYRIGHTBEGIN####
// -------------------------------------------
// Family microprocessor.
// Copyright (C) 2008 Freescale Semiconductor, Inc.
//
// Family microprocessor.
// Copyright (C) 2008 Freescale Semiconductor, Inc.
//
//this error code is defined in error/include/codes.h
//but when the usb driver is used in redboot, the codes.h won't
//be included, so that this definition will solve the problem
//this error code is defined in error/include/codes.h
//but when the usb driver is used in redboot, the codes.h won't
//be included, so that this definition will solve the problem
/* Bit3 - Mass Storage Information
Bit2 - Enumeration Information
Bit1 - Transaction Information
/* Bit3 - Mass Storage Information
Bit2 - Enumeration Information
Bit1 - Transaction Information
//This variable is used to workaround the 31-byte packet issue in i.MX37
//It is initialized as "0x1",
//When data read/write, it must initialize as '0x0'
//This variable is used to workaround the 31-byte packet issue in i.MX37
//It is initialized as "0x1",
//When data read/write, it must initialize as '0x0'
//The below two flags is used to distinguish the received data is data or command
cyg_uint32 g_received_data_type;
//The below two flags is used to distinguish the received data is data or command
cyg_uint32 g_received_data_type;
//2k aligned, this buffer must be uncacheable and unbufferable.
#if defined(CYGHWR_IMX_USB_BUFFER_USE_IRAM)
//2k aligned, this buffer must be uncacheable and unbufferable.
#if defined(CYGHWR_IMX_USB_BUFFER_USE_IRAM)
Reserve 0x800 bytes as USB buffer
Don't use 0x10001000~0x10001800 for other program. */
#if defined(CYGHWR_USB_DEVS_MX37_OTG)
Reserve 0x800 bytes as USB buffer
Don't use 0x10001000~0x10001800 for other program. */
#if defined(CYGHWR_USB_DEVS_MX37_OTG)
static volatile cyg_uint8 * bulk_buffer = (cyg_uint8 *)(0x10002000);
#endif
#if defined(CYGHWR_USB_DEVS_MX51_OTG)
static volatile cyg_uint8 * bulk_buffer = (cyg_uint8 *)(0x10002000);
#endif
#if defined(CYGHWR_USB_DEVS_MX51_OTG)
#endif //defined(CYGHWR_IMX_USB_BUFFER_USE_IRAM)
VOLATILE usbs_imx_otg_hardware* usbs_imx_otg_base = (VOLATILE usbs_imx_otg_hardware* const) USB_BASE_ADDRESS;
#endif //defined(CYGHWR_IMX_USB_BUFFER_USE_IRAM)
VOLATILE usbs_imx_otg_hardware* usbs_imx_otg_base = (VOLATILE usbs_imx_otg_hardware* const) USB_BASE_ADDRESS;
/* Base address of the buffer allocated to IP Layer */
static VOLATILE cyg_uint32 g_bulkbuffer_address_base;
/* length of the buffer */
/* Base address of the buffer allocated to IP Layer */
static VOLATILE cyg_uint32 g_bulkbuffer_address_base;
/* length of the buffer */
/* Length of setup data received */
static VOLATILE cyg_uint8 * g_usb_setup_data;
/* Array to keep information about the endpoints used */
/* Length of setup data received */
static VOLATILE cyg_uint8 * g_usb_setup_data;
/* Array to keep information about the endpoints used */
// ----------------------------------------------------------------------------
// Set USB device address
#define USBS_DEVICE_SET_ADDRESS(addr) (usbs_imx_otg_base->devaddr = ((cyg_uint32)addr & 0x7F) << 25)
// ----------------------------------------------------------------------------
// Set USB device address
#define USBS_DEVICE_SET_ADDRESS(addr) (usbs_imx_otg_base->devaddr = ((cyg_uint32)addr & 0x7F) << 25)
*/
#define USB_OTG_ID (&(usbs_imx_otg_base->id)) /* Identification Register */
#define USB_OTG_HWGENERAL (&(usbs_imx_otg_base->hwgeneral)) /* General Hardware Parameters */
*/
#define USB_OTG_ID (&(usbs_imx_otg_base->id)) /* Identification Register */
#define USB_OTG_HWGENERAL (&(usbs_imx_otg_base->hwgeneral)) /* General Hardware Parameters */
#define USB_OTG_ENDPTNAKEN (&(usbs_imx_otg_base->endptnaken)) /*Endpoint NAK Enable */
#define USB_OTG_CONFIGFLAG (&(usbs_imx_otg_base->configflg)) /* Configured Flag Register */
#define USB_OTG_PORTSC1 (&(usbs_imx_otg_base->portsc1)) /* Port 0 Status/Control */
#define USB_OTG_ENDPTNAKEN (&(usbs_imx_otg_base->endptnaken)) /*Endpoint NAK Enable */
#define USB_OTG_CONFIGFLAG (&(usbs_imx_otg_base->configflg)) /* Configured Flag Register */
#define USB_OTG_PORTSC1 (&(usbs_imx_otg_base->portsc1)) /* Port 0 Status/Control */
#define USB_OTG_USBMODE (&(usbs_imx_otg_base->usbmode)) /* USB Device Mode */
#define USB_OTG_ENDPTSETUPSTAT (&(usbs_imx_otg_base->endptsetupstat)) /* Endpoint Setup Status */
#define USB_OTG_ENDPTPRIME (&(usbs_imx_otg_base->endptprime)) /* Endpoint Initialization */
#define USB_OTG_USBMODE (&(usbs_imx_otg_base->usbmode)) /* USB Device Mode */
#define USB_OTG_ENDPTSETUPSTAT (&(usbs_imx_otg_base->endptsetupstat)) /* Endpoint Setup Status */
#define USB_OTG_ENDPTPRIME (&(usbs_imx_otg_base->endptprime)) /* Endpoint Initialization */
/* USB Device Descriptor according to USB2.0 Specification */
static VOLATILE usb_device_descriptor g_usb_device_desc ={
USB_DEV_DESC_LEN,
/* USB Device Descriptor according to USB2.0 Specification */
static VOLATILE usb_device_descriptor g_usb_device_desc ={
USB_DEV_DESC_LEN,
- USB_DEV_DESC_TYPE,
- USB_DEV_DESC_SPEC_LB,
- USB_DEV_DESC_SPEC_HB,
- USB_DEV_DESC_DEV_CLASS,
- USB_DEV_DESC_DEV_SUBCLASS,
- USB_DEV_DESC_DEV_PROTOCOL,
- USB_DEV_DESC_EP0_MAXPACKETSIZE,
- USB_DEV_DESC_VENDORID_LB,
- USB_DEV_DESC_VENDORID_HB,
- USB_DEV_DESC_PRODUCTID_LB,
- USB_DEV_DESC_PRODUCTID_HB,
- USB_DEV_DESC_DEV_RELEASE_NUM_LB,
- USB_DEV_DESC_DEV_RELEASE_NUM_HB,
+ USB_DEV_DESC_TYPE,
+ USB_DEV_DESC_SPEC_LB,
+ USB_DEV_DESC_SPEC_HB,
+ USB_DEV_DESC_DEV_CLASS,
+ USB_DEV_DESC_DEV_SUBCLASS,
+ USB_DEV_DESC_DEV_PROTOCOL,
+ USB_DEV_DESC_EP0_MAXPACKETSIZE,
+ USB_DEV_DESC_VENDORID_LB,
+ USB_DEV_DESC_VENDORID_HB,
+ USB_DEV_DESC_PRODUCTID_LB,
+ USB_DEV_DESC_PRODUCTID_HB,
+ USB_DEV_DESC_DEV_RELEASE_NUM_LB,
+ USB_DEV_DESC_DEV_RELEASE_NUM_HB,
USB_DEV_DESC_DEV_STRING_IND_SERIAL_NUM,
USB_DEV_DESC_DEV_NUM_CONFIGURATIONS
};
USB_DEV_DESC_DEV_STRING_IND_SERIAL_NUM,
USB_DEV_DESC_DEV_NUM_CONFIGURATIONS
};
/* USB Config Descriptor according to USB2.0 Specification */
static VOLATILE usb_conf_desc g_usb_config_desc = {
/* USB Config Descriptor according to USB2.0 Specification */
static VOLATILE usb_conf_desc g_usb_config_desc = {
- {
- USB_DEV_CONFIG_DESC_LEN,
- USB_DEV_CONFIG_DESC_TYPE,
- USB_DEV_CONFIG_DESC_TTL_LEN_LB ,
- USB_DEV_CONFIG_DESC_TTL_LEN_HB ,
- USB_DEV_CONFIG_DESC_NUM_0F_INF,
- USB_DEV_CONFIG_DESC_CONFIG_VALUE ,
- USB_DEV_CONFIG_DESC_STRING_INDEX,
- USB_DEV_CONFIG_DESC_ATTRIBUTES,
+ {
+ USB_DEV_CONFIG_DESC_LEN,
+ USB_DEV_CONFIG_DESC_TYPE,
+ USB_DEV_CONFIG_DESC_TTL_LEN_LB ,
+ USB_DEV_CONFIG_DESC_TTL_LEN_HB ,
+ USB_DEV_CONFIG_DESC_NUM_0F_INF,
+ USB_DEV_CONFIG_DESC_CONFIG_VALUE ,
+ USB_DEV_CONFIG_DESC_STRING_INDEX,
+ USB_DEV_CONFIG_DESC_ATTRIBUTES,
USB_DEV_INF_DESC_ALT_SETTING,
USB_DEV_INF_DESC_NUM_OF_EP, /* NOTE : This should not be more than 2 */
#if defined(CYGHWR_IMX_USB_DOWNLOAD_SUPPORT)
USB_DEV_INF_DESC_ALT_SETTING,
USB_DEV_INF_DESC_NUM_OF_EP, /* NOTE : This should not be more than 2 */
#if defined(CYGHWR_IMX_USB_DOWNLOAD_SUPPORT)
USB_DEV_INF_DESC_INF_SUBCLASS_NS_BLANK,
USB_DEV_INF_DESC_INF_PROTOCOL,
#else
USB_DEV_INF_DESC_INF_SUBCLASS_NS_BLANK,
USB_DEV_INF_DESC_INF_PROTOCOL,
#else
- USB_DEV_INF_DESC_INF_CLASS_MSC,
- USB_DEV_INF_DESC_INF_SUBCLASS_MSC_SCSI,
- USB_DEV_INF_DESC_INF_PROTOCOL_MSC_BOT,
+ USB_DEV_INF_DESC_INF_CLASS_MSC,
+ USB_DEV_INF_DESC_INF_SUBCLASS_MSC_SCSI,
+ USB_DEV_INF_DESC_INF_PROTOCOL_MSC_BOT,
- USB_EP1_DESC_ATTRIBUTES,
- USB_EP1_DESC_MAX_PACKET_SIZE_HS_LB,
- USB_EP1_DESC_MAX_PACKET_SIZE_HS_HB,
+ USB_EP1_DESC_ATTRIBUTES,
+ USB_EP1_DESC_MAX_PACKET_SIZE_HS_LB,
+ USB_EP1_DESC_MAX_PACKET_SIZE_HS_HB,
- USB_EP2_DESC_EP_ADDR,
- USB_EP2_DESC_ATTRIBUTES,
- USB_EP2_DESC_MAX_PACKET_SIZE_HS_LB,
- USB_EP2_DESC_MAX_PACKET_SIZE_HS_HB,
+ USB_EP2_DESC_EP_ADDR,
+ USB_EP2_DESC_ATTRIBUTES,
+ USB_EP2_DESC_MAX_PACKET_SIZE_HS_LB,
+ USB_EP2_DESC_MAX_PACKET_SIZE_HS_HB,
static VOLATILE usb_str2_desc g_usb_otg_string_desc2 = {
USB_STR2_DESC_SIZE_NS, /* bLength */
USB_STR2_DESC_TYPE, /* bDescriptorType */
{
'M', 0x00, /* bString */
static VOLATILE usb_str2_desc g_usb_otg_string_desc2 = {
USB_STR2_DESC_SIZE_NS, /* bLength */
USB_STR2_DESC_TYPE, /* bDescriptorType */
{
'M', 0x00, /* bString */
cyg_uint8 zlt - zero lengh packet termination (enable - ZLT_ENABLE; disable - ZLT_DISABLE)
cyg_uint16 mps - Max packet length
cyg_uint8 ios - interrupt on Setup
cyg_uint8 zlt - zero lengh packet termination (enable - ZLT_ENABLE; disable - ZLT_DISABLE)
cyg_uint16 mps - Max packet length
cyg_uint8 ios - interrupt on Setup
cyg_uint8 terminate - terminate - TERMINATE; not terminate - NOT_TERMINATE
cyg_uint16 total_bytes - Total Bytes to be transfered in this dQH
cyg_uint8 ioc - interrupt on complete, set - IOC_SET, not set - IOC_NOTSET
cyg_uint8 terminate - terminate - TERMINATE; not terminate - NOT_TERMINATE
cyg_uint16 total_bytes - Total Bytes to be transfered in this dQH
cyg_uint8 ioc - interrupt on complete, set - IOC_SET, not set - IOC_NOTSET
cyg_uint32 buffer_ptr0 - Buffer Pointer page 0
cyg_uint16 current_offset - current offset
cyg_uint32 buffer_ptr1 - Buffer Pointer page 1
cyg_uint32 buffer_ptr2 - Buffer Pointer page 1
cyg_uint32 buffer_ptr3 - Buffer Pointer page 1
cyg_uint32 buffer_ptr4 - Buffer Pointer page 1
cyg_uint32 buffer_ptr0 - Buffer Pointer page 0
cyg_uint16 current_offset - current offset
cyg_uint32 buffer_ptr1 - Buffer Pointer page 1
cyg_uint32 buffer_ptr2 - Buffer Pointer page 1
cyg_uint32 buffer_ptr3 - Buffer Pointer page 1
cyg_uint32 buffer_ptr4 - Buffer Pointer page 1
usbs_setup_queuehead(struct dqh_t* qhead)
{
volatile struct dqh_setup_t* dqh_word = (volatile struct dqh_setup_t*) qhead->dqh_base;
usbs_setup_queuehead(struct dqh_t* qhead)
{
volatile struct dqh_setup_t* dqh_word = (volatile struct dqh_setup_t*) qhead->dqh_base;
/*Current dTD Pointer => for hw use, not modified by DCD software */
dqh_word->dqh_word1 = 0x0;
/*Current dTD Pointer => for hw use, not modified by DCD software */
dqh_word->dqh_word1 = 0x0;
dqh_word->dqh_word3 = ((((cyg_uint32)(qhead->total_bytes) & 0x7FFF) << 16) | ((cyg_uint32)(qhead->ioc) <<15) | (qhead->status));
/*Bit31:12 Buffer Pointer (Page 0) */
dqh_word->dqh_word3 = ((((cyg_uint32)(qhead->total_bytes) & 0x7FFF) << 16) | ((cyg_uint32)(qhead->ioc) <<15) | (qhead->status));
/*Bit31:12 Buffer Pointer (Page 0) */
/*Bit31:12 Buffer Pointer (Page 2) */
dqh_word->dqh_word6 = (qhead->buffer_ptr2 & 0xFFFFF000);
/*Bit31:12 Buffer Pointer (Page 3) */
dqh_word->dqh_word7 = (qhead->buffer_ptr3 & 0xFFFFF000);
/*Bit31:12 Buffer Pointer (Page 2) */
dqh_word->dqh_word6 = (qhead->buffer_ptr2 & 0xFFFFF000);
/*Bit31:12 Buffer Pointer (Page 3) */
dqh_word->dqh_word7 = (qhead->buffer_ptr3 & 0xFFFFF000);
cyg_uint8 terminate - terminate - TERMINATE; not terminate - NOT_TERMINATE
cyg_uint16 total_bytes - Total Bytes to be transfered in this dQH
cyg_uint8 ioc - interrupt on complete, set - IOC_SET, not set - IOC_NOTSET
cyg_uint8 terminate - terminate - TERMINATE; not terminate - NOT_TERMINATE
cyg_uint16 total_bytes - Total Bytes to be transfered in this dQH
cyg_uint8 ioc - interrupt on complete, set - IOC_SET, not set - IOC_NOTSET
cyg_uint32 buffer_ptr0 - Buffer Pointer page 0
cyg_uint16 current_offset - current offset
cyg_uint32 buffer_ptr1 - Buffer Pointer page 1
cyg_uint32 buffer_ptr2 - Buffer Pointer page 1
cyg_uint32 buffer_ptr3 - Buffer Pointer page 1
cyg_uint32 buffer_ptr0 - Buffer Pointer page 0
cyg_uint16 current_offset - current offset
cyg_uint32 buffer_ptr1 - Buffer Pointer page 1
cyg_uint32 buffer_ptr2 - Buffer Pointer page 1
cyg_uint32 buffer_ptr3 - Buffer Pointer page 1
usbs_setup_transdesc(struct dtd_t* td)
{
volatile struct dtd_setup_t* dtd_word = (volatile struct dtd_setup_t *) td->dtd_base;
usbs_setup_transdesc(struct dtd_t* td)
{
volatile struct dtd_setup_t* dtd_word = (volatile struct dtd_setup_t *) td->dtd_base;
/* Bit30:16 total_bytes, Bit15 ioc, Bit7:0 status */
dtd_word->dtd_word1 = ((((cyg_uint32)td->total_bytes & 0x7FFF) << 16)| ((cyg_uint32)td->ioc <<15) | (td->status));
/* Bit30:16 total_bytes, Bit15 ioc, Bit7:0 status */
dtd_word->dtd_word1 = ((((cyg_uint32)td->total_bytes & 0x7FFF) << 16)| ((cyg_uint32)td->ioc <<15) | (td->status));
/* Bit31:12 Buffer Pointer Page 0 ; Bit11:0 Current Offset */
dtd_word->dtd_word2 = ((td->buffer_ptr0 & 0xFFFFF000) | (td->current_offset & 0xFFF));
/* Bit31:12 Buffer Pointer Page 0 ; Bit11:0 Current Offset */
dtd_word->dtd_word2 = ((td->buffer_ptr0 & 0xFFFFF000) | (td->current_offset & 0xFFF));
/* Bit31:12 Buffer Pointer Page 1 ; Bit10:0 Frame Number */
dtd_word->dtd_word3 = (td->buffer_ptr1 & 0xFFFFF000);
/* Bit31:12 Buffer Pointer Page 1 ; Bit10:0 Frame Number */
dtd_word->dtd_word3 = (td->buffer_ptr1 & 0xFFFFF000);
-RETURN VALUE: cyg_uint32 address : address of the allocated buffer
-IMPORTANT NOTES: If Buffer1 is FREE then return Buffer1 and mark this as Busy else check for buffer2 . If
+RETURN VALUE: cyg_uint32 address : address of the allocated buffer
+IMPORTANT NOTES: If Buffer1 is FREE then return Buffer1 and mark this as Busy else check for buffer2 . If
none of the buffer is free then return NULL.
==================================================================================================*/
cyg_uint32 util_alloc_buffer(void)
{
cyg_uint32 buffer_addr = (cyg_uint32)NULL; //force type conversion for multiple NULL definitions
none of the buffer is free then return NULL.
==================================================================================================*/
cyg_uint32 util_alloc_buffer(void)
{
cyg_uint32 buffer_addr = (cyg_uint32)NULL; //force type conversion for multiple NULL definitions
if (g_bulkbuffer_map.buffer1_status == BUFFER_FREE )
{
buffer_addr = g_bulkbuffer_map.buffer1_address;
g_bulkbuffer_map.buffer1_status = BUFFER_IN_USE;
}
if (g_bulkbuffer_map.buffer1_status == BUFFER_FREE )
{
buffer_addr = g_bulkbuffer_map.buffer1_address;
g_bulkbuffer_map.buffer1_status = BUFFER_IN_USE;
}
else if(g_bulkbuffer_map.buffer2_status == BUFFER_FREE)
{
buffer_addr = g_bulkbuffer_map.buffer2_address;
g_bulkbuffer_map.buffer2_status = BUFFER_IN_USE;
}
else if(g_bulkbuffer_map.buffer2_status == BUFFER_FREE)
{
buffer_addr = g_bulkbuffer_map.buffer2_address;
g_bulkbuffer_map.buffer2_status = BUFFER_IN_USE;
}
return buffer_addr ;
}
/*==================================================================================================
FUNCTION: util_free_buffer
DESCRIPTION: This function put the buffer in free state.
return buffer_addr ;
}
/*==================================================================================================
FUNCTION: util_free_buffer
DESCRIPTION: This function put the buffer in free state.
==================================================================================================*/
void util_free_buffer(cyg_uint32 address)
{
==================================================================================================*/
void util_free_buffer(cyg_uint32 address)
{
==================================================================================================*/
void util_set_status_bulk_buffer(cyg_uint32 buffer_addr,int buffer_status)
{
==================================================================================================*/
void util_set_status_bulk_buffer(cyg_uint32 buffer_addr,int buffer_status)
{
FUNCTION: usbs_endpoint_stall
DESCRIPTION: This function Send/Receive the STALL HANDSHAKE to USB Host
ARGUMENTS PASSED:
FUNCTION: usbs_endpoint_stall
DESCRIPTION: This function Send/Receive the STALL HANDSHAKE to USB Host
ARGUMENTS PASSED:
==============================================================================*/
static void
usbs_endpoint_stall(cyg_uint8 endpoint , cyg_uint8 direction)
{
if( direction == OUT )
==============================================================================*/
static void
usbs_endpoint_stall(cyg_uint8 endpoint , cyg_uint8 direction)
{
if( direction == OUT )
ARGUMENTS PASSED: cyg_uint8 direction OUT Receive Status Command From Host
IN Send Status Command to Host
RETURN VALUE: None
ARGUMENTS PASSED: cyg_uint8 direction OUT Receive Status Command From Host
IN Send Status Command to Host
RETURN VALUE: None
usbs_status_phase(cyg_uint8 trans_type, cyg_uint8 direction)
{
usb_buffer_descriptor_t bd ;
usbs_status_phase(cyg_uint8 trans_type, cyg_uint8 direction)
{
usb_buffer_descriptor_t bd ;
/* Send ZERO length Length Data */
//usbs_ep2_send_data(EP2,&bd,FALSE);
break;
/* Send ZERO length Length Data */
//usbs_ep2_send_data(EP2,&bd,FALSE);
break;
}
// ---------------------------------------------------------------------------
// The following static functions are for USB device enumeration processing
/*============================================================================
FUNCTION: usbs_handle_get_descriptor
DESCRIPTION: This function Handle the GET DESCRIPTOR request
}
// ---------------------------------------------------------------------------
// The following static functions are for USB device enumeration processing
/*============================================================================
FUNCTION: usbs_handle_get_descriptor
DESCRIPTION: This function Handle the GET DESCRIPTOR request
============================================================================*/
static void
usbs_handle_get_descriptor()
============================================================================*/
static void
usbs_handle_get_descriptor()
}
/*=============================================================================
FUNCTION: usbs_handle_get_device_desc
DESCRIPTION: This function Handle the GET DEVICE DESCRIPTOR request
ARGUMENTS PASSED: None
RETURN VALUE: None
}
/*=============================================================================
FUNCTION: usbs_handle_get_device_desc
DESCRIPTION: This function Handle the GET DEVICE DESCRIPTOR request
ARGUMENTS PASSED: None
RETURN VALUE: None
cyg_uint8 zlt = 0;//0 means false
USBDBGMSG(DEBUG_ENUM,"+USBDBGMSG: enum - get device descriptor\n");
cyg_uint8 zlt = 0;//0 means false
USBDBGMSG(DEBUG_ENUM,"+USBDBGMSG: enum - get device descriptor\n");
/* get the buffer address for data transfer over EP0 */
buffer_addrs = g_bulkbuffer_map.ep0_buffer_addrs; //256bytes before the two Bulk buffers
/* get the buffer address for data transfer over EP0 */
buffer_addrs = g_bulkbuffer_map.ep0_buffer_addrs; //256bytes before the two Bulk buffers
/* Fill the buffer with the descriptor data */
usbs_ep0in_fill_buffer(FILL_DEVICE_DESC,buffer_addrs);
/* Fill the buffer with the descriptor data */
usbs_ep0in_fill_buffer(FILL_DEVICE_DESC,buffer_addrs);
desc_length = g_usb_setup_data[WLENGTH_LOWBYTE];
desc_length |= ( g_usb_setup_data[WLENGTH_HIGHBYTE] <<0x8);
desc_length = g_usb_setup_data[WLENGTH_LOWBYTE];
desc_length |= ( g_usb_setup_data[WLENGTH_HIGHBYTE] <<0x8);
* requested length of descroptor only else send the actual length of descriptor*/
if( g_usb_dev_state == USB_DEV_DEFAULT_STATE )
{
bd.size = MPS_8;
}
* requested length of descroptor only else send the actual length of descriptor*/
if( g_usb_dev_state == USB_DEV_DEFAULT_STATE )
{
bd.size = MPS_8;
}
/* Send descriptor - Data Phase*/
usbs_ep0_send_data(&bd,zlt); //zlt is false=>not zero length packet
//send dev descriptor to host.
/* Send descriptor - Data Phase*/
usbs_ep0_send_data(&bd,zlt); //zlt is false=>not zero length packet
//send dev descriptor to host.
/* Status Phase -- OUT */
usbs_status_phase(CONTROL,OUT); //Get Zero-length data packet from Host, Device sends status: ACK(success), NAK(busy), or STALL(failed)
/* Status Phase -- OUT */
usbs_status_phase(CONTROL,OUT); //Get Zero-length data packet from Host, Device sends status: ACK(success), NAK(busy), or STALL(failed)
}
/*=============================================================================
FUNCTION: usbs_handle_get_config_desc
DESCRIPTION: This function Handle the GET CONFIGURATION DESCRIPTOR request
ARGUMENTS PASSED:
RETURN VALUE: None
}
/*=============================================================================
FUNCTION: usbs_handle_get_config_desc
DESCRIPTION: This function Handle the GET CONFIGURATION DESCRIPTOR request
ARGUMENTS PASSED:
RETURN VALUE: None
/* Fill the buffer with the descriptor data */
usbs_ep0in_fill_buffer(FILL_CONF_DESC, buffer_addrs);
/* Fill the buffer with the descriptor data */
usbs_ep0in_fill_buffer(FILL_CONF_DESC, buffer_addrs);
/* total length of descriptor */
desc_length = ((g_usb_desc.config_desc->usb_config_desc.total_length_lo) \
| ( g_usb_desc.config_desc->usb_config_desc.total_length_hi << 0x8 ));
/* total length of descriptor */
desc_length = ((g_usb_desc.config_desc->usb_config_desc.total_length_lo) \
| ( g_usb_desc.config_desc->usb_config_desc.total_length_hi << 0x8 ));
* requested length of descroptor only else send the actual length of descriptor*/
if(desc_length_req <= desc_length)
{
* requested length of descroptor only else send the actual length of descriptor*/
if(desc_length_req <= desc_length)
{
}
/*=============================================================================
FUNCTION: usbs_handle_get_string_desc
DESCRIPTION: This function Handle the GET STRING DESCRIPTOR request
ARGUMENTS PASSED: None
}
/*=============================================================================
FUNCTION: usbs_handle_get_string_desc
DESCRIPTION: This function Handle the GET STRING DESCRIPTOR request
ARGUMENTS PASSED: None
/* Get the length of descriptor requested */
desc_length_req = g_usb_setup_data[WLENGTH_LOWBYTE];
desc_length_req |= ( g_usb_setup_data[WLENGTH_HIGHBYTE] <<0x8);
/* Get the length of descriptor requested */
desc_length_req = g_usb_setup_data[WLENGTH_LOWBYTE];
desc_length_req |= ( g_usb_setup_data[WLENGTH_HIGHBYTE] <<0x8);
* requested length of descroptor only else send the actual length of descriptor*/
if(desc_length_req <= g_usb_desc.str_desc0->length )
{
* requested length of descroptor only else send the actual length of descriptor*/
if(desc_length_req <= g_usb_desc.str_desc0->length )
{
case STR_DES1: /*iManufacturer */
usbs_ep0in_fill_buffer(FILL_STR_DES1,buffer_addrs);
case STR_DES1: /*iManufacturer */
usbs_ep0in_fill_buffer(FILL_STR_DES1,buffer_addrs);
* requested length of descroptor only else send the actual length of descriptor*/
if(desc_length_req <= g_usb_desc.str_desc1->length )
{
* requested length of descroptor only else send the actual length of descriptor*/
if(desc_length_req <= g_usb_desc.str_desc1->length )
{
case STR_DES2: /*iProduct */
usbs_ep0in_fill_buffer(FILL_STR_DES2,buffer_addrs );
case STR_DES2: /*iProduct */
usbs_ep0in_fill_buffer(FILL_STR_DES2,buffer_addrs );
- length_of_desc = g_usb_desc.str_desc2->length;
- /* If requested length of descriptor is lesser than actual length of descriotor then send
+ length_of_desc = g_usb_desc.str_desc2->length;
+ /* If requested length of descriptor is lesser than actual length of descriotor then send
* requested length of descroptor only else send the actual length of descriptor*/
if(desc_length_req <= length_of_desc )
{
* requested length of descroptor only else send the actual length of descriptor*/
if(desc_length_req <= length_of_desc )
{
/* send zero length data */
usbs_status_phase(CONTROL,IN);
/* Status Phase -- OUT */
usbs_status_phase(CONTROL,OUT);
break;
/* send zero length data */
usbs_status_phase(CONTROL,IN);
/* Status Phase -- OUT */
usbs_status_phase(CONTROL,OUT);
break;
case STR_DES5: /*iSerialNumber */
#if !defined(CYGHWR_IMX_USB_DOWNLOAD_SUPPORT)
usbs_ep0in_fill_buffer(FILL_SN_DESC,buffer_addrs );
case STR_DES5: /*iSerialNumber */
#if !defined(CYGHWR_IMX_USB_DOWNLOAD_SUPPORT)
usbs_ep0in_fill_buffer(FILL_SN_DESC,buffer_addrs );
* requested length of descroptor only else send the actual length of descriptor*/
if(desc_length_req <= g_usb_desc.sn_desc->length )
{
* requested length of descroptor only else send the actual length of descriptor*/
if(desc_length_req <= g_usb_desc.sn_desc->length )
{
USBDBGMSG(DEBUG_ENUM,"+USBDBGMSG: enum - get string descriptor - SN\n");
break;
#endif
case STR_DES4: /*iSerialNumber */
usbs_ep0in_fill_buffer(FILL_STR_DES3,buffer_addrs );
USBDBGMSG(DEBUG_ENUM,"+USBDBGMSG: enum - get string descriptor - SN\n");
break;
#endif
case STR_DES4: /*iSerialNumber */
usbs_ep0in_fill_buffer(FILL_STR_DES3,buffer_addrs );
* requested length of descroptor only else send the actual length of descriptor*/
if(desc_length_req <= g_usb_desc.str_desc3->length )
{
* requested length of descroptor only else send the actual length of descriptor*/
if(desc_length_req <= g_usb_desc.str_desc3->length )
{
/* Get the Device Address to be SET from the Setup Data */
device_addrs = g_usb_setup_data[WVALUE_LOWBYTE] + (g_usb_setup_data[WVALUE_HIGHBYTE]<<8);
/* Get the Device Address to be SET from the Setup Data */
device_addrs = g_usb_setup_data[WVALUE_LOWBYTE] + (g_usb_setup_data[WVALUE_HIGHBYTE]<<8);
if ((g_usb_setup_data[WINDEX_LOWBYTE] == 0) &&
(g_usb_setup_data[WINDEX_HIGHBYTE] == 0) &&
(g_usb_setup_data[WLENGTH_LOWBYTE] == 0) &&
(g_usb_setup_data[WLENGTH_HIGHBYTE] == 0) &&
(device_addrs <= USB_MAX_DEVICE_ADDR))
if ((g_usb_setup_data[WINDEX_LOWBYTE] == 0) &&
(g_usb_setup_data[WINDEX_HIGHBYTE] == 0) &&
(g_usb_setup_data[WLENGTH_LOWBYTE] == 0) &&
(g_usb_setup_data[WLENGTH_HIGHBYTE] == 0) &&
(device_addrs <= USB_MAX_DEVICE_ADDR))
case USB_DEV_ADDRESSED_STATE :
/* Send Ack to Host */
usbs_status_phase(CONTROL,IN);
case USB_DEV_ADDRESSED_STATE :
/* Send Ack to Host */
usbs_status_phase(CONTROL,IN);
/* Set the Device Address */
USBS_DEVICE_SET_ADDRESS(USB_DEFAULT_ADDR);
/* Change state to ADDRESSED STATE */
/* Set the Device Address */
USBS_DEVICE_SET_ADDRESS(USB_DEFAULT_ADDR);
/* Change state to ADDRESSED STATE */
/* Set the Device Address */
USBS_DEVICE_SET_ADDRESS(device_addrs);
/* Change state to ADDRESSED STATE */
/* Set the Device Address */
USBS_DEVICE_SET_ADDRESS(device_addrs);
/* Change state to ADDRESSED STATE */
}
/*=============================================================================
FUNCTION: usbs_handle_get_configuration
DESCRIPTION: This function Handle the GET CONFIGURATION request
}
/*=============================================================================
FUNCTION: usbs_handle_get_configuration
DESCRIPTION: This function Handle the GET CONFIGURATION request
if((g_usb_setup_data[WINDEX_LOWBYTE] == 0) &&
(g_usb_setup_data[WINDEX_HIGHBYTE] == 0) &&
(g_usb_setup_data[WVALUE_LOWBYTE] == 0) &&
(g_usb_setup_data[WVALUE_HIGHBYTE] == 0) &&
(g_usb_setup_data[WLENGTH_LOWBYTE] == LEN_OF_CONFIG_VALUE) &&
if((g_usb_setup_data[WINDEX_LOWBYTE] == 0) &&
(g_usb_setup_data[WINDEX_HIGHBYTE] == 0) &&
(g_usb_setup_data[WVALUE_LOWBYTE] == 0) &&
(g_usb_setup_data[WVALUE_HIGHBYTE] == 0) &&
(g_usb_setup_data[WLENGTH_LOWBYTE] == LEN_OF_CONFIG_VALUE) &&
bd.size=LEN_OF_CONFIG_VALUE;
usbs_ep0_send_data(&bd,0);
bd.size=LEN_OF_CONFIG_VALUE;
usbs_ep0_send_data(&bd,0);
/* Receive Ack from Host*/
usbs_status_phase(CONTROL,OUT);
break;
/* Receive Ack from Host*/
usbs_status_phase(CONTROL,OUT);
break;
USBDBGMSG(DEBUG_ENUM,"+USBDBGMSG: enum - get config handler\n");
}
/*=============================================================================
FUNCTION: usbs_handle_set_configuration
DESCRIPTION: This function Handle the SET CONFIGURATION request
USBDBGMSG(DEBUG_ENUM,"+USBDBGMSG: enum - get config handler\n");
}
/*=============================================================================
FUNCTION: usbs_handle_set_configuration
DESCRIPTION: This function Handle the SET CONFIGURATION request
config_data.direction = g_end_pt_info[i].direction;
config_data.transfer_type = g_end_pt_info[i].transfer_type;
config_data.max_pkt_size = g_end_pt_info[i].max_pkt_size;
config_data.direction = g_end_pt_info[i].direction;
config_data.transfer_type = g_end_pt_info[i].transfer_type;
config_data.max_pkt_size = g_end_pt_info[i].max_pkt_size;
//USBDBGMSG("+USBDBGMSG:EP0 IN stalled at set conf in addr state\n");
}
USBDBGMSG(DEBUG_ENUM,"+USBDBGMSG: enum - set conf@ADDRESSED_STATE\n");
//USBDBGMSG("+USBDBGMSG:EP0 IN stalled at set conf in addr state\n");
}
USBDBGMSG(DEBUG_ENUM,"+USBDBGMSG: enum - set conf@ADDRESSED_STATE\n");
case USB_DEV_CONFIGURED_STATE :
if(g_usb_setup_data[WVALUE_LOWBYTE] == USB_DEV_CONFIG_DESC_CONFIG_VALUE)
{
case USB_DEV_CONFIGURED_STATE :
if(g_usb_setup_data[WVALUE_LOWBYTE] == USB_DEV_CONFIG_DESC_CONFIG_VALUE)
{
usbs_status_phase(CONTROL,IN);
}
else if (g_usb_setup_data[WVALUE_LOWBYTE] == USB_DEV_VALUE_OF_UNCONFIG)
usbs_status_phase(CONTROL,IN);
}
else if (g_usb_setup_data[WVALUE_LOWBYTE] == USB_DEV_VALUE_OF_UNCONFIG)
/* Send STALL Handshake */
usbs_endpoint_stall(EP0,IN);
USBDBGMSG(DEBUG_ENUM,"+USBDBGMSG: enum - set conf@incorrect state\n");
/* Send STALL Handshake */
usbs_endpoint_stall(EP0,IN);
USBDBGMSG(DEBUG_ENUM,"+USBDBGMSG: enum - set conf@incorrect state\n");
FUNCTION: usbs_handle_msc_get_maxlun
DESCRIPTION: This function Handle the GET MAX LUN Mass Storage class
specific request
FUNCTION: usbs_handle_msc_get_maxlun
DESCRIPTION: This function Handle the GET MAX LUN Mass Storage class
specific request
cyg_uint8 zlt = 0;//0 means false
cyg_uint8 Max_Lun=0;
USBDBGMSG(DEBUG_ENUM,"+USBDBGMSG: MASS - Get MAX LUN\n");
cyg_uint8 zlt = 0;//0 means false
cyg_uint8 Max_Lun=0;
USBDBGMSG(DEBUG_ENUM,"+USBDBGMSG: MASS - Get MAX LUN\n");
/* get the buffer address for data transfer over EP0 */
buffer_addrs = g_bulkbuffer_map.ep0_buffer_addrs; //256bytes before the two Bulk buffers
/* get the buffer address for data transfer over EP0 */
buffer_addrs = g_bulkbuffer_map.ep0_buffer_addrs; //256bytes before the two Bulk buffers
/* Send descriptor - Data Phase*/
usbs_ep0_send_data(&bd,zlt); //zlt is false=>not zero length packet
//send dev descriptor to host.
/* Send descriptor - Data Phase*/
usbs_ep0_send_data(&bd,zlt); //zlt is false=>not zero length packet
//send dev descriptor to host.
/* Status Phase -- OUT */
usbs_status_phase(CONTROL,OUT); //Get Zero-length data packet from Host, Device sends status: ACK(success), NAK(busy), or STALL(failed)
/* Status Phase -- OUT */
usbs_status_phase(CONTROL,OUT); //Get Zero-length data packet from Host, Device sends status: ACK(success), NAK(busy), or STALL(failed)
}
/*=============================================================================
FUNCTION: usbs_ep0in_fill_buffer
}
/*=============================================================================
FUNCTION: usbs_ep0in_fill_buffer
}
/*=============================================================================
FUNCTION: usbs_ep0_init_dqh
DESCRIPTION: This function is used to initialize the queue header of EP0
}
/*=============================================================================
FUNCTION: usbs_ep0_init_dqh
DESCRIPTION: This function is used to initialize the queue header of EP0
RETURN VALUE: NONE
IMPORTANT NOTES: called by usbs_imx_otg_dev_ep0_init(),usbs_imx_otg_dev_handle_bus_reset()
=============================================================================*/
RETURN VALUE: NONE
IMPORTANT NOTES: called by usbs_imx_otg_dev_ep0_init(),usbs_imx_otg_dev_handle_bus_reset()
=============================================================================*/
//clear queue header
ep_q_hdr_base = ((volatile cyg_uint32 *)g_bulkbuffer_map.ep_dqh_base_addrs);
/* Clear the dQH Memory */
//clear queue header
ep_q_hdr_base = ((volatile cyg_uint32 *)g_bulkbuffer_map.ep_dqh_base_addrs);
/* Clear the dQH Memory */
/******************************************************************************
/ =================
/ dQH0 for EP0OUT
/ =================
/ Initialize device queue heads in system memory
/ 8 bytes for the 1st setup packet */
/******************************************************************************
/ =================
/ dQH0 for EP0OUT
/ =================
/ Initialize device queue heads in system memory
/ 8 bytes for the 1st setup packet */
usbs_ep0_send_data(usb_buffer_descriptor_t* bd,cyg_uint8 zlt)
{
struct dtd_t td;
cyg_uint32 total_bytes ;
cyg_uint32 dtd_address,dqh_address;
usbs_ep0_send_data(usb_buffer_descriptor_t* bd,cyg_uint8 zlt)
{
struct dtd_t td;
cyg_uint32 total_bytes ;
cyg_uint32 dtd_address,dqh_address;
usb_status_t status = USB_FAILURE;
/* Get Device Transfer Descriptor of the requested endpoint */
dtd_address = USBS_EP_GET_dTD(EP0,IN);
usb_status_t status = USB_FAILURE;
/* Get Device Transfer Descriptor of the requested endpoint */
dtd_address = USBS_EP_GET_dTD(EP0,IN);
/* Get Device Queue head of the requested endpoint */
dqh_address = USBS_EP_GET_dQH(EP0,IN);
/* Get Device Queue head of the requested endpoint */
dqh_address = USBS_EP_GET_dQH(EP0,IN);
/* Enable ZLT when data size is in multiple of Maximum Packet Size */
if(zlt)
{
/* set ZLT enable */
(*(volatile cyg_uint32*)(dqh_address)) &= ~0x20000000;
}
/* Enable ZLT when data size is in multiple of Maximum Packet Size */
if(zlt)
{
/* set ZLT enable */
(*(volatile cyg_uint32*)(dqh_address)) &= ~0x20000000;
}
FUNCTION: usbs_ep0_recevie_data
DESCRIPTION: This function Handle the Status Token (IN/OUT) from USB Host
ARGUMENTS PASSED:
FUNCTION: usbs_ep0_recevie_data
DESCRIPTION: This function Handle the Status Token (IN/OUT) from USB Host
ARGUMENTS PASSED:
data is received from the host.
USB_FAILURE - : Some failure occurred in receiving the data.
USB_INVALID - : If the endpoint is invalid.
data is received from the host.
USB_FAILURE - : Some failure occurred in receiving the data.
USB_INVALID - : If the endpoint is invalid.
=============================================================================*/
static usb_status_t usbs_ep0_receive_data(usb_buffer_descriptor_t* bd)
{
=============================================================================*/
static usb_status_t usbs_ep0_receive_data(usb_buffer_descriptor_t* bd)
{
/* Get Device Device Queue Head of the requested endpoint */
dqh_address = USBS_EP_GET_dQH(EP0, OUT);
/* Get Device Device Queue Head of the requested endpoint */
dqh_address = USBS_EP_GET_dQH(EP0, OUT);
/* Get Device Transfer Descriptor of the requested endpoint */
dtd_address = USBS_EP_GET_dTD(EP0, OUT);
/* Get the total bytes to be received */
/* Get Device Transfer Descriptor of the requested endpoint */
dtd_address = USBS_EP_GET_dTD(EP0, OUT);
/* Get the total bytes to be received */
td.dtd_base = dtd_address;
td.next_link_ptr = dtd_address + 0x20;
td.terminate = TERMINATE;
td.dtd_base = dtd_address;
td.next_link_ptr = dtd_address + 0x20;
td.terminate = TERMINATE;
/* Set the Transfer Descriptor */
usbs_setup_transdesc(&td);
/* 1. write dQH next ptr and dQH terminate bit to 0 */
*(volatile cyg_uint32*)(dqh_address+0x8)= dtd_address;
/* Set the Transfer Descriptor */
usbs_setup_transdesc(&td);
/* 1. write dQH next ptr and dQH terminate bit to 0 */
*(volatile cyg_uint32*)(dqh_address+0x8)= dtd_address;
/* 3. prime endpoint by writing '1' in ENDPTPRIME */
usbs_imx_otg_base->endptprime |= ( EPOUT_PRIME << EP0 );
/* 4. Wait for the Complete Status */
while (!((usbs_imx_otg_base->endptprime) & ( EPOUT_COMPLETE << EP0)));
/* 3. prime endpoint by writing '1' in ENDPTPRIME */
usbs_imx_otg_base->endptprime |= ( EPOUT_PRIME << EP0 );
/* 4. Wait for the Complete Status */
while (!((usbs_imx_otg_base->endptprime) & ( EPOUT_COMPLETE << EP0)));
//USBDBGMSG("+USBDBGMSG: enter ep0 dsr.\n");
/* 1. Receive Setup Data*/
bd.buffer = (cyg_uint32 *)g_usb_setup_data;
bd.size = 0;
//USBDBGMSG("+USBDBGMSG: enter ep0 dsr.\n");
/* 1. Receive Setup Data*/
bd.buffer = (cyg_uint32 *)g_usb_setup_data;
bd.size = 0;
dqh_address = USBS_EP_GET_dQH(EP0,OUT);
dqh_word = (volatile struct dqh_setup_t*)dqh_address;
dqh_address = USBS_EP_GET_dQH(EP0,OUT);
dqh_word = (volatile struct dqh_setup_t*)dqh_address;
/* write '1' to clear corresponding bit in ENDPTSETUPSTAT */
temp = usbs_imx_otg_base->endptsetupstat;
/* write '1' to clear corresponding bit in ENDPTSETUPSTAT */
temp = usbs_imx_otg_base->endptsetupstat;
(bd.buffer) =(cyg_uint8 *)(bd.buffer) + 1;
*((cyg_uint8 *)(bd.buffer)) = (cyg_uint8 )((temp & 0xFF000000)>>24);
(bd.buffer) =(cyg_uint8 *)(bd.buffer) + 1;
(bd.buffer) =(cyg_uint8 *)(bd.buffer) + 1;
*((cyg_uint8 *)(bd.buffer)) = (cyg_uint8 )((temp & 0xFF000000)>>24);
(bd.buffer) =(cyg_uint8 *)(bd.buffer) + 1;
temp = (dqh_word->dqh_word11);
*((cyg_uint8 *)(bd.buffer)) = (cyg_uint8 )(temp & 0x000000FF);
(bd.buffer) =(cyg_uint8 *)(bd.buffer) + 1;
temp = (dqh_word->dqh_word11);
*((cyg_uint8 *)(bd.buffer)) = (cyg_uint8 )(temp & 0x000000FF);
(bd.buffer) =(cyg_uint8 *)(bd.buffer) + 1;
(bd.buffer) =(cyg_uint8 *)(bd.buffer) + 1;
*((cyg_uint8 *)(bd.buffer)) = (cyg_uint8 )((temp & 0xFF000000)>>24);
(bd.buffer) =(cyg_uint8 *)(bd.buffer) + 1;
(bd.buffer) =(cyg_uint8 *)(bd.buffer) + 1;
*((cyg_uint8 *)(bd.buffer)) = (cyg_uint8 )((temp & 0xFF000000)>>24);
(bd.buffer) =(cyg_uint8 *)(bd.buffer) + 1;
/* 2. Process Setup Data*/
/* switch construct to handle different request*/
/* Parser the Setup Request Type */
/* 2. Process Setup Data*/
/* switch construct to handle different request*/
/* Parser the Setup Request Type */
case USB_SET_CONFIGURATION:
/* Handle the SET CONFIGURATION Request */
if ((g_usb_setup_data[WINDEX_LOWBYTE] == 0) &&
(g_usb_setup_data[WINDEX_HIGHBYTE] == 0)&&
(g_usb_setup_data[WLENGTH_LOWBYTE] == 0)&&
(g_usb_setup_data[WLENGTH_HIGHBYTE] == 0)&&
case USB_SET_CONFIGURATION:
/* Handle the SET CONFIGURATION Request */
if ((g_usb_setup_data[WINDEX_LOWBYTE] == 0) &&
(g_usb_setup_data[WINDEX_HIGHBYTE] == 0)&&
(g_usb_setup_data[WLENGTH_LOWBYTE] == 0)&&
(g_usb_setup_data[WLENGTH_HIGHBYTE] == 0)&&
case USB_GET_CONFIGURATION:
/* GET CONFIGURATION request handler */
usbs_handle_get_configuration();
case USB_GET_CONFIGURATION:
/* GET CONFIGURATION request handler */
usbs_handle_get_configuration();
USBDBGMSG(DEBUG_ENUM,"+USBDBGMSG:EP0 IN stalled in ep0 dsr\n");
USBDBGMSG(DEBUG_ENUM,"+USBDBGMSG:Setup Request Type 0x%02x,0x%02X\n",g_usb_setup_data[BMREQUESTTYPE],g_usb_setup_data[BREQUEST]);
break;
}
USBDBGMSG(DEBUG_ENUM,"+USBDBGMSG:EP0 IN stalled in ep0 dsr\n");
USBDBGMSG(DEBUG_ENUM,"+USBDBGMSG:Setup Request Type 0x%02x,0x%02X\n",g_usb_setup_data[BMREQUESTTYPE],g_usb_setup_data[BREQUEST]);
break;
}
USBDBGMSG(DEBUG_ENUM,"+USBDBGMSG: ep0 dsr\n");
}
/*=============================================================================
USBDBGMSG(DEBUG_ENUM,"+USBDBGMSG: ep0 dsr\n");
}
/*=============================================================================
{
#if !defined(CYGHWR_IMX_USB_DOWNLOAD_SUPPORT)
(*ep0.common.complete_fn)(&ep0.common, -EPIPE);
{
#if !defined(CYGHWR_IMX_USB_DOWNLOAD_SUPPORT)
(*ep0.common.complete_fn)(&ep0.common, -EPIPE);
/*clear all interrupt status bits*/
temp = usbs_imx_otg_base->usbsts;
usbs_imx_otg_base->usbsts = temp; //clear all the previous interrupts
/*clear all interrupt status bits*/
temp = usbs_imx_otg_base->usbsts;
usbs_imx_otg_base->usbsts = temp; //clear all the previous interrupts
/*enable all the sub-interrupt sources for USB device*/
USBS_IMX_OTG_INTR_UNMASK(IMX_USB_INTR_DEV_PCE|IMX_USB_INTR_DEV_RESET|IMX_USB_INTR_DEV_USBINT);
/*enable all the sub-interrupt sources for USB device*/
USBS_IMX_OTG_INTR_UNMASK(IMX_USB_INTR_DEV_PCE|IMX_USB_INTR_DEV_RESET|IMX_USB_INTR_DEV_USBINT);
USBDBGMSG(DEBUG_TRANS,"+USBDBGMSG: ep1_rx_complete: NULL buffer \n");
return; //there is not a buffer used to store the data from host
USBDBGMSG(DEBUG_TRANS,"+USBDBGMSG: ep1_rx_complete: NULL buffer \n");
return; //there is not a buffer used to store the data from host
/* Get Device Device Queue Head of the out endpoint */
dqh_address = USBS_EP_GET_dQH(EP1,OUT);
/* Get Device Device Queue Head of the out endpoint */
dqh_address = USBS_EP_GET_dQH(EP1,OUT);
/* Get Device Transfer Descriptor of the out endpoint */
dtd_address = USBS_EP_GET_dTD(EP1,OUT);
/* Get Device Transfer Descriptor of the out endpoint */
dtd_address = USBS_EP_GET_dTD(EP1,OUT);
/*clear the complete status */
usbs_imx_otg_base->endptcomplete |= (EPOUT_COMPLETE << EP1);
//received_buffer_addrs = (*((unsigned int *)dtd_address + 2)) & 0xFFFFF000;
received_buffer_addrs = (cyg_uint32)ep1.common.buffer;
USBDBGMSG(DEBUG_TRANS,"+USBDBGMSG: ep1_rx_complete: received_buffer_addrs 0x%08X \n",received_buffer_addrs);
/*clear the complete status */
usbs_imx_otg_base->endptcomplete |= (EPOUT_COMPLETE << EP1);
//received_buffer_addrs = (*((unsigned int *)dtd_address + 2)) & 0xFFFFF000;
received_buffer_addrs = (cyg_uint32)ep1.common.buffer;
USBDBGMSG(DEBUG_TRANS,"+USBDBGMSG: ep1_rx_complete: received_buffer_addrs 0x%08X \n",received_buffer_addrs);
/* calculate the received data length using number of bytes left in TD */
temp = (cyg_uint32 *)dtd_address;
temp++; //pointer to total bytes in dtd, second work in dTD
/* calculate the received data length using number of bytes left in TD */
temp = (cyg_uint32 *)dtd_address;
temp++; //pointer to total bytes in dtd, second work in dTD
else if((g_bulk_out_sector_number_is_one == 1)&&(received_data_length!=31)) //last bulk out data sector
g_bulk_out_transdesc_buffer_offset = 1;
#endif
else if((g_bulk_out_sector_number_is_one == 1)&&(received_data_length!=31)) //last bulk out data sector
g_bulk_out_transdesc_buffer_offset = 1;
#endif
g_received_data_type = MASS_STORAGE_DATA_TYPE;
ep1.common.complete_data = (void*)(ep1.common.buffer);
g_received_data_type = MASS_STORAGE_DATA_TYPE;
ep1.common.complete_data = (void*)(ep1.common.buffer);
ep1.common.buffer_size = 0;
ep1_start_rx((usbs_rx_endpoint *)(&(ep1.common))); //prevent to receive more CBW before processing done
}
ep1.common.buffer_size = 0;
ep1_start_rx((usbs_rx_endpoint *)(&(ep1.common))); //prevent to receive more CBW before processing done
}
}
/*=============================================================================
// Start to receive data from host. This functionality is overloaded to cope with
// waiting for stalls to complete.
}
/*=============================================================================
// Start to receive data from host. This functionality is overloaded to cope with
// waiting for stalls to complete.
=============================================================================*/
static void
ep1_start_rx(usbs_rx_endpoint* endpoint)
=============================================================================*/
static void
ep1_start_rx(usbs_rx_endpoint* endpoint)
return; //EP1 only receives data when the USB device has been configured
#if 0 //don't check to prevent EP1 from receiving data before processing the previous.
if(endpoint->buffer == NULL)
return; //EP1 only receives data when the USB device has been configured
#if 0 //don't check to prevent EP1 from receiving data before processing the previous.
if(endpoint->buffer == NULL)
#endif
/* Get Device Device Queue Head of the out endpoint */
dqh_address = USBS_EP_GET_dQH(EP1,OUT);
#endif
/* Get Device Device Queue Head of the out endpoint */
dqh_address = USBS_EP_GET_dQH(EP1,OUT);
/* Get Device Transfer Descriptor of the out endpoint */
dtd_address = USBS_EP_GET_dTD(EP1,OUT);
/* ==Prepare TD for next bulk out transfer== */
/* get the dTD buffer pointer */
buffer_addrs_page0 = (cyg_uint32)(endpoint->buffer);
/* Get Device Transfer Descriptor of the out endpoint */
dtd_address = USBS_EP_GET_dTD(EP1,OUT);
/* ==Prepare TD for next bulk out transfer== */
/* get the dTD buffer pointer */
buffer_addrs_page0 = (cyg_uint32)(endpoint->buffer);
td.next_link_ptr = dtd_address + 0x20;
td.terminate = TERMINATE;
td.total_bytes = total_bytes;
td.ioc = IOC_SET;
td.status = ACTIVE;
td.next_link_ptr = dtd_address + 0x20;
td.terminate = TERMINATE;
td.total_bytes = total_bytes;
td.ioc = IOC_SET;
td.status = ACTIVE;
- td.buffer_ptr0 = buffer_addrs_page0 ;
- td.current_offset = ( buffer_addrs_page0 & 0xFFF ) + g_td_buffer_offset;
+ td.buffer_ptr0 = buffer_addrs_page0 ;
+ td.current_offset = ( buffer_addrs_page0 & 0xFFF ) + g_td_buffer_offset;
td.buffer_ptr2 = (td.buffer_ptr1 + BULK_TD_BUFFER_PAGE_SIZE);
if(total_bytes > BULK_TD_BUFFER_PAGE_SIZE*3)
td.buffer_ptr3 = (td.buffer_ptr2 + BULK_TD_BUFFER_PAGE_SIZE);
td.buffer_ptr2 = (td.buffer_ptr1 + BULK_TD_BUFFER_PAGE_SIZE);
if(total_bytes > BULK_TD_BUFFER_PAGE_SIZE*3)
td.buffer_ptr3 = (td.buffer_ptr2 + BULK_TD_BUFFER_PAGE_SIZE);
/* Set the Transfer Descriptor */
usbs_setup_transdesc(&td);
/* 1. write dQH next ptr and dQH terminate bit to 0 */
*(volatile cyg_uint32 *)(dqh_address+0x8)= dtd_address;
/* Set the Transfer Descriptor */
usbs_setup_transdesc(&td);
/* 1. write dQH next ptr and dQH terminate bit to 0 */
*(volatile cyg_uint32 *)(dqh_address+0x8)= dtd_address;
prime bulk out endpoint after sending the CSW of last command
*/
//usbs_imx_otg_base->endptprime |= ( EPOUT_PRIME << EP1 );
prime bulk out endpoint after sending the CSW of last command
*/
//usbs_imx_otg_base->endptprime |= ( EPOUT_PRIME << EP1 );
// Updating the stalled flag means that the DSR will do nothing.
usbs_endpoint_stall(EP1,OUT);
ep1.common.halted = 1;
// Updating the stalled flag means that the DSR will do nothing.
usbs_endpoint_stall(EP1,OUT);
ep1.common.halted = 1;
{
int result = 0; //contains the actual recevied data length from bulk-out endpoint
g_received_data_type = 0;//MASS_STORAGE_CBW_TYPE
{
int result = 0; //contains the actual recevied data length from bulk-out endpoint
g_received_data_type = 0;//MASS_STORAGE_CBW_TYPE
if(ep1.common.buffer)//buffer of TD is not null, then receive
{
ep1_rx_complete(result);
}
//USBDBGMSG(DEBUG_TRANS,"+USBDBGMSG: ep1 dsr - result = %d\n",result);
//recevie mass storage device CBW
if(ep1.common.buffer)//buffer of TD is not null, then receive
{
ep1_rx_complete(result);
}
//USBDBGMSG(DEBUG_TRANS,"+USBDBGMSG: ep1 dsr - result = %d\n",result);
//recevie mass storage device CBW
if((ep1.fetched == 31)&&(g_received_data_type == MASS_STORAGE_CBW_TYPE))
{
USBDBGMSG(DEBUG_TRANS,"+USBDBGMSG: ep1 dsr - CBW received\n");
if((ep1.fetched == 31)&&(g_received_data_type == MASS_STORAGE_CBW_TYPE))
{
USBDBGMSG(DEBUG_TRANS,"+USBDBGMSG: ep1 dsr - CBW received\n");
// Endpoints should never be halted during a start-up.
ep1.common.halted = 0; //false =0, true =1
ep1.common.complete_fn = ep1_rx_complete;
// Endpoints should never be halted during a start-up.
ep1.common.halted = 0; //false =0, true =1
ep1.common.complete_fn = ep1_rx_complete;
{
void (*complete_fn)(void*, int) = ep2.common.complete_fn;
void* complete_data = ep2.common.complete_data;
{
void (*complete_fn)(void*, int) = ep2.common.complete_fn;
void* complete_data = ep2.common.complete_data;
ep2.common.buffer = (unsigned char*) 0;
ep2.common.buffer_size = 0;
ep2.common.complete_fn = (void (*)(void*, int)) 0;
ep2.common.complete_data = (void*) 0;
ep2.common.buffer = (unsigned char*) 0;
ep2.common.buffer_size = 0;
ep2.common.complete_fn = (void (*)(void*, int)) 0;
ep2.common.complete_data = (void*) 0;
- if ((void (*)(void*, int))0 != complete_fn) {
- (*complete_fn)(complete_data, result);
+ if (NULL != complete_fn) {
+ complete_fn(complete_data, result);
/* Get Device Transfer Descriptor of the requested endpoint */
dtd_address = USBS_EP_GET_dTD(EP2,IN);
/* Get Device Transfer Descriptor of the requested endpoint */
dtd_address = USBS_EP_GET_dTD(EP2,IN);
total_bytes = (cyg_uint32)(endpoint->buffer_size);
size = (total_bytes < BULK_TD_BUFFER_TOTAL_SIZE )?total_bytes:(BULK_TD_BUFFER_TOTAL_SIZE);
total_bytes = (cyg_uint32)(endpoint->buffer_size);
size = (total_bytes < BULK_TD_BUFFER_TOTAL_SIZE )?total_bytes:(BULK_TD_BUFFER_TOTAL_SIZE);
td.next_link_ptr = dtd_address + 0x20 ;
td.terminate = TERMINATE;
td.total_bytes = size;
td.ioc = IOC_SET;
td.status = ACTIVE;
td.buffer_ptr0 = buffer_addrs_page0 ;
td.next_link_ptr = dtd_address + 0x20 ;
td.terminate = TERMINATE;
td.total_bytes = size;
td.ioc = IOC_SET;
td.status = ACTIVE;
td.buffer_ptr0 = buffer_addrs_page0 ;
/* 2. clear active & halt bit in dQH */
*(volatile cyg_uint32 *)(dqh_address+0xC) &= ~0xFF;
/* 3. prime endpoint by writing '1' in ENDPTPRIME */
usbs_imx_otg_base->endptprime = ( EPIN_PRIME << EP2 );
/* 2. clear active & halt bit in dQH */
*(volatile cyg_uint32 *)(dqh_address+0xC) &= ~0xFF;
/* 3. prime endpoint by writing '1' in ENDPTPRIME */
usbs_imx_otg_base->endptprime = ( EPIN_PRIME << EP2 );
/* wait for complete set and clear */
while (!((usbs_imx_otg_base->endptcomplete) & (EPIN_COMPLETE<<EP2)));
/* wait for complete set and clear */
while (!((usbs_imx_otg_base->endptcomplete) & (EPIN_COMPLETE<<EP2)));
}
/*=============================================================================
// The exported interface to halt the EP2
}
/*=============================================================================
// The exported interface to halt the EP2
// Updating the stalled flag means that the DSR will do nothing.
usbs_endpoint_stall(EP2,IN);
ep2.common.halted = 1;
// Updating the stalled flag means that the DSR will do nothing.
usbs_endpoint_stall(EP2,IN);
ep2.common.halted = 1;
/* EP2 DSR will be called as soon as a transfer complete to clear status*/
usbs_imx_otg_base->endptcomplete |= (EPIN_COMPLETE << EP2);
/* EP2 DSR will be called as soon as a transfer complete to clear status*/
usbs_imx_otg_base->endptcomplete |= (EPIN_COMPLETE << EP2);
// Reset is special, since it invalidates everything else.
// If the reset is still ongoing then do not attempt any
// further processing, there will just be another interrupt.
// Reset is special, since it invalidates everything else.
// If the reset is still ongoing then do not attempt any
// further processing, there will just be another interrupt.
// immediately if reset is still asserted, i.e. no threads
// will run, but there is no easy way of triggering action
// at the end of reset.
// immediately if reset is still asserted, i.e. no threads
// will run, but there is no easy way of triggering action
// at the end of reset.
{
usbs_imx_otg_dev_handle_bus_reset();
USBDBGMSG(DEBUG_BASIC,"+USBDBGMSG: !!USB BUS RESET\n");
{
usbs_imx_otg_dev_handle_bus_reset();
USBDBGMSG(DEBUG_BASIC,"+USBDBGMSG: !!USB BUS RESET\n");
// This unmask is likely to cause another interrupt immediately
#if !defined(CYGHWR_IMX_USB_DOWNLOAD_SUPPORT)
cyg_interrupt_unmask(MX51_IRQ_USB_SERVICE_REQUEST);
#endif
// This unmask is likely to cause another interrupt immediately
#if !defined(CYGHWR_IMX_USB_DOWNLOAD_SUPPORT)
cyg_interrupt_unmask(MX51_IRQ_USB_SERVICE_REQUEST);
#endif
{
#if !defined(CYGHWR_IMX_USB_DOWNLOAD_SUPPORT)
// This unmask is likely to cause another interrupt immediately
cyg_interrupt_unmask(MX51_IRQ_USB_SERVICE_REQUEST);
#endif
{
#if !defined(CYGHWR_IMX_USB_DOWNLOAD_SUPPORT)
// This unmask is likely to cause another interrupt immediately
cyg_interrupt_unmask(MX51_IRQ_USB_SERVICE_REQUEST);
#endif
CYG_ASSERT( 0 != isr_status_bits, "DSR's should only be scheduled when there is work to do");
cyg_semaphore_post(&usbs_imx_otg_dev_sem);
CYG_ASSERT( 0 != isr_status_bits, "DSR's should only be scheduled when there is work to do");
cyg_semaphore_post(&usbs_imx_otg_dev_sem);
CYG_UNUSED_PARAM(cyg_vector_t, vector);
CYG_UNUSED_PARAM(cyg_ucount32, count);
CYG_UNUSED_PARAM(cyg_addrword_t, data);
CYG_UNUSED_PARAM(cyg_vector_t, vector);
CYG_UNUSED_PARAM(cyg_ucount32, count);
CYG_UNUSED_PARAM(cyg_addrword_t, data);
// interrupts in the control register.
status_bits = usbs_imx_otg_base->usbsts;
USBDBGMSG(DEBUG_BASIC,"+USBDBGMSG: usb intr 0x%08X\n",status_bits);
// interrupts in the control register.
status_bits = usbs_imx_otg_base->usbsts;
USBDBGMSG(DEBUG_BASIC,"+USBDBGMSG: usb intr 0x%08X\n",status_bits);
g_isr_status_bits |= IMX_USB_STS_RESET;
usbs_imx_otg_base->usbsts |= IMX_USB_STS_RESET;
cyg_interrupt_mask(IMX_IRQ_USB_DEV_SERVICE_REQUEST);
g_isr_status_bits |= IMX_USB_STS_RESET;
usbs_imx_otg_base->usbsts |= IMX_USB_STS_RESET;
cyg_interrupt_mask(IMX_IRQ_USB_DEV_SERVICE_REQUEST);
else if(status_bits & IMX_USB_STS_USBINT)
{
g_isr_status_bits |= IMX_USB_STS_USBINT;
usbs_imx_otg_base->usbsts |= IMX_USB_STS_USBINT;
cyg_interrupt_mask(IMX_IRQ_USB_DEV_SERVICE_REQUEST);
}
else if(status_bits & IMX_USB_STS_USBINT)
{
g_isr_status_bits |= IMX_USB_STS_USBINT;
usbs_imx_otg_base->usbsts |= IMX_USB_STS_USBINT;
cyg_interrupt_mask(IMX_IRQ_USB_DEV_SERVICE_REQUEST);
}
{
usbs_imx_otg_base->usbsts = status_bits; //clear the status bit of USBSTS
g_isr_status_bits &= ~status_bits;
{
usbs_imx_otg_base->usbsts = status_bits; //clear the status bit of USBSTS
g_isr_status_bits &= ~status_bits;
usbs_imx_otg_dev_poll(usbs_control_endpoint* endpoint)
{
CYG_ASSERT( endpoint == &ep0.common, "USB poll involves the wrong endpoint");
usbs_imx_otg_dev_poll(usbs_control_endpoint* endpoint)
{
CYG_ASSERT( endpoint == &ep0.common, "USB poll involves the wrong endpoint");
{
// Reset was detected the last time poll() was invoked. If
// reset is still active, do nothing. Once the reset has
// completed things can continue.
{
// Reset was detected the last time poll() was invoked. If
// reset is still active, do nothing. Once the reset has
// completed things can continue.
else if (IMX_USB_STS_USBINT & g_isr_status_bits)
{
usbs_imx_otg_dev_dsr(IMX_IRQ_USB_DEV_SERVICE_REQUEST, 0, (cyg_addrword_t) 0);
else if (IMX_USB_STS_USBINT & g_isr_status_bits)
{
usbs_imx_otg_dev_dsr(IMX_IRQ_USB_DEV_SERVICE_REQUEST, 0, (cyg_addrword_t) 0);
usbs_imx_otg_base->usbcmd &= ~BIT0; //detach device from bus temprorarily
usbs_imx_otg_base->usbsts |= BIT6; //clear reset bit in USBSTS
//temp = usbs_imx_otg_base->usbsts;
//usbs_imx_otg_base->usbsts = temp;
usbs_imx_otg_base->usbcmd &= ~BIT0; //detach device from bus temprorarily
usbs_imx_otg_base->usbsts |= BIT6; //clear reset bit in USBSTS
//temp = usbs_imx_otg_base->usbsts;
//usbs_imx_otg_base->usbsts = temp;
/*1. Reading and writing back the ENDPTSETUPSTAT register
clears the setup token semaphores */
temp = usbs_imx_otg_base->endptsetupstat;
/*1. Reading and writing back the ENDPTSETUPSTAT register
clears the setup token semaphores */
temp = usbs_imx_otg_base->endptsetupstat;
clears the endpoint complete status bits */
temp = usbs_imx_otg_base->endptcomplete;
usbs_imx_otg_base->endptcomplete = temp;
clears the endpoint complete status bits */
temp = usbs_imx_otg_base->endptcomplete;
usbs_imx_otg_base->endptcomplete = temp;
/*3. Cancel all primed status by waiting until all bits in ENDPTPRIME are 0
and then write 0xFFFFFFFF to ENDPTFLUSH */
/*3. Cancel all primed status by waiting until all bits in ENDPTPRIME are 0
and then write 0xFFFFFFFF to ENDPTFLUSH */
usbs_imx_otg_base->usbcmd |= BIT0; //re-attach device to the bus
g_usb_dev_state = USB_DEV_DEFAULT_STATE;
usbs_imx_otg_base->usbcmd |= BIT0; //re-attach device to the bus
g_usb_dev_state = USB_DEV_DEFAULT_STATE;
}
/*=============================================================================
// Perform port change operations on all endpoints that have been
}
/*=============================================================================
// Perform port change operations on all endpoints that have been
FUNCTION: usbs_imx_otg_dev_set_configuration
DESCRIPTION: This function Handle the SET CONFIGRATION Request.
ARGUMENTS PASSED: usb_end_pt_info_t* config_data;
FUNCTION: usbs_imx_otg_dev_set_configuration
DESCRIPTION: This function Handle the SET CONFIGRATION Request.
ARGUMENTS PASSED: usb_end_pt_info_t* config_data;
=============================================================================*/
static void
usbs_imx_otg_dev_set_configuration(usb_end_pt_info_t* config_data)
=============================================================================*/
static void
usbs_imx_otg_dev_set_configuration(usb_end_pt_info_t* config_data)
cyg_uint32 dqh_address = 0;
cyg_uint32 dtd_address = 0;
cyg_uint8 endpt_num,direction;
cyg_uint32 dqh_address = 0;
cyg_uint32 dtd_address = 0;
cyg_uint8 endpt_num,direction;
direction= config_data->direction;
USBDBGMSG(DEBUG_BASIC,"+USBDBGMSG: set config - ep%d\n",endpt_num);
/* Check if the endpoint number and direction is withing the permitted range or not */
direction= config_data->direction;
USBDBGMSG(DEBUG_BASIC,"+USBDBGMSG: set config - ep%d\n",endpt_num);
/* Check if the endpoint number and direction is withing the permitted range or not */
dtd_address = USBS_EP_GET_dTD(endpt_num,direction);
if ( direction == OUT )
{
total_bytes = BULK_BUFFER_SIZE ;
dtd_address = USBS_EP_GET_dTD(endpt_num,direction);
if ( direction == OUT )
{
total_bytes = BULK_BUFFER_SIZE ;
/* Endpoint 1 : MPS = 64, OUT (Rx endpoint) */
usbs_imx_otg_base->endptctrl[endpt_num] = 0x00080048;
/* Enable EP1 OUT */
usbs_imx_otg_base->endptctrl[endpt_num] |= EPOUT_ENABLE;
/* Endpoint 1 : MPS = 64, OUT (Rx endpoint) */
usbs_imx_otg_base->endptctrl[endpt_num] = 0x00080048;
/* Enable EP1 OUT */
usbs_imx_otg_base->endptctrl[endpt_num] |= EPOUT_ENABLE;
/* allocate buffer for receiving data */
/* free the usb buffer after re-enumeration*/
//g_bulkbuffer_map.buffer1_status = BUFFER_FREE;
//g_bulkbuffer_map.buffer2_status = BUFFER_FREE;
g_bulkbuffer_a.stat = BUFFER_FREED;
/* allocate buffer for receiving data */
/* free the usb buffer after re-enumeration*/
//g_bulkbuffer_map.buffer1_status = BUFFER_FREE;
//g_bulkbuffer_map.buffer2_status = BUFFER_FREE;
g_bulkbuffer_a.stat = BUFFER_FREED;
//buffer_addrs_page0 = util_alloc_buffer();
ep1.common.buffer = g_bulkbuffer_a.buffer;
ep1.common.buffer_size = total_bytes;
g_bulkbuffer_a.stat = BUFFER_ALLOCATED;
buffer_addrs_page0 = (cyg_uint32)(ep1.common.buffer);
//buffer_addrs_page0 = util_alloc_buffer();
ep1.common.buffer = g_bulkbuffer_a.buffer;
ep1.common.buffer_size = total_bytes;
g_bulkbuffer_a.stat = BUFFER_ALLOCATED;
buffer_addrs_page0 = (cyg_uint32)(ep1.common.buffer);
/* Set the Transfer Descriptor */
usbs_setup_transdesc(&td);
/* 1. write dQH next ptr and dQH terminate bit to 0 */
/* Set the Transfer Descriptor */
usbs_setup_transdesc(&td);
/* 1. write dQH next ptr and dQH terminate bit to 0 */
/* 3. prime endpoint by writing '1' in ENDPTPRIME */
usbs_imx_otg_base->endptprime |= ( EPOUT_PRIME << endpt_num );
/* Endpoint Configured for output */
g_out_endpoint= endpt_num;
/* 3. prime endpoint by writing '1' in ENDPTPRIME */
usbs_imx_otg_base->endptprime |= ( EPOUT_PRIME << endpt_num );
/* Endpoint Configured for output */
g_out_endpoint= endpt_num;
qhead.dqh_base = USBS_EP_GET_dQH(endpt_num,direction);
qhead.zlt = ZLT_DISABLE;
qhead.mps = config_data->max_pkt_size;
qhead.dqh_base = USBS_EP_GET_dQH(endpt_num,direction);
qhead.zlt = ZLT_DISABLE;
qhead.mps = config_data->max_pkt_size;
/* Endpoint 2: MPS = 64, IN (Tx endpoint) */
usbs_imx_otg_base->endptctrl[endpt_num] = 0x00480008;
/* Enable EP2 IN */
usbs_imx_otg_base->endptctrl[endpt_num] |= EPIN_ENABLE;
/* Endpoint 2: MPS = 64, IN (Tx endpoint) */
usbs_imx_otg_base->endptctrl[endpt_num] = 0x00480008;
/* Enable EP2 IN */
usbs_imx_otg_base->endptctrl[endpt_num] |= EPIN_ENABLE;
/* 3. prime endpoint by writing '1' in ENDPTPRIME */
usbs_imx_otg_base->endptprime |= (EPIN_PRIME << g_in_endpoint);
/* 3. prime endpoint by writing '1' in ENDPTPRIME */
usbs_imx_otg_base->endptprime |= (EPIN_PRIME << g_in_endpoint);
- /*Configure plldivvalue of USB_PHY_CTRL_1_REG for 24 Mhz*/
- temp = *(volatile cyg_uint32 *)USB_PHY_CTRL_1_REG;
- temp &= ~USB_PHY_CTRL_PLLDIVVALUE_MASK;
- temp |= USB_PHY_CTRL_PLLDIVVALUE_24_MHZ;
+ /*Configure plldivvalue of USB_PHY_CTRL_1_REG for 24 Mhz*/
+ temp = *(volatile cyg_uint32 *)USB_PHY_CTRL_1_REG;
+ temp &= ~USB_PHY_CTRL_PLLDIVVALUE_MASK;
+ temp |= USB_PHY_CTRL_PLLDIVVALUE_24_MHZ;
{/*Setup USB Buffer Map*/
config_data_ptr.buffer_address = (cyg_uint32)usb_buffer;
config_data_ptr.buffer_size = BUFFER_SIZE;
{/*Setup USB Buffer Map*/
config_data_ptr.buffer_address = (cyg_uint32)usb_buffer;
config_data_ptr.buffer_size = BUFFER_SIZE;
/* Base address of the buffer allocated to IP Layer */
g_bulkbuffer_address_base = config_data_ptr.buffer_address;
/* Base address of the buffer allocated to IP Layer */
g_bulkbuffer_address_base = config_data_ptr.buffer_address;
/* Maximum Number of EPs to be confiured */
g_max_ep_supported = (( g_bulkbuffer_length - TOTAL_DATA_BUFFER_SIZE)/(BUFFER_USED_PER_EP)); //=(2048-1088)/256~=3.75->3
/* Maximum Number of EPs to be confiured */
g_max_ep_supported = (( g_bulkbuffer_length - TOTAL_DATA_BUFFER_SIZE)/(BUFFER_USED_PER_EP)); //=(2048-1088)/256~=3.75->3
/* Total size of qhead */
temp = (SIZE_OF_QHD * (g_max_ep_supported * 2)); //total size of QH is 384byte
/* Base Address of dTDs */
g_bulkbuffer_map.ep_dtd_base_addrs = (g_bulkbuffer_map.ep_dqh_base_addrs + temp);
/* Total size of qhead */
temp = (SIZE_OF_QHD * (g_max_ep_supported * 2)); //total size of QH is 384byte
/* Base Address of dTDs */
g_bulkbuffer_map.ep_dtd_base_addrs = (g_bulkbuffer_map.ep_dqh_base_addrs + temp);
/* Base Address of EP0 Buffer */
g_bulkbuffer_map.ep0_buffer_addrs = (g_bulkbuffer_map.ep_dtd_base_addrs + temp ); //256byte
/* Base Address of EP0 Buffer */
g_bulkbuffer_map.ep0_buffer_addrs = (g_bulkbuffer_map.ep_dtd_base_addrs + temp ); //256byte
/*Bulk Buffer Areas, 512byte per buffer*/
/*Actually, the dual 512 byte bulk buffers are not used, because two larger 16kB bulk buffers are used*/
/*Bulk Buffer Areas, 512byte per buffer*/
/*Actually, the dual 512 byte bulk buffers are not used, because two larger 16kB bulk buffers are used*/
g_bulkbuffer_map.buffer1_address=(g_bulkbuffer_address_base + g_bulkbuffer_length -(BULK_BUFFER_SIZE*NUM_OF_BULK_BUFFER));
g_bulkbuffer_map.buffer1_status = BUFFER_FREE;
g_bulkbuffer_map.buffer1_address=(g_bulkbuffer_address_base + g_bulkbuffer_length -(BULK_BUFFER_SIZE*NUM_OF_BULK_BUFFER));
g_bulkbuffer_map.buffer1_status = BUFFER_FREE;
g_bulkbuffer_map.buffer2_address = g_bulkbuffer_map.buffer1_address + BULK_BUFFER_SIZE;
g_bulkbuffer_map.buffer2_status = BUFFER_FREE;
}
g_bulkbuffer_map.buffer2_address = g_bulkbuffer_map.buffer1_address + BULK_BUFFER_SIZE;
g_bulkbuffer_map.buffer2_status = BUFFER_FREE;
}
{/*Set USB OTG at device only mode*/
usbs_imx_otg_base->usbmode = 0x2; //set OTG as a device controller
temp = 0xA5A55A5A;
{/*Set USB OTG at device only mode*/
usbs_imx_otg_base->usbmode = 0x2; //set OTG as a device controller
temp = 0xA5A55A5A;
usbs_imx_otg_base->usbmode |= BIT3; // Disable Setup Lockout by writing '1' to SLOM in USBMODE
//usbs_imx_otg_base->usbcmd |= BIT0; // Set Run/Stop bit to Run Mode, make USB run in usbs_imx_otg_dev_ep0_start()
}
usbs_imx_otg_base->usbmode |= BIT3; // Disable Setup Lockout by writing '1' to SLOM in USBMODE
//usbs_imx_otg_base->usbcmd |= BIT0; // Set Run/Stop bit to Run Mode, make USB run in usbs_imx_otg_dev_ep0_start()
}
g_usb_desc.device_desc = &g_usb_device_desc ;
g_usb_desc.config_desc = &g_usb_config_desc;
g_usb_desc.sn_desc = &g_usb_serialnumber_desc;
g_usb_desc.device_desc = &g_usb_device_desc ;
g_usb_desc.config_desc = &g_usb_config_desc;
g_usb_desc.sn_desc = &g_usb_serialnumber_desc;
g_usb_desc.str_desc1 = &g_usb_otg_string_desc1; //Manufacturer desc
g_usb_desc.str_desc2 = &g_usb_otg_string_desc2; //USB Name Desc
g_usb_desc.str_desc3 = &g_usb_otg_string_desc3; //Device Name Desc
g_usb_desc.str_desc1 = &g_usb_otg_string_desc1; //Manufacturer desc
g_usb_desc.str_desc2 = &g_usb_otg_string_desc2; //USB Name Desc
g_usb_desc.str_desc3 = &g_usb_otg_string_desc3; //Device Name Desc
/* Get Number of Endpoints supported from Configuration Descriptor*/
g_number_of_endpoints = g_usb_desc.config_desc->usb_interface_desc.number_endpoints;
/* Get Number of Endpoints supported from Configuration Descriptor*/
g_number_of_endpoints = g_usb_desc.config_desc->usb_interface_desc.number_endpoints;
/* Store the Endpoint specific information in local variable structure to this Layer */
for ( i = 0 ; i< g_number_of_endpoints ; i++)
{
/* Store the Endpoint specific information in local variable structure to this Layer */
for ( i = 0 ; i< g_number_of_endpoints ; i++)
{
g_end_pt_info[i].max_pkt_size = ((g_usb_desc.config_desc->usb_endpoint_desc[i].max_packet_lo) \
| (( g_usb_desc.config_desc->usb_endpoint_desc[i].max_packet_hi ) << 8 ));
}
g_end_pt_info[i].max_pkt_size = ((g_usb_desc.config_desc->usb_endpoint_desc[i].max_packet_lo) \
| (( g_usb_desc.config_desc->usb_endpoint_desc[i].max_packet_hi ) << 8 ));
}
// ****************************************************************************
/*=============================================================================
// Initialization i.MX37(Marley) USB OTG Hardware
// ****************************************************************************
/*=============================================================================
// Initialization i.MX37(Marley) USB OTG Hardware
-// This function is the only extern function of this device driver, and it
-// registers the driver ISR and DSRs to the kernel.
+// This function is the only extern function of this device driver, and it
+// registers the driver ISR and DSRs to the kernel.
USBDBGMSG(DEBUG_BASIC,"+USBDBGMSG: USB Device Driver Start Initializing...\n");
USBDBGMSG(DEBUG_BASIC,"+USBDBGMSG: USB OTG REG BASE@0x%08X\n",USB_BASE_ADDRESS);
g_usb_setup_data = ep0.common.control_buffer;
USBDBGMSG(DEBUG_BASIC,"+USBDBGMSG: USB Device Driver Start Initializing...\n");
USBDBGMSG(DEBUG_BASIC,"+USBDBGMSG: USB OTG REG BASE@0x%08X\n",USB_BASE_ADDRESS);
g_usb_setup_data = ep0.common.control_buffer;
g_td_buffer_offset = 0;
#if !defined(CYGHWR_IMX_USB_DOWNLOAD_SUPPORT)
USB_IMX_SET_TD_OFFSET(g_td_buffer_offset,1);
g_td_buffer_offset = 0;
#if !defined(CYGHWR_IMX_USB_DOWNLOAD_SUPPORT)
USB_IMX_SET_TD_OFFSET(g_td_buffer_offset,1);
USBDBGMSG(DEBUG_BASIC,"+USBDBGMSG: Usb Hardware Initialize Complete.\n");
usbs_imx_otg_dev_ep0_init();
USBDBGMSG(DEBUG_BASIC,"+USBDBGMSG: Usb Ep0 Initialize Complete.\n");
usbs_imx_otg_dev_ep1_init();
USBDBGMSG(DEBUG_BASIC,"+USBDBGMSG: Usb Ep1 Initialize Complete.\n");
usbs_imx_otg_dev_ep2_init();
USBDBGMSG(DEBUG_BASIC,"+USBDBGMSG: Usb Hardware Initialize Complete.\n");
usbs_imx_otg_dev_ep0_init();
USBDBGMSG(DEBUG_BASIC,"+USBDBGMSG: Usb Ep0 Initialize Complete.\n");
usbs_imx_otg_dev_ep1_init();
USBDBGMSG(DEBUG_BASIC,"+USBDBGMSG: Usb Ep1 Initialize Complete.\n");
usbs_imx_otg_dev_ep2_init();
#if !defined(CYGHWR_IMX_USB_DOWNLOAD_SUPPORT)
cyg_semaphore_init(&usbs_imx_otg_dev_sem, 0);
#if !defined(CYGHWR_IMX_USB_DOWNLOAD_SUPPORT)
cyg_semaphore_init(&usbs_imx_otg_dev_sem, 0);
cyg_interrupt_create(IMX_IRQ_USB_DEV_SERVICE_REQUEST,
IMX_IRQ_USB_DEV_PRIORITY, // priority
0, // data
cyg_interrupt_create(IMX_IRQ_USB_DEV_SERVICE_REQUEST,
IMX_IRQ_USB_DEV_PRIORITY, // priority
0, // data
&usbs_imx_otg_dev_thread_dsr,
&g_usbs_dev_intr_handle,
&g_usbs_dev_intr_data);
USBDBGMSG(DEBUG_BASIC,"+USBDBGMSG: cyg_interrupt_create@vector %d.\n",IMX_IRQ_USB_DEV_SERVICE_REQUEST);
&usbs_imx_otg_dev_thread_dsr,
&g_usbs_dev_intr_handle,
&g_usbs_dev_intr_data);
USBDBGMSG(DEBUG_BASIC,"+USBDBGMSG: cyg_interrupt_create@vector %d.\n",IMX_IRQ_USB_DEV_SERVICE_REQUEST);
USBDBGMSG(DEBUG_BASIC,"+USBDBGMSG: cyg_interrupt_attach.\n");
cyg_interrupt_unmask(IMX_IRQ_USB_DEV_SERVICE_REQUEST); //enable USB interrrupt
USBDBGMSG(DEBUG_BASIC,"+USBDBGMSG: cyg_interrupt_unmask.\n");
USBDBGMSG(DEBUG_BASIC,"+USBDBGMSG: cyg_interrupt_attach.\n");
cyg_interrupt_unmask(IMX_IRQ_USB_DEV_SERVICE_REQUEST); //enable USB interrrupt
USBDBGMSG(DEBUG_BASIC,"+USBDBGMSG: cyg_interrupt_unmask.\n");
usbs_imx_otg_device_deinit(void) //works like usb port close
{
usbs_imx_otg_base->usbcmd &= (~BIT0); // Set Run/Stop bit to Stop Mode
usbs_imx_otg_device_deinit(void) //works like usb port close
{
usbs_imx_otg_base->usbcmd &= (~BIT0); // Set Run/Stop bit to Stop Mode
/* Check if Reset is already received and Setup Token Received */
if((usbs_imx_otg_base->endptsetupstat) & BIT0)
{
/* Handle Setup Token */
usbs_imx_otg_dev_ep0_dsr();
}
/* Check if Reset is already received and Setup Token Received */
if((usbs_imx_otg_base->endptsetupstat) & BIT0)
{
/* Handle Setup Token */
usbs_imx_otg_dev_ep0_dsr();
}
return ( bytes_received );
}
static usb_status_t usb_tx_processing(cyg_uint8* write_ptr, cyg_uint32 data_len)
return ( bytes_received );
}
static usb_status_t usb_tx_processing(cyg_uint8* write_ptr, cyg_uint32 data_len)
buf_desc.buffer = (void *)write_ptr;
buf_desc.size = data_len;
buf_desc.bytes_transfered = 0;
buf_desc.buffer = (void *)write_ptr;
buf_desc.size = data_len;
buf_desc.bytes_transfered = 0;
//if(g_timeout_value%1000==0) D("C");
//D("%d\n",g_timeout_value);
bytes_recvd = usb_rx_processing(sdp_payload_data, &status, SDP_CMD_MAX_LEN);
//if(g_timeout_value%1000==0) D("C");
//D("%d\n",g_timeout_value);
bytes_recvd = usb_rx_processing(sdp_payload_data, &status, SDP_CMD_MAX_LEN);
if(g_timeout_value == USB_DOWNLOAD_TIMEOUT_LIMIT) return false;
}
//D("+USBDBGMSG: start_command = 0x%02X\n",start_command);
if(g_timeout_value == USB_DOWNLOAD_TIMEOUT_LIMIT) return false;
}
//D("+USBDBGMSG: start_command = 0x%02X\n",start_command);
{
//receive rest of the bytes
bytes_recvd = usb_rx_processing(sdp_payload_data, &status, start_command);
{
//receive rest of the bytes
bytes_recvd = usb_rx_processing(sdp_payload_data, &status, start_command);
(sdp_payload_data[i] == 0x07) && (sdp_payload_data[i+1] == 0x07) ||
(sdp_payload_data[i] == 0x08) && (sdp_payload_data[i+1] == 0x08) ||
(sdp_payload_data[i] == 0x09) && (sdp_payload_data[i+1] == 0x09) ||
(sdp_payload_data[i] == 0x07) && (sdp_payload_data[i+1] == 0x07) ||
(sdp_payload_data[i] == 0x08) && (sdp_payload_data[i+1] == 0x08) ||
(sdp_payload_data[i] == 0x09) && (sdp_payload_data[i+1] == 0x09) ||
{
case WRITE_FILE:
//D("+USBDBGMSG: usb download file to address 0x%08X, length %d\n",usb_download_address,ByteCount);
{
case WRITE_FILE:
//D("+USBDBGMSG: usb download file to address 0x%08X, length %d\n",usb_download_address,ByteCount);
//pl_handle_write_file(Address, ByteCount);
//if(g_load_cycle==0) usb_download_address=Address;
//g_load_cycle ++;
usb_download_address += ByteCount;
usb_download_length +=ByteCount;
D(".");
//pl_handle_write_file(Address, ByteCount);
//if(g_load_cycle==0) usb_download_address=Address;
//g_load_cycle ++;
usb_download_address += ByteCount;
usb_download_length +=ByteCount;
D(".");
usb_rx_processing((cyg_uint8*)address, &status, total_bytes);
}
static void pl_command_ack(cyg_uint32 ack)
{
usb_tx_processing((cyg_uint8*)&ack, SDP_CMD_ACK_LEN);
usb_rx_processing((cyg_uint8*)address, &status, total_bytes);
}
static void pl_command_ack(cyg_uint32 ack)
{
usb_tx_processing((cyg_uint8*)&ack, SDP_CMD_ACK_LEN);
usbs_imx_otg_download(unsigned char * buffer, unsigned int length)
{
cyg_bool bytes_recvd = false;
usbs_imx_otg_download(unsigned char * buffer, unsigned int length)
{
cyg_bool bytes_recvd = false;
/* Check if Reset is already received and Setup Token Received */
if((g_usb_dev_state != USB_DEV_DUMMY_STATE) && (usbs_imx_otg_base->endptsetupstat & BIT0))
{
/* Handle Setup Token */
usbs_imx_otg_dev_ep0_dsr();
/* Check if Reset is already received and Setup Token Received */
if((g_usb_dev_state != USB_DEV_DUMMY_STATE) && (usbs_imx_otg_base->endptsetupstat & BIT0))
{
/* Handle Setup Token */
usbs_imx_otg_dev_ep0_dsr();
- g_usb_download_state = pl_handle_command(g_error_status);
- }
-
- if((g_usb_download_state==COMPLETE)||(g_timeout_value == USB_DOWNLOAD_TIMEOUT_LIMIT))
+ g_usb_download_state = pl_handle_command(g_error_status);
+ }
+
+ if((g_usb_download_state==COMPLETE)||(g_timeout_value == USB_DOWNLOAD_TIMEOUT_LIMIT))
D("USB file download complete\n");
//D("+usbdownload: image base 0x%08X, length %d\n",usb_download_address,usb_download_length);
}
D("USB file download complete\n");
//D("+usbdownload: image base 0x%08X, length %d\n",usb_download_address,usb_download_length);
}