4 Commits

Author SHA1 Message Date
slimih
5af065de85 Release v2.8.0 2021-03-16 12:39:31 +01:00
slimih
60d163f271 Release v2.7.1 2020-08-31 09:19:23 +01:00
slimih
d1a9b6baea Release v2.7.0 2020-08-31 08:40:19 +01:00
slimih
edbaa3cd1d Release v2.6.1 2020-07-20 14:58:08 +01:00
48 changed files with 6272 additions and 2527 deletions

View File

@@ -157,13 +157,17 @@ __ALIGN_BEGIN static uint8_t USBD_AUDIO_CfgDesc[USB_AUDIO_CONFIG_DESC_SIZ] __ALI
/* Configuration 1 */ /* Configuration 1 */
0x09, /* bLength */ 0x09, /* bLength */
USB_DESC_TYPE_CONFIGURATION, /* bDescriptorType */ USB_DESC_TYPE_CONFIGURATION, /* bDescriptorType */
LOBYTE(USB_AUDIO_CONFIG_DESC_SIZ), /* wTotalLength 109 bytes*/ LOBYTE(USB_AUDIO_CONFIG_DESC_SIZ), /* wTotalLength */
HIBYTE(USB_AUDIO_CONFIG_DESC_SIZ), HIBYTE(USB_AUDIO_CONFIG_DESC_SIZ),
0x02, /* bNumInterfaces */ 0x02, /* bNumInterfaces */
0x01, /* bConfigurationValue */ 0x01, /* bConfigurationValue */
0x00, /* iConfiguration */ 0x00, /* iConfiguration */
0xC0, /* bmAttributes BUS Powred*/ #if (USBD_SELF_POWERED == 1U)
0x32, /* bMaxPower = 100 mA*/ 0xC0, /* bmAttributes: Bus Powered according to user configuration */
#else
0x80, /* bmAttributes: Bus Powered according to user configuration */
#endif
USBD_MAX_POWER, /* MaxPower (mA) */
/* 09 byte*/ /* 09 byte*/
/* USB Speaker Standard interface descriptor */ /* USB Speaker Standard interface descriptor */
@@ -184,7 +188,7 @@ __ALIGN_BEGIN static uint8_t USBD_AUDIO_CfgDesc[USB_AUDIO_CONFIG_DESC_SIZ] __ALI
AUDIO_CONTROL_HEADER, /* bDescriptorSubtype */ AUDIO_CONTROL_HEADER, /* bDescriptorSubtype */
0x00, /* 1.00 */ /* bcdADC */ 0x00, /* 1.00 */ /* bcdADC */
0x01, 0x01,
0x27, /* wTotalLength = 39*/ 0x27, /* wTotalLength */
0x00, 0x00,
0x01, /* bInCollection */ 0x01, /* bInCollection */
0x01, /* baInterfaceNr */ 0x01, /* baInterfaceNr */
@@ -215,22 +219,22 @@ __ALIGN_BEGIN static uint8_t USBD_AUDIO_CfgDesc[USB_AUDIO_CONFIG_DESC_SIZ] __ALI
AUDIO_CONTROL_MUTE, /* bmaControls(0) */ AUDIO_CONTROL_MUTE, /* bmaControls(0) */
0, /* bmaControls(1) */ 0, /* bmaControls(1) */
0x00, /* iTerminal */ 0x00, /* iTerminal */
/* 09 byte*/ /* 09 byte */
/*USB Speaker Output Terminal Descriptor */ /* USB Speaker Output Terminal Descriptor */
0x09, /* bLength */ 0x09, /* bLength */
AUDIO_INTERFACE_DESCRIPTOR_TYPE, /* bDescriptorType */ AUDIO_INTERFACE_DESCRIPTOR_TYPE, /* bDescriptorType */
AUDIO_CONTROL_OUTPUT_TERMINAL, /* bDescriptorSubtype */ AUDIO_CONTROL_OUTPUT_TERMINAL, /* bDescriptorSubtype */
0x03, /* bTerminalID */ 0x03, /* bTerminalID */
0x01, /* wTerminalType 0x0301*/ 0x01, /* wTerminalType 0x0301 */
0x03, 0x03,
0x00, /* bAssocTerminal */ 0x00, /* bAssocTerminal */
0x02, /* bSourceID */ 0x02, /* bSourceID */
0x00, /* iTerminal */ 0x00, /* iTerminal */
/* 09 byte*/ /* 09 byte */
/* USB Speaker Standard AS Interface Descriptor - Audio Streaming Zero Bandwith */ /* USB Speaker Standard AS Interface Descriptor - Audio Streaming Zero Bandwidth */
/* Interface 1, Alternate Setting 0 */ /* Interface 1, Alternate Setting 0 */
AUDIO_INTERFACE_DESC_SIZE, /* bLength */ AUDIO_INTERFACE_DESC_SIZE, /* bLength */
USB_DESC_TYPE_INTERFACE, /* bDescriptorType */ USB_DESC_TYPE_INTERFACE, /* bDescriptorType */
0x01, /* bInterfaceNumber */ 0x01, /* bInterfaceNumber */
@@ -288,7 +292,7 @@ __ALIGN_BEGIN static uint8_t USBD_AUDIO_CfgDesc[USB_AUDIO_CONFIG_DESC_SIZ] __ALI
0x00, /* bSynchAddress */ 0x00, /* bSynchAddress */
/* 09 byte*/ /* 09 byte*/
/* Endpoint - Audio Streaming Descriptor*/ /* Endpoint - Audio Streaming Descriptor */
AUDIO_STREAMING_ENDPOINT_DESC_SIZE, /* bLength */ AUDIO_STREAMING_ENDPOINT_DESC_SIZE, /* bLength */
AUDIO_ENDPOINT_DESCRIPTOR_TYPE, /* bDescriptorType */ AUDIO_ENDPOINT_DESCRIPTOR_TYPE, /* bDescriptorType */
AUDIO_ENDPOINT_GENERAL, /* bDescriptor */ AUDIO_ENDPOINT_GENERAL, /* bDescriptor */
@@ -334,8 +338,8 @@ static uint8_t USBD_AUDIO_Init(USBD_HandleTypeDef *pdev, uint8_t cfgidx)
UNUSED(cfgidx); UNUSED(cfgidx);
USBD_AUDIO_HandleTypeDef *haudio; USBD_AUDIO_HandleTypeDef *haudio;
/* Allocate Audio structure */ /* Allocate Audio structure */
haudio = USBD_malloc(sizeof(USBD_AUDIO_HandleTypeDef)); haudio = (USBD_AUDIO_HandleTypeDef *)USBD_malloc(sizeof(USBD_AUDIO_HandleTypeDef));
if (haudio == NULL) if (haudio == NULL)
{ {
@@ -424,97 +428,102 @@ static uint8_t USBD_AUDIO_Setup(USBD_HandleTypeDef *pdev,
haudio = (USBD_AUDIO_HandleTypeDef *)pdev->pClassData; haudio = (USBD_AUDIO_HandleTypeDef *)pdev->pClassData;
if (haudio == NULL)
{
return (uint8_t)USBD_FAIL;
}
switch (req->bmRequest & USB_REQ_TYPE_MASK) switch (req->bmRequest & USB_REQ_TYPE_MASK)
{ {
case USB_REQ_TYPE_CLASS: case USB_REQ_TYPE_CLASS:
switch (req->bRequest) switch (req->bRequest)
{
case AUDIO_REQ_GET_CUR:
AUDIO_REQ_GetCurrent(pdev, req);
break;
case AUDIO_REQ_SET_CUR:
AUDIO_REQ_SetCurrent(pdev, req);
break;
default:
USBD_CtlError(pdev, req);
ret = USBD_FAIL;
break;
}
break;
case USB_REQ_TYPE_STANDARD:
switch (req->bRequest)
{
case USB_REQ_GET_STATUS:
if (pdev->dev_state == USBD_STATE_CONFIGURED)
{ {
(void)USBD_CtlSendData(pdev, (uint8_t *)&status_info, 2U); case AUDIO_REQ_GET_CUR:
} AUDIO_REQ_GetCurrent(pdev, req);
else break;
{
USBD_CtlError(pdev, req);
ret = USBD_FAIL;
}
break;
case USB_REQ_GET_DESCRIPTOR: case AUDIO_REQ_SET_CUR:
if ((req->wValue >> 8) == AUDIO_DESCRIPTOR_TYPE) AUDIO_REQ_SetCurrent(pdev, req);
{ break;
pbuf = USBD_AUDIO_CfgDesc + 18;
len = MIN(USB_AUDIO_DESC_SIZ, req->wLength);
(void)USBD_CtlSendData(pdev, pbuf, len); default:
}
break;
case USB_REQ_GET_INTERFACE:
if (pdev->dev_state == USBD_STATE_CONFIGURED)
{
(void)USBD_CtlSendData(pdev, (uint8_t *)&haudio->alt_setting, 1U);
}
else
{
USBD_CtlError(pdev, req);
ret = USBD_FAIL;
}
break;
case USB_REQ_SET_INTERFACE:
if (pdev->dev_state == USBD_STATE_CONFIGURED)
{
if ((uint8_t)(req->wValue) <= USBD_MAX_NUM_INTERFACES)
{
haudio->alt_setting = (uint8_t)(req->wValue);
}
else
{
/* Call the error management function (command will be nacked */
USBD_CtlError(pdev, req); USBD_CtlError(pdev, req);
ret = USBD_FAIL; ret = USBD_FAIL;
} break;
} }
else break;
case USB_REQ_TYPE_STANDARD:
switch (req->bRequest)
{ {
USBD_CtlError(pdev, req); case USB_REQ_GET_STATUS:
ret = USBD_FAIL; if (pdev->dev_state == USBD_STATE_CONFIGURED)
{
(void)USBD_CtlSendData(pdev, (uint8_t *)&status_info, 2U);
}
else
{
USBD_CtlError(pdev, req);
ret = USBD_FAIL;
}
break;
case USB_REQ_GET_DESCRIPTOR:
if ((req->wValue >> 8) == AUDIO_DESCRIPTOR_TYPE)
{
pbuf = USBD_AUDIO_CfgDesc + 18;
len = MIN(USB_AUDIO_DESC_SIZ, req->wLength);
(void)USBD_CtlSendData(pdev, pbuf, len);
}
break;
case USB_REQ_GET_INTERFACE:
if (pdev->dev_state == USBD_STATE_CONFIGURED)
{
(void)USBD_CtlSendData(pdev, (uint8_t *)&haudio->alt_setting, 1U);
}
else
{
USBD_CtlError(pdev, req);
ret = USBD_FAIL;
}
break;
case USB_REQ_SET_INTERFACE:
if (pdev->dev_state == USBD_STATE_CONFIGURED)
{
if ((uint8_t)(req->wValue) <= USBD_MAX_NUM_INTERFACES)
{
haudio->alt_setting = (uint8_t)(req->wValue);
}
else
{
/* Call the error management function (command will be NAKed */
USBD_CtlError(pdev, req);
ret = USBD_FAIL;
}
}
else
{
USBD_CtlError(pdev, req);
ret = USBD_FAIL;
}
break;
case USB_REQ_CLEAR_FEATURE:
break;
default:
USBD_CtlError(pdev, req);
ret = USBD_FAIL;
break;
} }
break; break;
case USB_REQ_CLEAR_FEATURE:
break;
default: default:
USBD_CtlError(pdev, req); USBD_CtlError(pdev, req);
ret = USBD_FAIL; ret = USBD_FAIL;
break; break;
}
break;
default:
USBD_CtlError(pdev, req);
ret = USBD_FAIL;
break;
} }
return (uint8_t)ret; return (uint8_t)ret;
@@ -562,6 +571,11 @@ static uint8_t USBD_AUDIO_EP0_RxReady(USBD_HandleTypeDef *pdev)
USBD_AUDIO_HandleTypeDef *haudio; USBD_AUDIO_HandleTypeDef *haudio;
haudio = (USBD_AUDIO_HandleTypeDef *)pdev->pClassData; haudio = (USBD_AUDIO_HandleTypeDef *)pdev->pClassData;
if (haudio == NULL)
{
return (uint8_t)USBD_FAIL;
}
if (haudio->control.cmd == AUDIO_REQ_SET_CUR) if (haudio->control.cmd == AUDIO_REQ_SET_CUR)
{ {
/* In this driver, to simplify code, only SET_CUR request is managed */ /* In this driver, to simplify code, only SET_CUR request is managed */
@@ -651,13 +665,13 @@ void USBD_AUDIO_Sync(USBD_HandleTypeDef *pdev, AUDIO_OffsetTypeDef offset)
{ {
if ((haudio->wr_ptr - haudio->rd_ptr) < AUDIO_OUT_PACKET) if ((haudio->wr_ptr - haudio->rd_ptr) < AUDIO_OUT_PACKET)
{ {
BufferSize -= 4U; BufferSize -= 4U;
} }
else else
{ {
if ((haudio->wr_ptr - haudio->rd_ptr) > (AUDIO_TOTAL_BUF_SIZE - AUDIO_OUT_PACKET)) if ((haudio->wr_ptr - haudio->rd_ptr) > (AUDIO_TOTAL_BUF_SIZE - AUDIO_OUT_PACKET))
{ {
BufferSize += 4U; BufferSize += 4U;
} }
} }
} }
@@ -712,6 +726,11 @@ static uint8_t USBD_AUDIO_DataOut(USBD_HandleTypeDef *pdev, uint8_t epnum)
haudio = (USBD_AUDIO_HandleTypeDef *)pdev->pClassData; haudio = (USBD_AUDIO_HandleTypeDef *)pdev->pClassData;
if (haudio == NULL)
{
return (uint8_t)USBD_FAIL;
}
if (epnum == AUDIO_OUT_EP) if (epnum == AUDIO_OUT_EP)
{ {
/* Get received data packet length */ /* Get received data packet length */
@@ -767,10 +786,16 @@ static void AUDIO_REQ_GetCurrent(USBD_HandleTypeDef *pdev, USBD_SetupReqTypedef
USBD_AUDIO_HandleTypeDef *haudio; USBD_AUDIO_HandleTypeDef *haudio;
haudio = (USBD_AUDIO_HandleTypeDef *)pdev->pClassData; haudio = (USBD_AUDIO_HandleTypeDef *)pdev->pClassData;
(void)USBD_memset(haudio->control.data, 0, 64U); if (haudio == NULL)
{
return;
}
(void)USBD_memset(haudio->control.data, 0, USB_MAX_EP0_SIZE);
/* Send the current mute state */ /* Send the current mute state */
(void)USBD_CtlSendData(pdev, haudio->control.data, req->wLength); (void)USBD_CtlSendData(pdev, haudio->control.data,
MIN(req->wLength, USB_MAX_EP0_SIZE));
} }
/** /**
@@ -785,24 +810,29 @@ static void AUDIO_REQ_SetCurrent(USBD_HandleTypeDef *pdev, USBD_SetupReqTypedef
USBD_AUDIO_HandleTypeDef *haudio; USBD_AUDIO_HandleTypeDef *haudio;
haudio = (USBD_AUDIO_HandleTypeDef *)pdev->pClassData; haudio = (USBD_AUDIO_HandleTypeDef *)pdev->pClassData;
if (haudio == NULL)
{
return;
}
if (req->wLength != 0U) if (req->wLength != 0U)
{ {
/* Prepare the reception of the buffer over EP0 */
(void)USBD_CtlPrepareRx(pdev, haudio->control.data, req->wLength);
haudio->control.cmd = AUDIO_REQ_SET_CUR; /* Set the request value */ haudio->control.cmd = AUDIO_REQ_SET_CUR; /* Set the request value */
haudio->control.len = (uint8_t)req->wLength; /* Set the request data length */ haudio->control.len = (uint8_t)MIN(req->wLength, USB_MAX_EP0_SIZE); /* Set the request data length */
haudio->control.unit = HIBYTE(req->wIndex); /* Set the request target unit */ haudio->control.unit = HIBYTE(req->wIndex); /* Set the request target unit */
/* Prepare the reception of the buffer over EP0 */
(void)USBD_CtlPrepareRx(pdev, haudio->control.data, haudio->control.len);
} }
} }
/** /**
* @brief DeviceQualifierDescriptor * @brief DeviceQualifierDescriptor
* return Device Qualifier descriptor * return Device Qualifier descriptor
* @param length : pointer data length * @param length : pointer data length
* @retval pointer to descriptor buffer * @retval pointer to descriptor buffer
*/ */
static uint8_t *USBD_AUDIO_GetDeviceQualifierDesc(uint16_t *length) static uint8_t *USBD_AUDIO_GetDeviceQualifierDesc(uint16_t *length)
{ {
*length = (uint16_t)sizeof(USBD_AUDIO_DeviceQualifierDesc); *length = (uint16_t)sizeof(USBD_AUDIO_DeviceQualifierDesc);
@@ -811,10 +841,10 @@ static uint8_t *USBD_AUDIO_GetDeviceQualifierDesc(uint16_t *length)
} }
/** /**
* @brief USBD_AUDIO_RegisterInterface * @brief USBD_AUDIO_RegisterInterface
* @param fops: Audio interface callback * @param fops: Audio interface callback
* @retval status * @retval status
*/ */
uint8_t USBD_AUDIO_RegisterInterface(USBD_HandleTypeDef *pdev, uint8_t USBD_AUDIO_RegisterInterface(USBD_HandleTypeDef *pdev,
USBD_AUDIO_ItfTypeDef *fops) USBD_AUDIO_ItfTypeDef *fops)
{ {

View File

@@ -7,7 +7,7 @@
* - Initialization and Configuration of high and low layer * - Initialization and Configuration of high and low layer
* - Enumeration as BillBoard Device * - Enumeration as BillBoard Device
* - Error management * - Error management
* @verbatim * @verbatim
* *
* =================================================================== * ===================================================================
* BillBoard Class Description * BillBoard Class Description
@@ -150,8 +150,12 @@ __ALIGN_BEGIN static uint8_t USBD_BB_CfgDesc[USB_BB_CONFIG_DESC_SIZ] __ALIGN_EN
0x01, /* bNumInterfaces: 1 interface */ 0x01, /* bNumInterfaces: 1 interface */
0x01, /* bConfigurationValue: Configuration value */ 0x01, /* bConfigurationValue: Configuration value */
USBD_IDX_CONFIG_STR, /* iConfiguration: Index of string descriptor describing the configuration */ USBD_IDX_CONFIG_STR, /* iConfiguration: Index of string descriptor describing the configuration */
0xC0, /* bmAttributes: bus powered and Support Remote Wake-up */ #if (USBD_SELF_POWERED == 1U)
0x00, /* MaxPower 100 mA: this current is used for detecting Vbus */ 0xC0, /* bmAttributes: Bus Powered according to user configuration */
#else
0x80, /* bmAttributes: Bus Powered according to user configuration */
#endif
USBD_MAX_POWER, /* MaxPower (mA) */
/* 09 */ /* 09 */
/************** Descriptor of BillBoard interface ****************/ /************** Descriptor of BillBoard interface ****************/
@@ -170,15 +174,19 @@ __ALIGN_BEGIN static uint8_t USBD_BB_CfgDesc[USB_BB_CONFIG_DESC_SIZ] __ALIGN_EN
/* USB device Other Speed Configuration Descriptor */ /* USB device Other Speed Configuration Descriptor */
__ALIGN_BEGIN static uint8_t USBD_BB_OtherSpeedCfgDesc[USB_BB_CONFIG_DESC_SIZ] __ALIGN_END = __ALIGN_BEGIN static uint8_t USBD_BB_OtherSpeedCfgDesc[USB_BB_CONFIG_DESC_SIZ] __ALIGN_END =
{ {
0x09, /* bLength: Configuation Descriptor size */ 0x09, /* bLength: Configuration Descriptor size */
USB_DESC_TYPE_OTHER_SPEED_CONFIGURATION, USB_DESC_TYPE_OTHER_SPEED_CONFIGURATION,
USB_BB_CONFIG_DESC_SIZ, USB_BB_CONFIG_DESC_SIZ,
0x00, 0x00,
0x01, /* bNumInterfaces: 1 interface */ 0x01, /* bNumInterfaces: 1 interface */
0x01, /* bConfigurationValue: */ 0x01, /* bConfigurationValue */
USBD_IDX_CONFIG_STR, /* iConfiguration: */ USBD_IDX_CONFIG_STR, /* iConfiguration */
0xC0, /* bmAttributes: */ #if (USBD_SELF_POWERED == 1U)
0x00, /* MaxPower 100 mA */ 0xC0, /* bmAttributes: Bus Powered according to user configuration */
#else
0x80, /* bmAttributes: Bus Powered according to user configuration */
#endif
USBD_MAX_POWER, /* MaxPower (mA) */
/************** Descriptor of BillBoard interface ****************/ /************** Descriptor of BillBoard interface ****************/
/* 09 */ /* 09 */
@@ -248,50 +256,50 @@ static uint8_t USBD_BB_Setup(USBD_HandleTypeDef *pdev, USBD_SetupReqTypedef *req
switch (req->bmRequest & USB_REQ_TYPE_MASK) switch (req->bmRequest & USB_REQ_TYPE_MASK)
{ {
case USB_REQ_TYPE_CLASS: case USB_REQ_TYPE_CLASS:
break;
case USB_REQ_TYPE_STANDARD:
switch (req->bRequest)
{
case USB_REQ_GET_STATUS:
if (pdev->dev_state == USBD_STATE_CONFIGURED)
{
(void)USBD_CtlSendData(pdev, (uint8_t *)&status_info, 2U);
}
else
{
USBD_CtlError(pdev, req);
ret = USBD_FAIL;
}
break; break;
case USB_REQ_TYPE_STANDARD:
case USB_REQ_GET_INTERFACE: switch (req->bRequest)
if (pdev->dev_state == USBD_STATE_CONFIGURED)
{ {
(void)USBD_CtlSendData(pdev, (uint8_t *)&AltSetting, 1U); case USB_REQ_GET_STATUS:
} if (pdev->dev_state == USBD_STATE_CONFIGURED)
else {
{ (void)USBD_CtlSendData(pdev, (uint8_t *)&status_info, 2U);
USBD_CtlError(pdev, req); }
ret = USBD_FAIL; else
} {
break; USBD_CtlError(pdev, req);
ret = USBD_FAIL;
}
break;
case USB_REQ_SET_INTERFACE: case USB_REQ_GET_INTERFACE:
case USB_REQ_CLEAR_FEATURE: if (pdev->dev_state == USBD_STATE_CONFIGURED)
{
(void)USBD_CtlSendData(pdev, (uint8_t *)&AltSetting, 1U);
}
else
{
USBD_CtlError(pdev, req);
ret = USBD_FAIL;
}
break;
case USB_REQ_SET_INTERFACE:
case USB_REQ_CLEAR_FEATURE:
break;
default:
USBD_CtlError(pdev, req);
ret = USBD_FAIL;
break;
}
break; break;
default: default:
USBD_CtlError(pdev, req); USBD_CtlError(pdev, req);
ret = USBD_FAIL; ret = USBD_FAIL;
break; break;
}
break;
default:
USBD_CtlError(pdev, req);
ret = USBD_FAIL;
break;
} }
return (uint8_t)ret; return (uint8_t)ret;
@@ -391,10 +399,10 @@ static uint8_t *USBD_BB_GetDeviceQualifierDesc(uint16_t *length)
*/ */
USBD_BB_DescHeader_t *USBD_BB_GetNextDesc(uint8_t *pbuf, uint16_t *ptr) USBD_BB_DescHeader_t *USBD_BB_GetNextDesc(uint8_t *pbuf, uint16_t *ptr)
{ {
USBD_BB_DescHeader_t *pnext = (USBD_BB_DescHeader_t *)pbuf; USBD_BB_DescHeader_t *pnext = (USBD_BB_DescHeader_t *)(void *)pbuf;
*ptr += pnext->bLength; *ptr += pnext->bLength;
pnext = (USBD_BB_DescHeader_t *)(pbuf + pnext->bLength); pnext = (USBD_BB_DescHeader_t *)(void *)(pbuf + pnext->bLength);
return (pnext); return (pnext);
} }
@@ -411,8 +419,8 @@ void *USBD_BB_GetCapDesc(USBD_HandleTypeDef *pdev, uint8_t *pBosDesc)
{ {
UNUSED(pdev); UNUSED(pdev);
USBD_BB_DescHeader_t *pdesc = (USBD_BB_DescHeader_t *)pBosDesc; USBD_BB_DescHeader_t *pdesc = (USBD_BB_DescHeader_t *)(void *)pBosDesc;
USBD_BosDescTypedef *desc = (USBD_BosDescTypedef *)pBosDesc; USBD_BosDescTypedef *desc = (USBD_BosDescTypedef *)(void *)pBosDesc;
USBD_BosBBCapDescTypedef *pCapDesc = NULL; USBD_BosBBCapDescTypedef *pCapDesc = NULL;
uint16_t ptr; uint16_t ptr;
@@ -426,7 +434,7 @@ void *USBD_BB_GetCapDesc(USBD_HandleTypeDef *pdev, uint8_t *pBosDesc)
if (pdesc->bDevCapabilityType == USBD_BILLBOARD_CAPABILITY) if (pdesc->bDevCapabilityType == USBD_BILLBOARD_CAPABILITY)
{ {
pCapDesc = (USBD_BosBBCapDescTypedef *)pdesc; pCapDesc = (USBD_BosBBCapDescTypedef *)(void *)pdesc;
break; break;
} }
} }
@@ -447,8 +455,8 @@ void *USBD_BB_GetAltModeDesc(USBD_HandleTypeDef *pdev, uint8_t *pBosDesc, uint8_
{ {
UNUSED(pdev); UNUSED(pdev);
USBD_BB_DescHeader_t *pdesc = (USBD_BB_DescHeader_t *)pBosDesc; USBD_BB_DescHeader_t *pdesc = (USBD_BB_DescHeader_t *)(void *)pBosDesc;
USBD_BosDescTypedef *desc = (USBD_BosDescTypedef *)pBosDesc; USBD_BosDescTypedef *desc = (USBD_BosDescTypedef *)(void *)pBosDesc;
USBD_BB_AltModeCapDescTypeDef *pAltModDesc = NULL; USBD_BB_AltModeCapDescTypeDef *pAltModDesc = NULL;
uint8_t cnt = 0U; uint8_t cnt = 0U;
uint16_t ptr; uint16_t ptr;
@@ -465,7 +473,7 @@ void *USBD_BB_GetAltModeDesc(USBD_HandleTypeDef *pdev, uint8_t *pBosDesc, uint8_
{ {
if (cnt == idx) if (cnt == idx)
{ {
pAltModDesc = (USBD_BB_AltModeCapDescTypeDef *)pdesc; pAltModDesc = (USBD_BB_AltModeCapDescTypeDef *)(void *)pdesc;
break; break;
} }
else else

View File

@@ -65,6 +65,7 @@ extern "C" {
#define CDC_DATA_FS_IN_PACKET_SIZE CDC_DATA_FS_MAX_PACKET_SIZE #define CDC_DATA_FS_IN_PACKET_SIZE CDC_DATA_FS_MAX_PACKET_SIZE
#define CDC_DATA_FS_OUT_PACKET_SIZE CDC_DATA_FS_MAX_PACKET_SIZE #define CDC_DATA_FS_OUT_PACKET_SIZE CDC_DATA_FS_MAX_PACKET_SIZE
#define CDC_REQ_MAX_DATA_SIZE 0x7U
/*---------------------------------------------------------------------*/ /*---------------------------------------------------------------------*/
/* CDC definitions */ /* CDC definitions */
/*---------------------------------------------------------------------*/ /*---------------------------------------------------------------------*/
@@ -110,7 +111,7 @@ typedef struct _USBD_CDC_Itf
typedef struct typedef struct
{ {
uint32_t data[CDC_DATA_HS_MAX_PACKET_SIZE / 4U]; /* Force 32bits alignment */ uint32_t data[CDC_DATA_HS_MAX_PACKET_SIZE / 4U]; /* Force 32-bit alignment */
uint8_t CmdOpCode; uint8_t CmdOpCode;
uint8_t CmdLength; uint8_t CmdLength;
uint8_t *RxBuffer; uint8_t *RxBuffer;

View File

@@ -142,7 +142,7 @@ USBD_ClassTypeDef USBD_CDC =
USBD_CDC_Init, USBD_CDC_Init,
USBD_CDC_DeInit, USBD_CDC_DeInit,
USBD_CDC_Setup, USBD_CDC_Setup,
NULL, /* EP0_TxSent, */ NULL, /* EP0_TxSent */
USBD_CDC_EP0_RxReady, USBD_CDC_EP0_RxReady,
USBD_CDC_DataIn, USBD_CDC_DataIn,
USBD_CDC_DataOut, USBD_CDC_DataOut,
@@ -163,25 +163,28 @@ __ALIGN_BEGIN static uint8_t USBD_CDC_CfgHSDesc[USB_CDC_CONFIG_DESC_SIZ] __ALIGN
USB_DESC_TYPE_CONFIGURATION, /* bDescriptorType: Configuration */ USB_DESC_TYPE_CONFIGURATION, /* bDescriptorType: Configuration */
USB_CDC_CONFIG_DESC_SIZ, /* wTotalLength:no of returned bytes */ USB_CDC_CONFIG_DESC_SIZ, /* wTotalLength:no of returned bytes */
0x00, 0x00,
0x02, /* bNumInterfaces: 2 interface */ 0x02, /* bNumInterfaces: 2 interfaces */
0x01, /* bConfigurationValue: Configuration value */ 0x01, /* bConfigurationValue: Configuration value */
0x00, /* iConfiguration: Index of string descriptor describing the configuration */ 0x00, /* iConfiguration: Index of string descriptor describing the configuration */
0xC0, /* bmAttributes: self powered */ #if (USBD_SELF_POWERED == 1U)
0x32, /* MaxPower 0 mA */ 0xC0, /* bmAttributes: Bus Powered according to user configuration */
#else
0x80, /* bmAttributes: Bus Powered according to user configuration */
#endif
USBD_MAX_POWER, /* MaxPower (mA) */
/*---------------------------------------------------------------------------*/ /*---------------------------------------------------------------------------*/
/* Interface Descriptor */ /* Interface Descriptor */
0x09, /* bLength: Interface Descriptor size */ 0x09, /* bLength: Interface Descriptor size */
USB_DESC_TYPE_INTERFACE, /* bDescriptorType: Interface */ USB_DESC_TYPE_INTERFACE, /* bDescriptorType: Interface */
/* Interface descriptor type */
0x00, /* bInterfaceNumber: Number of Interface */ 0x00, /* bInterfaceNumber: Number of Interface */
0x00, /* bAlternateSetting: Alternate setting */ 0x00, /* bAlternateSetting: Alternate setting */
0x01, /* bNumEndpoints: One endpoints used */ 0x01, /* bNumEndpoints: One endpoints used */
0x02, /* bInterfaceClass: Communication Interface Class */ 0x02, /* bInterfaceClass: Communication Interface Class */
0x02, /* bInterfaceSubClass: Abstract Control Model */ 0x02, /* bInterfaceSubClass: Abstract Control Model */
0x01, /* bInterfaceProtocol: Common AT commands */ 0x01, /* bInterfaceProtocol: Common AT commands */
0x00, /* iInterface: */ 0x00, /* iInterface */
/* Header Functional Descriptor */ /* Header Functional Descriptor */
0x05, /* bLength: Endpoint Descriptor size */ 0x05, /* bLength: Endpoint Descriptor size */
@@ -215,9 +218,9 @@ __ALIGN_BEGIN static uint8_t USBD_CDC_CfgHSDesc[USB_CDC_CONFIG_DESC_SIZ] __ALIGN
USB_DESC_TYPE_ENDPOINT, /* bDescriptorType: Endpoint */ USB_DESC_TYPE_ENDPOINT, /* bDescriptorType: Endpoint */
CDC_CMD_EP, /* bEndpointAddress */ CDC_CMD_EP, /* bEndpointAddress */
0x03, /* bmAttributes: Interrupt */ 0x03, /* bmAttributes: Interrupt */
LOBYTE(CDC_CMD_PACKET_SIZE), /* wMaxPacketSize: */ LOBYTE(CDC_CMD_PACKET_SIZE), /* wMaxPacketSize */
HIBYTE(CDC_CMD_PACKET_SIZE), HIBYTE(CDC_CMD_PACKET_SIZE),
CDC_HS_BINTERVAL, /* bInterval: */ CDC_HS_BINTERVAL, /* bInterval */
/*---------------------------------------------------------------------------*/ /*---------------------------------------------------------------------------*/
/* Data class interface descriptor */ /* Data class interface descriptor */
@@ -227,27 +230,27 @@ __ALIGN_BEGIN static uint8_t USBD_CDC_CfgHSDesc[USB_CDC_CONFIG_DESC_SIZ] __ALIGN
0x00, /* bAlternateSetting: Alternate setting */ 0x00, /* bAlternateSetting: Alternate setting */
0x02, /* bNumEndpoints: Two endpoints used */ 0x02, /* bNumEndpoints: Two endpoints used */
0x0A, /* bInterfaceClass: CDC */ 0x0A, /* bInterfaceClass: CDC */
0x00, /* bInterfaceSubClass: */ 0x00, /* bInterfaceSubClass */
0x00, /* bInterfaceProtocol: */ 0x00, /* bInterfaceProtocol */
0x00, /* iInterface: */ 0x00, /* iInterface */
/* Endpoint OUT Descriptor */ /* Endpoint OUT Descriptor */
0x07, /* bLength: Endpoint Descriptor size */ 0x07, /* bLength: Endpoint Descriptor size */
USB_DESC_TYPE_ENDPOINT, /* bDescriptorType: Endpoint */ USB_DESC_TYPE_ENDPOINT, /* bDescriptorType: Endpoint */
CDC_OUT_EP, /* bEndpointAddress */ CDC_OUT_EP, /* bEndpointAddress */
0x02, /* bmAttributes: Bulk */ 0x02, /* bmAttributes: Bulk */
LOBYTE(CDC_DATA_HS_MAX_PACKET_SIZE), /* wMaxPacketSize: */ LOBYTE(CDC_DATA_HS_MAX_PACKET_SIZE), /* wMaxPacketSize */
HIBYTE(CDC_DATA_HS_MAX_PACKET_SIZE), HIBYTE(CDC_DATA_HS_MAX_PACKET_SIZE),
0x00, /* bInterval: ignore for Bulk transfer */ 0x00, /* bInterval */
/* Endpoint IN Descriptor */ /* Endpoint IN Descriptor */
0x07, /* bLength: Endpoint Descriptor size */ 0x07, /* bLength: Endpoint Descriptor size */
USB_DESC_TYPE_ENDPOINT, /* bDescriptorType: Endpoint */ USB_DESC_TYPE_ENDPOINT, /* bDescriptorType: Endpoint */
CDC_IN_EP, /* bEndpointAddress */ CDC_IN_EP, /* bEndpointAddress */
0x02, /* bmAttributes: Bulk */ 0x02, /* bmAttributes: Bulk */
LOBYTE(CDC_DATA_HS_MAX_PACKET_SIZE), /* wMaxPacketSize: */ LOBYTE(CDC_DATA_HS_MAX_PACKET_SIZE), /* wMaxPacketSize */
HIBYTE(CDC_DATA_HS_MAX_PACKET_SIZE), HIBYTE(CDC_DATA_HS_MAX_PACKET_SIZE),
0x00 /* bInterval: ignore for Bulk transfer */ 0x00 /* bInterval */
}; };
@@ -257,13 +260,17 @@ __ALIGN_BEGIN static uint8_t USBD_CDC_CfgFSDesc[USB_CDC_CONFIG_DESC_SIZ] __ALIGN
/* Configuration Descriptor */ /* Configuration Descriptor */
0x09, /* bLength: Configuration Descriptor size */ 0x09, /* bLength: Configuration Descriptor size */
USB_DESC_TYPE_CONFIGURATION, /* bDescriptorType: Configuration */ USB_DESC_TYPE_CONFIGURATION, /* bDescriptorType: Configuration */
USB_CDC_CONFIG_DESC_SIZ, /* wTotalLength:no of returned bytes */ USB_CDC_CONFIG_DESC_SIZ, /* wTotalLength */
0x00, 0x00,
0x02, /* bNumInterfaces: 2 interface */ 0x02, /* bNumInterfaces: 2 interfaces */
0x01, /* bConfigurationValue: Configuration value */ 0x01, /* bConfigurationValue: Configuration value */
0x00, /* iConfiguration: Index of string descriptor describing the configuration */ 0x00, /* iConfiguration: Index of string descriptor describing the configuration */
0xC0, /* bmAttributes: self powered */ #if (USBD_SELF_POWERED == 1U)
0x32, /* MaxPower 0 mA */ 0xC0, /* bmAttributes: Bus Powered according to user configuration */
#else
0x80, /* bmAttributes: Bus Powered according to user configuration */
#endif
USBD_MAX_POWER, /* MaxPower (mA) */
/*---------------------------------------------------------------------------*/ /*---------------------------------------------------------------------------*/
@@ -273,11 +280,11 @@ __ALIGN_BEGIN static uint8_t USBD_CDC_CfgFSDesc[USB_CDC_CONFIG_DESC_SIZ] __ALIGN
/* Interface descriptor type */ /* Interface descriptor type */
0x00, /* bInterfaceNumber: Number of Interface */ 0x00, /* bInterfaceNumber: Number of Interface */
0x00, /* bAlternateSetting: Alternate setting */ 0x00, /* bAlternateSetting: Alternate setting */
0x01, /* bNumEndpoints: One endpoints used */ 0x01, /* bNumEndpoints: One endpoint used */
0x02, /* bInterfaceClass: Communication Interface Class */ 0x02, /* bInterfaceClass: Communication Interface Class */
0x02, /* bInterfaceSubClass: Abstract Control Model */ 0x02, /* bInterfaceSubClass: Abstract Control Model */
0x01, /* bInterfaceProtocol: Common AT commands */ 0x01, /* bInterfaceProtocol: Common AT commands */
0x00, /* iInterface: */ 0x00, /* iInterface */
/* Header Functional Descriptor */ /* Header Functional Descriptor */
0x05, /* bLength: Endpoint Descriptor size */ 0x05, /* bLength: Endpoint Descriptor size */
@@ -291,7 +298,7 @@ __ALIGN_BEGIN static uint8_t USBD_CDC_CfgFSDesc[USB_CDC_CONFIG_DESC_SIZ] __ALIGN
0x24, /* bDescriptorType: CS_INTERFACE */ 0x24, /* bDescriptorType: CS_INTERFACE */
0x01, /* bDescriptorSubtype: Call Management Func Desc */ 0x01, /* bDescriptorSubtype: Call Management Func Desc */
0x00, /* bmCapabilities: D0+D1 */ 0x00, /* bmCapabilities: D0+D1 */
0x01, /* bDataInterface: 1 */ 0x01, /* bDataInterface */
/* ACM Functional Descriptor */ /* ACM Functional Descriptor */
0x04, /* bFunctionLength */ 0x04, /* bFunctionLength */
@@ -311,9 +318,9 @@ __ALIGN_BEGIN static uint8_t USBD_CDC_CfgFSDesc[USB_CDC_CONFIG_DESC_SIZ] __ALIGN
USB_DESC_TYPE_ENDPOINT, /* bDescriptorType: Endpoint */ USB_DESC_TYPE_ENDPOINT, /* bDescriptorType: Endpoint */
CDC_CMD_EP, /* bEndpointAddress */ CDC_CMD_EP, /* bEndpointAddress */
0x03, /* bmAttributes: Interrupt */ 0x03, /* bmAttributes: Interrupt */
LOBYTE(CDC_CMD_PACKET_SIZE), /* wMaxPacketSize: */ LOBYTE(CDC_CMD_PACKET_SIZE), /* wMaxPacketSize */
HIBYTE(CDC_CMD_PACKET_SIZE), HIBYTE(CDC_CMD_PACKET_SIZE),
CDC_FS_BINTERVAL, /* bInterval: */ CDC_FS_BINTERVAL, /* bInterval */
/*---------------------------------------------------------------------------*/ /*---------------------------------------------------------------------------*/
/* Data class interface descriptor */ /* Data class interface descriptor */
@@ -323,42 +330,46 @@ __ALIGN_BEGIN static uint8_t USBD_CDC_CfgFSDesc[USB_CDC_CONFIG_DESC_SIZ] __ALIGN
0x00, /* bAlternateSetting: Alternate setting */ 0x00, /* bAlternateSetting: Alternate setting */
0x02, /* bNumEndpoints: Two endpoints used */ 0x02, /* bNumEndpoints: Two endpoints used */
0x0A, /* bInterfaceClass: CDC */ 0x0A, /* bInterfaceClass: CDC */
0x00, /* bInterfaceSubClass: */ 0x00, /* bInterfaceSubClass */
0x00, /* bInterfaceProtocol: */ 0x00, /* bInterfaceProtocol */
0x00, /* iInterface: */ 0x00, /* iInterface */
/* Endpoint OUT Descriptor */ /* Endpoint OUT Descriptor */
0x07, /* bLength: Endpoint Descriptor size */ 0x07, /* bLength: Endpoint Descriptor size */
USB_DESC_TYPE_ENDPOINT, /* bDescriptorType: Endpoint */ USB_DESC_TYPE_ENDPOINT, /* bDescriptorType: Endpoint */
CDC_OUT_EP, /* bEndpointAddress */ CDC_OUT_EP, /* bEndpointAddress */
0x02, /* bmAttributes: Bulk */ 0x02, /* bmAttributes: Bulk */
LOBYTE(CDC_DATA_FS_MAX_PACKET_SIZE), /* wMaxPacketSize: */ LOBYTE(CDC_DATA_FS_MAX_PACKET_SIZE), /* wMaxPacketSize */
HIBYTE(CDC_DATA_FS_MAX_PACKET_SIZE), HIBYTE(CDC_DATA_FS_MAX_PACKET_SIZE),
0x00, /* bInterval: ignore for Bulk transfer */ 0x00, /* bInterval */
/* Endpoint IN Descriptor */ /* Endpoint IN Descriptor */
0x07, /* bLength: Endpoint Descriptor size */ 0x07, /* bLength: Endpoint Descriptor size */
USB_DESC_TYPE_ENDPOINT, /* bDescriptorType: Endpoint */ USB_DESC_TYPE_ENDPOINT, /* bDescriptorType: Endpoint */
CDC_IN_EP, /* bEndpointAddress */ CDC_IN_EP, /* bEndpointAddress */
0x02, /* bmAttributes: Bulk */ 0x02, /* bmAttributes: Bulk */
LOBYTE(CDC_DATA_FS_MAX_PACKET_SIZE), /* wMaxPacketSize: */ LOBYTE(CDC_DATA_FS_MAX_PACKET_SIZE), /* wMaxPacketSize */
HIBYTE(CDC_DATA_FS_MAX_PACKET_SIZE), HIBYTE(CDC_DATA_FS_MAX_PACKET_SIZE),
0x00 /* bInterval: ignore for Bulk transfer */ 0x00 /* bInterval */
}; };
__ALIGN_BEGIN static uint8_t USBD_CDC_OtherSpeedCfgDesc[USB_CDC_CONFIG_DESC_SIZ] __ALIGN_END = __ALIGN_BEGIN static uint8_t USBD_CDC_OtherSpeedCfgDesc[USB_CDC_CONFIG_DESC_SIZ] __ALIGN_END =
{ {
0x09, /* bLength: Configuation Descriptor size */ 0x09, /* bLength: Configuration Descriptor size */
USB_DESC_TYPE_OTHER_SPEED_CONFIGURATION, USB_DESC_TYPE_OTHER_SPEED_CONFIGURATION,
USB_CDC_CONFIG_DESC_SIZ, USB_CDC_CONFIG_DESC_SIZ,
0x00, 0x00,
0x02, /* bNumInterfaces: 2 interfaces */ 0x02, /* bNumInterfaces: 2 interfaces */
0x01, /* bConfigurationValue: */ 0x01, /* bConfigurationValue */
0x04, /* iConfiguration: */ 0x04, /* iConfiguration */
0xC0, /* bmAttributes: */ #if (USBD_SELF_POWERED == 1U)
0x32, /* MaxPower 100 mA */ 0xC0, /* bmAttributes: Bus Powered according to user configuration */
#else
0x80, /* bmAttributes: Bus Powered according to user configuration */
#endif
USBD_MAX_POWER, /* MaxPower (mA) */
/*Interface Descriptor */ /* Interface Descriptor */
0x09, /* bLength: Interface Descriptor size */ 0x09, /* bLength: Interface Descriptor size */
USB_DESC_TYPE_INTERFACE, /* bDescriptorType: Interface */ USB_DESC_TYPE_INTERFACE, /* bDescriptorType: Interface */
/* Interface descriptor type */ /* Interface descriptor type */
@@ -368,7 +379,7 @@ __ALIGN_BEGIN static uint8_t USBD_CDC_OtherSpeedCfgDesc[USB_CDC_CONFIG_DESC_SIZ]
0x02, /* bInterfaceClass: Communication Interface Class */ 0x02, /* bInterfaceClass: Communication Interface Class */
0x02, /* bInterfaceSubClass: Abstract Control Model */ 0x02, /* bInterfaceSubClass: Abstract Control Model */
0x01, /* bInterfaceProtocol: Common AT commands */ 0x01, /* bInterfaceProtocol: Common AT commands */
0x00, /* iInterface: */ 0x00, /* iInterface */
/* Header Functional Descriptor */ /* Header Functional Descriptor */
0x05, /* bLength: Endpoint Descriptor size */ 0x05, /* bLength: Endpoint Descriptor size */
@@ -377,34 +388,34 @@ __ALIGN_BEGIN static uint8_t USBD_CDC_OtherSpeedCfgDesc[USB_CDC_CONFIG_DESC_SIZ]
0x10, /* bcdCDC: spec release number */ 0x10, /* bcdCDC: spec release number */
0x01, 0x01,
/*Call Management Functional Descriptor*/ /* Call Management Functional Descriptor */
0x05, /* bFunctionLength */ 0x05, /* bFunctionLength */
0x24, /* bDescriptorType: CS_INTERFACE */ 0x24, /* bDescriptorType: CS_INTERFACE */
0x01, /* bDescriptorSubtype: Call Management Func Desc */ 0x01, /* bDescriptorSubtype: Call Management Func Desc */
0x00, /* bmCapabilities: D0+D1 */ 0x00, /* bmCapabilities */
0x01, /* bDataInterface: 1 */ 0x01, /* bDataInterface */
/*ACM Functional Descriptor*/ /* ACM Functional Descriptor */
0x04, /* bFunctionLength */ 0x04, /* bFunctionLength */
0x24, /* bDescriptorType: CS_INTERFACE */ 0x24, /* bDescriptorType: CS_INTERFACE */
0x02, /* bDescriptorSubtype: Abstract Control Management desc */ 0x02, /* bDescriptorSubtype: Abstract Control Management desc */
0x02, /* bmCapabilities */ 0x02, /* bmCapabilities */
/*Union Functional Descriptor*/ /* Union Functional Descriptor */
0x05, /* bFunctionLength */ 0x05, /* bFunctionLength */
0x24, /* bDescriptorType: CS_INTERFACE */ 0x24, /* bDescriptorType: CS_INTERFACE */
0x06, /* bDescriptorSubtype: Union func desc */ 0x06, /* bDescriptorSubtype: Union func desc */
0x00, /* bMasterInterface: Communication class interface */ 0x00, /* bMasterInterface: Communication class interface */
0x01, /* bSlaveInterface0: Data Class Interface */ 0x01, /* bSlaveInterface0: Data Class Interface */
/*Endpoint 2 Descriptor*/ /* Endpoint 2 Descriptor */
0x07, /* bLength: Endpoint Descriptor size */ 0x07, /* bLength: Endpoint Descriptor size */
USB_DESC_TYPE_ENDPOINT, /* bDescriptorType: Endpoint */ USB_DESC_TYPE_ENDPOINT, /* bDescriptorType: Endpoint */
CDC_CMD_EP, /* bEndpointAddress */ CDC_CMD_EP, /* bEndpointAddress */
0x03, /* bmAttributes: Interrupt */ 0x03, /* bmAttributes: Interrupt */
LOBYTE(CDC_CMD_PACKET_SIZE), /* wMaxPacketSize: */ LOBYTE(CDC_CMD_PACKET_SIZE), /* wMaxPacketSize */
HIBYTE(CDC_CMD_PACKET_SIZE), HIBYTE(CDC_CMD_PACKET_SIZE),
CDC_FS_BINTERVAL, /* bInterval: */ CDC_FS_BINTERVAL, /* bInterval */
/*---------------------------------------------------------------------------*/ /*---------------------------------------------------------------------------*/
@@ -415,25 +426,25 @@ __ALIGN_BEGIN static uint8_t USBD_CDC_OtherSpeedCfgDesc[USB_CDC_CONFIG_DESC_SIZ]
0x00, /* bAlternateSetting: Alternate setting */ 0x00, /* bAlternateSetting: Alternate setting */
0x02, /* bNumEndpoints: Two endpoints used */ 0x02, /* bNumEndpoints: Two endpoints used */
0x0A, /* bInterfaceClass: CDC */ 0x0A, /* bInterfaceClass: CDC */
0x00, /* bInterfaceSubClass: */ 0x00, /* bInterfaceSubClass */
0x00, /* bInterfaceProtocol: */ 0x00, /* bInterfaceProtocol */
0x00, /* iInterface: */ 0x00, /* iInterface */
/*Endpoint OUT Descriptor*/ /*Endpoint OUT Descriptor*/
0x07, /* bLength: Endpoint Descriptor size */ 0x07, /* bLength: Endpoint Descriptor size */
USB_DESC_TYPE_ENDPOINT, /* bDescriptorType: Endpoint */ USB_DESC_TYPE_ENDPOINT, /* bDescriptorType: Endpoint */
CDC_OUT_EP, /* bEndpointAddress */ CDC_OUT_EP, /* bEndpointAddress */
0x02, /* bmAttributes: Bulk */ 0x02, /* bmAttributes: Bulk */
0x40, /* wMaxPacketSize: */ 0x40, /* wMaxPacketSize */
0x00, 0x00,
0x00, /* bInterval: ignore for Bulk transfer */ 0x00, /* bInterval */
/*Endpoint IN Descriptor*/ /*Endpoint IN Descriptor*/
0x07, /* bLength: Endpoint Descriptor size */ 0x07, /* bLength: Endpoint Descriptor size */
USB_DESC_TYPE_ENDPOINT, /* bDescriptorType: Endpoint */ USB_DESC_TYPE_ENDPOINT, /* bDescriptorType: Endpoint */
CDC_IN_EP, /* bEndpointAddress */ CDC_IN_EP, /* bEndpointAddress */
0x02, /* bmAttributes: Bulk */ 0x02, /* bmAttributes: Bulk */
0x40, /* wMaxPacketSize: */ 0x40, /* wMaxPacketSize */
0x00, 0x00,
0x00 /* bInterval */ 0x00 /* bInterval */
}; };
@@ -458,7 +469,7 @@ static uint8_t USBD_CDC_Init(USBD_HandleTypeDef *pdev, uint8_t cfgidx)
UNUSED(cfgidx); UNUSED(cfgidx);
USBD_CDC_HandleTypeDef *hcdc; USBD_CDC_HandleTypeDef *hcdc;
hcdc = USBD_malloc(sizeof(USBD_CDC_HandleTypeDef)); hcdc = (USBD_CDC_HandleTypeDef *)USBD_malloc(sizeof(USBD_CDC_HandleTypeDef));
if (hcdc == NULL) if (hcdc == NULL)
{ {
@@ -474,16 +485,16 @@ static uint8_t USBD_CDC_Init(USBD_HandleTypeDef *pdev, uint8_t cfgidx)
(void)USBD_LL_OpenEP(pdev, CDC_IN_EP, USBD_EP_TYPE_BULK, (void)USBD_LL_OpenEP(pdev, CDC_IN_EP, USBD_EP_TYPE_BULK,
CDC_DATA_HS_IN_PACKET_SIZE); CDC_DATA_HS_IN_PACKET_SIZE);
pdev->ep_in[CDC_IN_EP & 0xFU].is_used = 1U; pdev->ep_in[CDC_IN_EP & 0xFU].is_used = 1U;
/* Open EP OUT */ /* Open EP OUT */
(void)USBD_LL_OpenEP(pdev, CDC_OUT_EP, USBD_EP_TYPE_BULK, (void)USBD_LL_OpenEP(pdev, CDC_OUT_EP, USBD_EP_TYPE_BULK,
CDC_DATA_HS_OUT_PACKET_SIZE); CDC_DATA_HS_OUT_PACKET_SIZE);
pdev->ep_out[CDC_OUT_EP & 0xFU].is_used = 1U; pdev->ep_out[CDC_OUT_EP & 0xFU].is_used = 1U;
/* Set bInterval for CDC CMD Endpoint */ /* Set bInterval for CDC CMD Endpoint */
pdev->ep_in[CDC_CMD_EP & 0xFU].bInterval = CDC_HS_BINTERVAL; pdev->ep_in[CDC_CMD_EP & 0xFU].bInterval = CDC_HS_BINTERVAL;
} }
else else
{ {
@@ -491,16 +502,16 @@ static uint8_t USBD_CDC_Init(USBD_HandleTypeDef *pdev, uint8_t cfgidx)
(void)USBD_LL_OpenEP(pdev, CDC_IN_EP, USBD_EP_TYPE_BULK, (void)USBD_LL_OpenEP(pdev, CDC_IN_EP, USBD_EP_TYPE_BULK,
CDC_DATA_FS_IN_PACKET_SIZE); CDC_DATA_FS_IN_PACKET_SIZE);
pdev->ep_in[CDC_IN_EP & 0xFU].is_used = 1U; pdev->ep_in[CDC_IN_EP & 0xFU].is_used = 1U;
/* Open EP OUT */ /* Open EP OUT */
(void)USBD_LL_OpenEP(pdev, CDC_OUT_EP, USBD_EP_TYPE_BULK, (void)USBD_LL_OpenEP(pdev, CDC_OUT_EP, USBD_EP_TYPE_BULK,
CDC_DATA_FS_OUT_PACKET_SIZE); CDC_DATA_FS_OUT_PACKET_SIZE);
pdev->ep_out[CDC_OUT_EP & 0xFU].is_used = 1U; pdev->ep_out[CDC_OUT_EP & 0xFU].is_used = 1U;
/* Set bInterval for CMD Endpoint */ /* Set bInterval for CMD Endpoint */
pdev->ep_in[CDC_CMD_EP & 0xFU].bInterval = CDC_FS_BINTERVAL; pdev->ep_in[CDC_CMD_EP & 0xFU].bInterval = CDC_FS_BINTERVAL;
} }
/* Open Command IN EP */ /* Open Command IN EP */
@@ -540,7 +551,6 @@ static uint8_t USBD_CDC_Init(USBD_HandleTypeDef *pdev, uint8_t cfgidx)
static uint8_t USBD_CDC_DeInit(USBD_HandleTypeDef *pdev, uint8_t cfgidx) static uint8_t USBD_CDC_DeInit(USBD_HandleTypeDef *pdev, uint8_t cfgidx)
{ {
UNUSED(cfgidx); UNUSED(cfgidx);
uint8_t ret = 0U;
/* Close EP IN */ /* Close EP IN */
(void)USBD_LL_CloseEP(pdev, CDC_IN_EP); (void)USBD_LL_CloseEP(pdev, CDC_IN_EP);
@@ -563,7 +573,7 @@ static uint8_t USBD_CDC_DeInit(USBD_HandleTypeDef *pdev, uint8_t cfgidx)
pdev->pClassData = NULL; pdev->pClassData = NULL;
} }
return ret; return (uint8_t)USBD_OK;
} }
/** /**
@@ -577,87 +587,94 @@ static uint8_t USBD_CDC_Setup(USBD_HandleTypeDef *pdev,
USBD_SetupReqTypedef *req) USBD_SetupReqTypedef *req)
{ {
USBD_CDC_HandleTypeDef *hcdc = (USBD_CDC_HandleTypeDef *)pdev->pClassData; USBD_CDC_HandleTypeDef *hcdc = (USBD_CDC_HandleTypeDef *)pdev->pClassData;
uint16_t len;
uint8_t ifalt = 0U; uint8_t ifalt = 0U;
uint16_t status_info = 0U; uint16_t status_info = 0U;
USBD_StatusTypeDef ret = USBD_OK; USBD_StatusTypeDef ret = USBD_OK;
if (hcdc == NULL)
{
return (uint8_t)USBD_FAIL;
}
switch (req->bmRequest & USB_REQ_TYPE_MASK) switch (req->bmRequest & USB_REQ_TYPE_MASK)
{ {
case USB_REQ_TYPE_CLASS: case USB_REQ_TYPE_CLASS:
if (req->wLength != 0U) if (req->wLength != 0U)
{ {
if ((req->bmRequest & 0x80U) != 0U) if ((req->bmRequest & 0x80U) != 0U)
{
((USBD_CDC_ItfTypeDef *)pdev->pUserData)->Control(req->bRequest,
(uint8_t *)hcdc->data,
req->wLength);
len = MIN(CDC_REQ_MAX_DATA_SIZE, req->wLength);
(void)USBD_CtlSendData(pdev, (uint8_t *)hcdc->data, len);
}
else
{
hcdc->CmdOpCode = req->bRequest;
hcdc->CmdLength = (uint8_t)MIN(req->wLength, USB_MAX_EP0_SIZE);
(void)USBD_CtlPrepareRx(pdev, (uint8_t *)hcdc->data, hcdc->CmdLength);
}
}
else
{ {
((USBD_CDC_ItfTypeDef *)pdev->pUserData)->Control(req->bRequest, ((USBD_CDC_ItfTypeDef *)pdev->pUserData)->Control(req->bRequest,
(uint8_t *)hcdc->data, (uint8_t *)req, 0U);
req->wLength);
(void)USBD_CtlSendData(pdev, (uint8_t *)hcdc->data, req->wLength);
}
else
{
hcdc->CmdOpCode = req->bRequest;
hcdc->CmdLength = (uint8_t)req->wLength;
(void)USBD_CtlPrepareRx(pdev, (uint8_t *)hcdc->data, req->wLength);
}
}
else
{
((USBD_CDC_ItfTypeDef *)pdev->pUserData)->Control(req->bRequest,
(uint8_t *)req, 0U);
}
break;
case USB_REQ_TYPE_STANDARD:
switch (req->bRequest)
{
case USB_REQ_GET_STATUS:
if (pdev->dev_state == USBD_STATE_CONFIGURED)
{
(void)USBD_CtlSendData(pdev, (uint8_t *)&status_info, 2U);
}
else
{
USBD_CtlError(pdev, req);
ret = USBD_FAIL;
} }
break; break;
case USB_REQ_GET_INTERFACE: case USB_REQ_TYPE_STANDARD:
if (pdev->dev_state == USBD_STATE_CONFIGURED) switch (req->bRequest)
{ {
(void)USBD_CtlSendData(pdev, &ifalt, 1U); case USB_REQ_GET_STATUS:
} if (pdev->dev_state == USBD_STATE_CONFIGURED)
else {
{ (void)USBD_CtlSendData(pdev, (uint8_t *)&status_info, 2U);
USBD_CtlError(pdev, req); }
ret = USBD_FAIL; else
} {
break; USBD_CtlError(pdev, req);
ret = USBD_FAIL;
}
break;
case USB_REQ_SET_INTERFACE: case USB_REQ_GET_INTERFACE:
if (pdev->dev_state != USBD_STATE_CONFIGURED) if (pdev->dev_state == USBD_STATE_CONFIGURED)
{ {
USBD_CtlError(pdev, req); (void)USBD_CtlSendData(pdev, &ifalt, 1U);
ret = USBD_FAIL; }
} else
break; {
USBD_CtlError(pdev, req);
ret = USBD_FAIL;
}
break;
case USB_REQ_CLEAR_FEATURE: case USB_REQ_SET_INTERFACE:
if (pdev->dev_state != USBD_STATE_CONFIGURED)
{
USBD_CtlError(pdev, req);
ret = USBD_FAIL;
}
break;
case USB_REQ_CLEAR_FEATURE:
break;
default:
USBD_CtlError(pdev, req);
ret = USBD_FAIL;
break;
}
break; break;
default: default:
USBD_CtlError(pdev, req); USBD_CtlError(pdev, req);
ret = USBD_FAIL; ret = USBD_FAIL;
break; break;
}
break;
default:
USBD_CtlError(pdev, req);
ret = USBD_FAIL;
break;
} }
return (uint8_t)ret; return (uint8_t)ret;
@@ -694,7 +711,11 @@ static uint8_t USBD_CDC_DataIn(USBD_HandleTypeDef *pdev, uint8_t epnum)
else else
{ {
hcdc->TxState = 0U; hcdc->TxState = 0U;
((USBD_CDC_ItfTypeDef *)pdev->pUserData)->TransmitCplt(hcdc->TxBuffer, &hcdc->TxLength, epnum);
if (((USBD_CDC_ItfTypeDef *)pdev->pUserData)->TransmitCplt != NULL)
{
((USBD_CDC_ItfTypeDef *)pdev->pUserData)->TransmitCplt(hcdc->TxBuffer, &hcdc->TxLength, epnum);
}
} }
return (uint8_t)USBD_OK; return (uint8_t)USBD_OK;
@@ -737,13 +758,17 @@ static uint8_t USBD_CDC_EP0_RxReady(USBD_HandleTypeDef *pdev)
{ {
USBD_CDC_HandleTypeDef *hcdc = (USBD_CDC_HandleTypeDef *)pdev->pClassData; USBD_CDC_HandleTypeDef *hcdc = (USBD_CDC_HandleTypeDef *)pdev->pClassData;
if (hcdc == NULL)
{
return (uint8_t)USBD_FAIL;
}
if ((pdev->pUserData != NULL) && (hcdc->CmdOpCode != 0xFFU)) if ((pdev->pUserData != NULL) && (hcdc->CmdOpCode != 0xFFU))
{ {
((USBD_CDC_ItfTypeDef *)pdev->pUserData)->Control(hcdc->CmdOpCode, ((USBD_CDC_ItfTypeDef *)pdev->pUserData)->Control(hcdc->CmdOpCode,
(uint8_t *)hcdc->data, (uint8_t *)hcdc->data,
(uint16_t)hcdc->CmdLength); (uint16_t)hcdc->CmdLength);
hcdc->CmdOpCode = 0xFFU; hcdc->CmdOpCode = 0xFFU;
} }
return (uint8_t)USBD_OK; return (uint8_t)USBD_OK;
@@ -778,7 +803,7 @@ static uint8_t *USBD_CDC_GetHSCfgDesc(uint16_t *length)
} }
/** /**
* @brief USBD_CDC_GetCfgDesc * @brief USBD_CDC_GetOtherSpeedCfgDesc
* Return configuration descriptor * Return configuration descriptor
* @param speed : current device speed * @param speed : current device speed
* @param length : pointer data length * @param length : pointer data length
@@ -792,11 +817,11 @@ static uint8_t *USBD_CDC_GetOtherSpeedCfgDesc(uint16_t *length)
} }
/** /**
* @brief DeviceQualifierDescriptor * @brief USBD_CDC_GetDeviceQualifierDescriptor
* return Device Qualifier descriptor * return Device Qualifier descriptor
* @param length : pointer data length * @param length : pointer data length
* @retval pointer to descriptor buffer * @retval pointer to descriptor buffer
*/ */
uint8_t *USBD_CDC_GetDeviceQualifierDescriptor(uint16_t *length) uint8_t *USBD_CDC_GetDeviceQualifierDescriptor(uint16_t *length)
{ {
*length = (uint16_t)sizeof(USBD_CDC_DeviceQualifierDesc); *length = (uint16_t)sizeof(USBD_CDC_DeviceQualifierDesc);
@@ -805,7 +830,7 @@ uint8_t *USBD_CDC_GetDeviceQualifierDescriptor(uint16_t *length)
} }
/** /**
* @brief USBD_CDC_RegisterInterface * @brief USBD_CDC_RegisterInterface
* @param pdev: device instance * @param pdev: device instance
* @param fops: CD Interface callback * @param fops: CD Interface callback
* @retval status * @retval status
@@ -834,13 +859,17 @@ uint8_t USBD_CDC_SetTxBuffer(USBD_HandleTypeDef *pdev,
{ {
USBD_CDC_HandleTypeDef *hcdc = (USBD_CDC_HandleTypeDef *)pdev->pClassData; USBD_CDC_HandleTypeDef *hcdc = (USBD_CDC_HandleTypeDef *)pdev->pClassData;
if (hcdc == NULL)
{
return (uint8_t)USBD_FAIL;
}
hcdc->TxBuffer = pbuff; hcdc->TxBuffer = pbuff;
hcdc->TxLength = length; hcdc->TxLength = length;
return (uint8_t)USBD_OK; return (uint8_t)USBD_OK;
} }
/** /**
* @brief USBD_CDC_SetRxBuffer * @brief USBD_CDC_SetRxBuffer
* @param pdev: device instance * @param pdev: device instance
@@ -851,6 +880,11 @@ uint8_t USBD_CDC_SetRxBuffer(USBD_HandleTypeDef *pdev, uint8_t *pbuff)
{ {
USBD_CDC_HandleTypeDef *hcdc = (USBD_CDC_HandleTypeDef *)pdev->pClassData; USBD_CDC_HandleTypeDef *hcdc = (USBD_CDC_HandleTypeDef *)pdev->pClassData;
if (hcdc == NULL)
{
return (uint8_t)USBD_FAIL;
}
hcdc->RxBuffer = pbuff; hcdc->RxBuffer = pbuff;
return (uint8_t)USBD_OK; return (uint8_t)USBD_OK;
@@ -889,7 +923,6 @@ uint8_t USBD_CDC_TransmitPacket(USBD_HandleTypeDef *pdev)
return (uint8_t)ret; return (uint8_t)ret;
} }
/** /**
* @brief USBD_CDC_ReceivePacket * @brief USBD_CDC_ReceivePacket
* prepare OUT Endpoint for reception * prepare OUT Endpoint for reception

View File

@@ -213,7 +213,7 @@ static int8_t TEMPLATE_Receive(uint8_t *Buf, uint32_t *Len)
/** /**
* @brief TEMPLATE_TransmitCplt * @brief TEMPLATE_TransmitCplt
* Data transmited callback * Data transmitted callback
* *
* @note * @note
* This function is IN transfer complete callback used to inform user that * This function is IN transfer complete callback used to inform user that

View File

@@ -75,6 +75,8 @@ extern "C" {
#define CDC_ECM_CONFIG_DESC_SIZ 79U #define CDC_ECM_CONFIG_DESC_SIZ 79U
#define CDC_ECM_DATA_BUFFER_SIZE 2000U
#define CDC_ECM_DATA_HS_IN_PACKET_SIZE CDC_ECM_DATA_HS_MAX_PACKET_SIZE #define CDC_ECM_DATA_HS_IN_PACKET_SIZE CDC_ECM_DATA_HS_MAX_PACKET_SIZE
#define CDC_ECM_DATA_HS_OUT_PACKET_SIZE CDC_ECM_DATA_HS_MAX_PACKET_SIZE #define CDC_ECM_DATA_HS_OUT_PACKET_SIZE CDC_ECM_DATA_HS_MAX_PACKET_SIZE
@@ -173,7 +175,7 @@ typedef struct
typedef struct typedef struct
{ {
uint32_t data[2000 / 4]; /* Force 32bits alignment */ uint32_t data[CDC_ECM_DATA_BUFFER_SIZE / 4U]; /* Force 32-bit alignment */
uint8_t CmdOpCode; uint8_t CmdOpCode;
uint8_t CmdLength; uint8_t CmdLength;
uint8_t Reserved1; /* Reserved Byte to force 4 bytes alignment of following fields */ uint8_t Reserved1; /* Reserved Byte to force 4 bytes alignment of following fields */

View File

@@ -113,7 +113,8 @@ __ALIGN_BEGIN static uint8_t USBD_CDC_ECM_DeviceQualifierDesc[USB_LEN_DEV_QUALIF
}; };
static uint32_t ConnSpeedTab[2] = {CDC_ECM_CONNECT_SPEED_UPSTREAM, static uint32_t ConnSpeedTab[2] = {CDC_ECM_CONNECT_SPEED_UPSTREAM,
CDC_ECM_CONNECT_SPEED_DOWNSTREAM}; CDC_ECM_CONNECT_SPEED_DOWNSTREAM
};
/** /**
* @} * @}
@@ -154,11 +155,15 @@ __ALIGN_BEGIN static uint8_t USBD_CDC_ECM_CfgHSDesc[] __ALIGN_END =
USB_DESC_TYPE_CONFIGURATION, /* bDescriptorType: Configuration */ USB_DESC_TYPE_CONFIGURATION, /* bDescriptorType: Configuration */
LOBYTE(CDC_ECM_CONFIG_DESC_SIZ), /* wTotalLength:no of returned bytes */ LOBYTE(CDC_ECM_CONFIG_DESC_SIZ), /* wTotalLength:no of returned bytes */
HIBYTE(CDC_ECM_CONFIG_DESC_SIZ), HIBYTE(CDC_ECM_CONFIG_DESC_SIZ),
0x02, /* bNumInterfaces: 2 interface */ 0x02, /* bNumInterfaces: 2 interfaces */
0x01, /* bConfigurationValue: Configuration value */ 0x01, /* bConfigurationValue: Configuration value */
0x00, /* iConfiguration: Index of string descriptor describing the configuration */ 0x00, /* iConfiguration: Index of string descriptor describing the configuration */
0xC0, /* bmAttributes: self powered */ #if (USBD_SELF_POWERED == 1U)
0x32, /* MaxPower 0 mA */ 0xC0, /* bmAttributes: Bus Powered according to user configuration */
#else
0x80, /* bmAttributes: Bus Powered according to user configuration */
#endif
USBD_MAX_POWER, /* MaxPower (mA) */
/*---------------------------------------------------------------------------*/ /*---------------------------------------------------------------------------*/
@@ -181,7 +186,7 @@ __ALIGN_BEGIN static uint8_t USBD_CDC_ECM_CfgHSDesc[] __ALIGN_END =
0x02, /* bInterfaceClass: Communication Interface Class */ 0x02, /* bInterfaceClass: Communication Interface Class */
0x06, /* bInterfaceSubClass: Ethernet Control Model */ 0x06, /* bInterfaceSubClass: Ethernet Control Model */
0x00, /* bInterfaceProtocol: No specific protocol required */ 0x00, /* bInterfaceProtocol: No specific protocol required */
0x00, /* iInterface: */ 0x00, /* iInterface */
/* Header Functional Descriptor */ /* Header Functional Descriptor */
0x05, /* bLength: Endpoint Descriptor size */ 0x05, /* bLength: Endpoint Descriptor size */
@@ -217,7 +222,7 @@ __ALIGN_BEGIN static uint8_t USBD_CDC_ECM_CfgHSDesc[] __ALIGN_END =
USB_DESC_TYPE_ENDPOINT, /* bDescriptorType: Endpoint */ USB_DESC_TYPE_ENDPOINT, /* bDescriptorType: Endpoint */
CDC_ECM_CMD_EP, /* bEndpointAddress */ CDC_ECM_CMD_EP, /* bEndpointAddress */
0x03, /* bmAttributes: Interrupt */ 0x03, /* bmAttributes: Interrupt */
LOBYTE(CDC_ECM_CMD_PACKET_SIZE), /* wMaxPacketSize: */ LOBYTE(CDC_ECM_CMD_PACKET_SIZE), /* wMaxPacketSize */
HIBYTE(CDC_ECM_CMD_PACKET_SIZE), HIBYTE(CDC_ECM_CMD_PACKET_SIZE),
CDC_ECM_HS_BINTERVAL, /* bInterval */ CDC_ECM_HS_BINTERVAL, /* bInterval */
@@ -230,27 +235,27 @@ __ALIGN_BEGIN static uint8_t USBD_CDC_ECM_CfgHSDesc[] __ALIGN_END =
0x00, /* bAlternateSetting: Alternate setting */ 0x00, /* bAlternateSetting: Alternate setting */
0x02, /* bNumEndpoints: Two endpoints used */ 0x02, /* bNumEndpoints: Two endpoints used */
0x0A, /* bInterfaceClass: CDC */ 0x0A, /* bInterfaceClass: CDC */
0x00, /* bInterfaceSubClass: */ 0x00, /* bInterfaceSubClass */
0x00, /* bInterfaceProtocol: */ 0x00, /* bInterfaceProtocol */
0x00, /* iInterface: */ 0x00, /* iInterface */
/* Endpoint OUT Descriptor */ /* Endpoint OUT Descriptor */
0x07, /* bLength: Endpoint Descriptor size */ 0x07, /* bLength: Endpoint Descriptor size */
USB_DESC_TYPE_ENDPOINT, /* bDescriptorType: Endpoint */ USB_DESC_TYPE_ENDPOINT, /* bDescriptorType: Endpoint */
CDC_ECM_OUT_EP, /* bEndpointAddress */ CDC_ECM_OUT_EP, /* bEndpointAddress */
0x02, /* bmAttributes: Bulk */ 0x02, /* bmAttributes: Bulk */
LOBYTE(CDC_ECM_DATA_HS_MAX_PACKET_SIZE), /* wMaxPacketSize: */ LOBYTE(CDC_ECM_DATA_HS_MAX_PACKET_SIZE), /* wMaxPacketSize */
HIBYTE(CDC_ECM_DATA_HS_MAX_PACKET_SIZE), HIBYTE(CDC_ECM_DATA_HS_MAX_PACKET_SIZE),
0xFF, /* bInterval: ignore for Bulk transfer */ 0x00, /* bInterval */
/* Endpoint IN Descriptor */ /* Endpoint IN Descriptor */
0x07, /* bLength: Endpoint Descriptor size */ 0x07, /* bLength: Endpoint Descriptor size */
USB_DESC_TYPE_ENDPOINT, /* bDescriptorType: Endpoint */ USB_DESC_TYPE_ENDPOINT, /* bDescriptorType: Endpoint */
CDC_ECM_IN_EP, /* bEndpointAddress */ CDC_ECM_IN_EP, /* bEndpointAddress */
0x02, /* bmAttributes: Bulk */ 0x02, /* bmAttributes: Bulk */
LOBYTE(CDC_ECM_DATA_HS_MAX_PACKET_SIZE), /* wMaxPacketSize: */ LOBYTE(CDC_ECM_DATA_HS_MAX_PACKET_SIZE), /* wMaxPacketSize */
HIBYTE(CDC_ECM_DATA_HS_MAX_PACKET_SIZE), HIBYTE(CDC_ECM_DATA_HS_MAX_PACKET_SIZE),
0xFF /* bInterval: ignore for Bulk transfer */ 0x00 /* bInterval */
}; };
@@ -262,11 +267,15 @@ __ALIGN_BEGIN static uint8_t USBD_CDC_ECM_CfgFSDesc[] __ALIGN_END =
USB_DESC_TYPE_CONFIGURATION, /* bDescriptorType: Configuration */ USB_DESC_TYPE_CONFIGURATION, /* bDescriptorType: Configuration */
LOBYTE(CDC_ECM_CONFIG_DESC_SIZ), /* wTotalLength: Total size of the Config descriptor */ LOBYTE(CDC_ECM_CONFIG_DESC_SIZ), /* wTotalLength: Total size of the Config descriptor */
HIBYTE(CDC_ECM_CONFIG_DESC_SIZ), HIBYTE(CDC_ECM_CONFIG_DESC_SIZ),
0x02, /* bNumInterfaces: 2 interface */ 0x02, /* bNumInterfaces: 2 interfaces */
0x01, /* bConfigurationValue: Configuration value */ 0x01, /* bConfigurationValue: Configuration value */
0x00, /* iConfiguration: Index of string descriptor describing the configuration */ 0x00, /* iConfiguration: Index of string descriptor describing the configuration */
0xC0, /* bmAttributes: self powered */ #if (USBD_SELF_POWERED == 1U)
0x32, /* MaxPower 0 mA */ 0xC0, /* bmAttributes: Bus Powered according to user configuration */
#else
0x80, /* bmAttributes: Bus Powered according to user configuration */
#endif
USBD_MAX_POWER, /* MaxPower (mA) */
/*---------------------------------------------------------------------------*/ /*---------------------------------------------------------------------------*/
/* IAD descriptor */ /* IAD descriptor */
@@ -288,7 +297,7 @@ __ALIGN_BEGIN static uint8_t USBD_CDC_ECM_CfgFSDesc[] __ALIGN_END =
0x02, /* bInterfaceClass: Communication Interface Class */ 0x02, /* bInterfaceClass: Communication Interface Class */
0x06, /* bInterfaceSubClass: Ethernet Control Model */ 0x06, /* bInterfaceSubClass: Ethernet Control Model */
0x00, /* bInterfaceProtocol: No specific protocol required */ 0x00, /* bInterfaceProtocol: No specific protocol required */
0x00, /* iInterface: */ 0x00, /* iInterface */
/* Header Functional Descriptor */ /* Header Functional Descriptor */
0x05, /* bLength: Endpoint Descriptor size */ 0x05, /* bLength: Endpoint Descriptor size */
@@ -325,7 +334,7 @@ __ALIGN_BEGIN static uint8_t USBD_CDC_ECM_CfgFSDesc[] __ALIGN_END =
USB_DESC_TYPE_ENDPOINT, /* bDescriptorType: Endpoint */ USB_DESC_TYPE_ENDPOINT, /* bDescriptorType: Endpoint */
CDC_ECM_CMD_EP, /* bEndpointAddress */ CDC_ECM_CMD_EP, /* bEndpointAddress */
0x03, /* bmAttributes: Interrupt */ 0x03, /* bmAttributes: Interrupt */
LOBYTE(CDC_ECM_CMD_PACKET_SIZE), /* wMaxPacketSize: */ LOBYTE(CDC_ECM_CMD_PACKET_SIZE), /* wMaxPacketSize */
HIBYTE(CDC_ECM_CMD_PACKET_SIZE), HIBYTE(CDC_ECM_CMD_PACKET_SIZE),
CDC_ECM_FS_BINTERVAL, /* bInterval */ CDC_ECM_FS_BINTERVAL, /* bInterval */
@@ -338,27 +347,27 @@ __ALIGN_BEGIN static uint8_t USBD_CDC_ECM_CfgFSDesc[] __ALIGN_END =
0x00, /* bAlternateSetting: Alternate setting */ 0x00, /* bAlternateSetting: Alternate setting */
0x02, /* bNumEndpoints: Two endpoints used */ 0x02, /* bNumEndpoints: Two endpoints used */
0x0A, /* bInterfaceClass: CDC_ECM */ 0x0A, /* bInterfaceClass: CDC_ECM */
0x00, /* bInterfaceSubClass: */ 0x00, /* bInterfaceSubClass */
0x00, /* bInterfaceProtocol: */ 0x00, /* bInterfaceProtocol */
0x00, /* iInterface: */ 0x00, /* iInterface */
/* Endpoint OUT Descriptor */ /* Endpoint OUT Descriptor */
0x07, /* bLength: Endpoint Descriptor size */ 0x07, /* bLength: Endpoint Descriptor size */
USB_DESC_TYPE_ENDPOINT, /* bDescriptorType: Endpoint */ USB_DESC_TYPE_ENDPOINT, /* bDescriptorType: Endpoint */
CDC_ECM_OUT_EP, /* bEndpointAddress */ CDC_ECM_OUT_EP, /* bEndpointAddress */
0x02, /* bmAttributes: Bulk */ 0x02, /* bmAttributes: Bulk */
LOBYTE(CDC_ECM_DATA_FS_MAX_PACKET_SIZE), /* wMaxPacketSize: */ LOBYTE(CDC_ECM_DATA_FS_MAX_PACKET_SIZE), /* wMaxPacketSize */
HIBYTE(CDC_ECM_DATA_FS_MAX_PACKET_SIZE), HIBYTE(CDC_ECM_DATA_FS_MAX_PACKET_SIZE),
0xFF, /* bInterval: ignore for Bulk transfer */ 0x00, /* bInterval */
/* Endpoint IN Descriptor */ /* Endpoint IN Descriptor */
0x07, /* bLength: Endpoint Descriptor size */ 0x07, /* bLength: Endpoint Descriptor size */
USB_DESC_TYPE_ENDPOINT, /* bDescriptorType: Endpoint */ USB_DESC_TYPE_ENDPOINT, /* bDescriptorType: Endpoint */
CDC_ECM_IN_EP, /* bEndpointAddress */ CDC_ECM_IN_EP, /* bEndpointAddress */
0x02, /* bmAttributes: Bulk */ 0x02, /* bmAttributes: Bulk */
LOBYTE(CDC_ECM_DATA_FS_MAX_PACKET_SIZE), /* wMaxPacketSize: */ LOBYTE(CDC_ECM_DATA_FS_MAX_PACKET_SIZE), /* wMaxPacketSize */
HIBYTE(CDC_ECM_DATA_FS_MAX_PACKET_SIZE), HIBYTE(CDC_ECM_DATA_FS_MAX_PACKET_SIZE),
0xFF /* bInterval: ignore for Bulk transfer */ 0x00 /* bInterval */
} ; } ;
__ALIGN_BEGIN static uint8_t USBD_CDC_ECM_OtherSpeedCfgDesc[] __ALIGN_END = __ALIGN_BEGIN static uint8_t USBD_CDC_ECM_OtherSpeedCfgDesc[] __ALIGN_END =
@@ -366,13 +375,17 @@ __ALIGN_BEGIN static uint8_t USBD_CDC_ECM_OtherSpeedCfgDesc[] __ALIGN_END =
/* Configuration Descriptor */ /* Configuration Descriptor */
0x09, /* bLength: Configuration Descriptor size */ 0x09, /* bLength: Configuration Descriptor size */
USB_DESC_TYPE_CONFIGURATION, /* bDescriptorType: Configuration */ USB_DESC_TYPE_CONFIGURATION, /* bDescriptorType: Configuration */
LOBYTE(CDC_ECM_CONFIG_DESC_SIZ), /* wTotalLength:no of returned bytes */ LOBYTE(CDC_ECM_CONFIG_DESC_SIZ), /* wTotalLength */
HIBYTE(CDC_ECM_CONFIG_DESC_SIZ), HIBYTE(CDC_ECM_CONFIG_DESC_SIZ),
0x02, /* bNumInterfaces: 2 interface */ 0x02, /* bNumInterfaces: 2 interfaces */
0x01, /* bConfigurationValue: Configuration value */ 0x01, /* bConfigurationValue: Configuration value */
0x04, /* iConfiguration: Index of string descriptor describing the configuration */ 0x04, /* iConfiguration: Index of string descriptor describing the configuration */
0xC0, /* bmAttributes: self powered */ #if (USBD_SELF_POWERED == 1U)
0x32, /* MaxPower 0 mA */ 0xC0, /* bmAttributes: Bus Powered according to user configuration */
#else
0x80, /* bmAttributes: Bus Powered according to user configuration */
#endif
USBD_MAX_POWER, /* MaxPower (mA) */
/*--------------------------------------- ------------------------------------*/ /*--------------------------------------- ------------------------------------*/
/* IAD descriptor */ /* IAD descriptor */
@@ -430,7 +443,7 @@ __ALIGN_BEGIN static uint8_t USBD_CDC_ECM_OtherSpeedCfgDesc[] __ALIGN_END =
USB_DESC_TYPE_ENDPOINT, /* bDescriptorType: Endpoint */ USB_DESC_TYPE_ENDPOINT, /* bDescriptorType: Endpoint */
CDC_ECM_CMD_EP, /* bEndpointAddress */ CDC_ECM_CMD_EP, /* bEndpointAddress */
0x03, /* bmAttributes: Interrupt */ 0x03, /* bmAttributes: Interrupt */
LOBYTE(CDC_ECM_CMD_PACKET_SIZE), /* wMaxPacketSize: */ LOBYTE(CDC_ECM_CMD_PACKET_SIZE), /* wMaxPacketSize */
HIBYTE(CDC_ECM_CMD_PACKET_SIZE), HIBYTE(CDC_ECM_CMD_PACKET_SIZE),
CDC_ECM_FS_BINTERVAL, /* bInterval */ CDC_ECM_FS_BINTERVAL, /* bInterval */
@@ -438,13 +451,13 @@ __ALIGN_BEGIN static uint8_t USBD_CDC_ECM_OtherSpeedCfgDesc[] __ALIGN_END =
/* Data class interface descriptor */ /* Data class interface descriptor */
0x09, /* bLength: Endpoint Descriptor size */ 0x09, /* bLength: Endpoint Descriptor size */
USB_DESC_TYPE_INTERFACE, /* bDescriptorType: */ USB_DESC_TYPE_INTERFACE, /* bDescriptorType: interface */
0x01, /* bInterfaceNumber: Number of Interface */ 0x01, /* bInterfaceNumber: Number of Interface */
0x00, /* bAlternateSetting: Alternate setting */ 0x00, /* bAlternateSetting: Alternate setting */
0x02, /* bNumEndpoints: Two endpoints used */ 0x02, /* bNumEndpoints: Two endpoints used */
0x0A, /* bInterfaceClass: CDC */ 0x0A, /* bInterfaceClass: CDC */
0x00, /* bInterfaceSubClass: */ 0x00, /* bInterfaceSubClass */
0x00, /* bInterfaceProtocol: */ 0x00, /* bInterfaceProtocol */
0x00, /* iInterface: */ 0x00, /* iInterface: */
/* Endpoint OUT Descriptor */ /* Endpoint OUT Descriptor */
@@ -452,18 +465,18 @@ __ALIGN_BEGIN static uint8_t USBD_CDC_ECM_OtherSpeedCfgDesc[] __ALIGN_END =
USB_DESC_TYPE_ENDPOINT, /* bDescriptorType: Endpoint */ USB_DESC_TYPE_ENDPOINT, /* bDescriptorType: Endpoint */
CDC_ECM_OUT_EP, /* bEndpointAddress */ CDC_ECM_OUT_EP, /* bEndpointAddress */
0x02, /* bmAttributes: Bulk */ 0x02, /* bmAttributes: Bulk */
0x40, /* wMaxPacketSize: */ 0x40, /* wMaxPacketSize */
0x00, 0x00,
0xFF, /* bInterval: ignore for Bulk transfer */ 0x00, /* bInterval */
/* Endpoint IN Descriptor */ /* Endpoint IN Descriptor */
0x07, /* bLength: Endpoint Descriptor size */ 0x07, /* bLength: Endpoint Descriptor size */
USB_DESC_TYPE_ENDPOINT, /* bDescriptorType: Endpoint */ USB_DESC_TYPE_ENDPOINT, /* bDescriptorType: Endpoint */
CDC_ECM_IN_EP, /* bEndpointAddress */ CDC_ECM_IN_EP, /* bEndpointAddress */
0x02, /* bmAttributes: Bulk */ 0x02, /* bmAttributes: Bulk */
0x40, /* wMaxPacketSize: */ 0x40, /* wMaxPacketSize */
0x00, 0x00,
0xFF /* bInterval: ignore for Bulk transfer */ 0x00 /* bInterval */
}; };
/** /**
@@ -487,7 +500,7 @@ static uint8_t USBD_CDC_ECM_Init(USBD_HandleTypeDef *pdev, uint8_t cfgidx)
USBD_CDC_ECM_HandleTypeDef *hcdc; USBD_CDC_ECM_HandleTypeDef *hcdc;
hcdc = USBD_malloc(sizeof(USBD_CDC_ECM_HandleTypeDef)); hcdc = (USBD_CDC_ECM_HandleTypeDef *)USBD_malloc(sizeof(USBD_CDC_ECM_HandleTypeDef));
if (hcdc == NULL) if (hcdc == NULL)
{ {
@@ -602,84 +615,91 @@ static uint8_t USBD_CDC_ECM_Setup(USBD_HandleTypeDef *pdev,
USBD_CDC_ECM_HandleTypeDef *hcdc = (USBD_CDC_ECM_HandleTypeDef *) pdev->pClassData; USBD_CDC_ECM_HandleTypeDef *hcdc = (USBD_CDC_ECM_HandleTypeDef *) pdev->pClassData;
USBD_CDC_ECM_ItfTypeDef *EcmInterface = (USBD_CDC_ECM_ItfTypeDef *)pdev->pUserData; USBD_CDC_ECM_ItfTypeDef *EcmInterface = (USBD_CDC_ECM_ItfTypeDef *)pdev->pUserData;
USBD_StatusTypeDef ret = USBD_OK; USBD_StatusTypeDef ret = USBD_OK;
uint8_t ifalt = 0U; uint16_t len;
uint16_t status_info = 0U; uint16_t status_info = 0U;
uint8_t ifalt = 0U;
if (hcdc == NULL)
{
return (uint8_t)USBD_FAIL;
}
switch (req->bmRequest & USB_REQ_TYPE_MASK) switch (req->bmRequest & USB_REQ_TYPE_MASK)
{ {
case USB_REQ_TYPE_CLASS : case USB_REQ_TYPE_CLASS :
if (req->wLength != 0U) if (req->wLength != 0U)
{
if ((req->bmRequest & 0x80U) != 0U)
{ {
EcmInterface->Control(req->bRequest, if ((req->bmRequest & 0x80U) != 0U)
(uint8_t *)hcdc->data, req->wLength); {
EcmInterface->Control(req->bRequest,
(uint8_t *)hcdc->data, req->wLength);
(void)USBD_CtlSendData(pdev, (uint8_t *)hcdc->data, req->wLength); len = MIN(CDC_ECM_DATA_BUFFER_SIZE, req->wLength);
(void)USBD_CtlSendData(pdev, (uint8_t *)hcdc->data, len);
}
else
{
hcdc->CmdOpCode = req->bRequest;
hcdc->CmdLength = (uint8_t)MIN(req->wLength, USB_MAX_EP0_SIZE);
(void)USBD_CtlPrepareRx(pdev, (uint8_t *)hcdc->data, hcdc->CmdLength);
}
} }
else else
{ {
hcdc->CmdOpCode = req->bRequest; EcmInterface->Control(req->bRequest, (uint8_t *)req, 0U);
hcdc->CmdLength = (uint8_t)req->wLength;
(void)USBD_CtlPrepareRx(pdev, (uint8_t *)hcdc->data, req->wLength);
}
}
else
{
EcmInterface->Control(req->bRequest, (uint8_t *)req, 0U);
}
break;
case USB_REQ_TYPE_STANDARD:
switch (req->bRequest)
{
case USB_REQ_GET_STATUS:
if (pdev->dev_state == USBD_STATE_CONFIGURED)
{
(void)USBD_CtlSendData(pdev, (uint8_t *)&status_info, 2U);
}
else
{
USBD_CtlError(pdev, req);
ret = USBD_FAIL;
} }
break; break;
case USB_REQ_GET_INTERFACE: case USB_REQ_TYPE_STANDARD:
if (pdev->dev_state == USBD_STATE_CONFIGURED) switch (req->bRequest)
{ {
(void)USBD_CtlSendData(pdev, &ifalt, 1U); case USB_REQ_GET_STATUS:
} if (pdev->dev_state == USBD_STATE_CONFIGURED)
else {
{ (void)USBD_CtlSendData(pdev, (uint8_t *)&status_info, 2U);
USBD_CtlError(pdev, req); }
ret = USBD_FAIL; else
} {
break; USBD_CtlError(pdev, req);
ret = USBD_FAIL;
}
break;
case USB_REQ_SET_INTERFACE: case USB_REQ_GET_INTERFACE:
if (pdev->dev_state != USBD_STATE_CONFIGURED) if (pdev->dev_state == USBD_STATE_CONFIGURED)
{ {
USBD_CtlError(pdev, req); (void)USBD_CtlSendData(pdev, &ifalt, 1U);
ret = USBD_FAIL; }
} else
break; {
USBD_CtlError(pdev, req);
ret = USBD_FAIL;
}
break;
case USB_REQ_CLEAR_FEATURE: case USB_REQ_SET_INTERFACE:
if (pdev->dev_state != USBD_STATE_CONFIGURED)
{
USBD_CtlError(pdev, req);
ret = USBD_FAIL;
}
break;
case USB_REQ_CLEAR_FEATURE:
break;
default:
USBD_CtlError(pdev, req);
ret = USBD_FAIL;
break;
}
break; break;
default: default:
USBD_CtlError(pdev, req); USBD_CtlError(pdev, req);
ret = USBD_FAIL; ret = USBD_FAIL;
break; break;
}
break;
default:
USBD_CtlError(pdev, req);
ret = USBD_FAIL;
break;
} }
return (uint8_t)ret; return (uint8_t)ret;
@@ -716,7 +736,10 @@ static uint8_t USBD_CDC_ECM_DataIn(USBD_HandleTypeDef *pdev, uint8_t epnum)
else else
{ {
hcdc->TxState = 0U; hcdc->TxState = 0U;
((USBD_CDC_ECM_ItfTypeDef *)pdev->pUserData)->TransmitCplt(hcdc->TxBuffer, &hcdc->TxLength, epnum); if (((USBD_CDC_ECM_ItfTypeDef *)pdev->pUserData)->TransmitCplt != NULL)
{
((USBD_CDC_ECM_ItfTypeDef *)pdev->pUserData)->TransmitCplt(hcdc->TxBuffer, &hcdc->TxLength, epnum);
}
} }
} }
else if (epnum == (CDC_ECM_CMD_EP & 0x7FU)) else if (epnum == (CDC_ECM_CMD_EP & 0x7FU))
@@ -766,7 +789,7 @@ static uint8_t USBD_CDC_ECM_DataOut(USBD_HandleTypeDef *pdev, uint8_t epnum)
if ((CurrPcktLen < hcdc->MaxPcktLen) || (hcdc->RxLength >= CDC_ECM_ETH_MAX_SEGSZE)) if ((CurrPcktLen < hcdc->MaxPcktLen) || (hcdc->RxLength >= CDC_ECM_ETH_MAX_SEGSZE))
{ {
/* USB data will be immediately processed, this allow next USB traffic being /* USB data will be immediately processed, this allow next USB traffic being
NACKed till the end of the application Xfer */ NAKed till the end of the application Xfer */
/* Process data by application (ie. copy to app buffer or notify user) /* Process data by application (ie. copy to app buffer or notify user)
hcdc->RxLength must be reset to zero at the end of the call of this function */ hcdc->RxLength must be reset to zero at the end of the call of this function */
@@ -798,6 +821,11 @@ static uint8_t USBD_CDC_ECM_EP0_RxReady(USBD_HandleTypeDef *pdev)
{ {
USBD_CDC_ECM_HandleTypeDef *hcdc = (USBD_CDC_ECM_HandleTypeDef *)pdev->pClassData; USBD_CDC_ECM_HandleTypeDef *hcdc = (USBD_CDC_ECM_HandleTypeDef *)pdev->pClassData;
if (hcdc == NULL)
{
return (uint8_t)USBD_FAIL;
}
if ((pdev->pUserData != NULL) && (hcdc->CmdOpCode != 0xFFU)) if ((pdev->pUserData != NULL) && (hcdc->CmdOpCode != 0xFFU))
{ {
((USBD_CDC_ECM_ItfTypeDef *)pdev->pUserData)->Control(hcdc->CmdOpCode, ((USBD_CDC_ECM_ItfTypeDef *)pdev->pUserData)->Control(hcdc->CmdOpCode,
@@ -921,6 +949,11 @@ uint8_t USBD_CDC_ECM_SetTxBuffer(USBD_HandleTypeDef *pdev, uint8_t *pbuff, uint3
{ {
USBD_CDC_ECM_HandleTypeDef *hcdc = (USBD_CDC_ECM_HandleTypeDef *)pdev->pClassData; USBD_CDC_ECM_HandleTypeDef *hcdc = (USBD_CDC_ECM_HandleTypeDef *)pdev->pClassData;
if (hcdc == NULL)
{
return (uint8_t)USBD_FAIL;
}
hcdc->TxBuffer = pbuff; hcdc->TxBuffer = pbuff;
hcdc->TxLength = length; hcdc->TxLength = length;
@@ -938,6 +971,11 @@ uint8_t USBD_CDC_ECM_SetRxBuffer(USBD_HandleTypeDef *pdev, uint8_t *pbuff)
{ {
USBD_CDC_ECM_HandleTypeDef *hcdc = (USBD_CDC_ECM_HandleTypeDef *)pdev->pClassData; USBD_CDC_ECM_HandleTypeDef *hcdc = (USBD_CDC_ECM_HandleTypeDef *)pdev->pClassData;
if (hcdc == NULL)
{
return (uint8_t)USBD_FAIL;
}
hcdc->RxBuffer = pbuff; hcdc->RxBuffer = pbuff;
return (uint8_t)USBD_OK; return (uint8_t)USBD_OK;
@@ -970,7 +1008,7 @@ uint8_t USBD_CDC_ECM_TransmitPacket(USBD_HandleTypeDef *pdev)
/* Transmit next packet */ /* Transmit next packet */
(void)USBD_LL_Transmit(pdev, CDC_ECM_IN_EP, hcdc->TxBuffer, hcdc->TxLength); (void)USBD_LL_Transmit(pdev, CDC_ECM_IN_EP, hcdc->TxBuffer, hcdc->TxLength);
ret = USBD_OK; ret = USBD_OK;
} }
return (uint8_t)ret; return (uint8_t)ret;
@@ -993,7 +1031,7 @@ uint8_t USBD_CDC_ECM_ReceivePacket(USBD_HandleTypeDef *pdev)
} }
/* Prepare Out endpoint to receive next packet */ /* Prepare Out endpoint to receive next packet */
(void)USBD_LL_PrepareReceive(pdev, CDC_ECM_OUT_EP,hcdc->RxBuffer, hcdc->MaxPcktLen); (void)USBD_LL_PrepareReceive(pdev, CDC_ECM_OUT_EP, hcdc->RxBuffer, hcdc->MaxPcktLen);
return (uint8_t)USBD_OK; return (uint8_t)USBD_OK;
} }
@@ -1016,11 +1054,16 @@ uint8_t USBD_CDC_ECM_SendNotification(USBD_HandleTypeDef *pdev,
USBD_CDC_ECM_HandleTypeDef *hcdc = (USBD_CDC_ECM_HandleTypeDef *)pdev->pClassData; USBD_CDC_ECM_HandleTypeDef *hcdc = (USBD_CDC_ECM_HandleTypeDef *)pdev->pClassData;
USBD_StatusTypeDef ret = USBD_OK; USBD_StatusTypeDef ret = USBD_OK;
if (hcdc == NULL)
{
return (uint8_t)USBD_FAIL;
}
/* Initialize the request fields */ /* Initialize the request fields */
(hcdc->Req).bmRequest = CDC_ECM_BMREQUEST_TYPE_ECM; (hcdc->Req).bmRequest = CDC_ECM_BMREQUEST_TYPE_ECM;
(hcdc->Req).bRequest = (uint8_t)Notif; (hcdc->Req).bRequest = (uint8_t)Notif;
switch (Notif) switch ((hcdc->Req).bRequest)
{ {
case NETWORK_CONNECTION: case NETWORK_CONNECTION:
(hcdc->Req).wValue = bVal; (hcdc->Req).wValue = bVal;
@@ -1069,7 +1112,7 @@ uint8_t USBD_CDC_ECM_SendNotification(USBD_HandleTypeDef *pdev,
/* Transmit notification packet */ /* Transmit notification packet */
if (ReqSize != 0U) if (ReqSize != 0U)
{ {
(void)USBD_LL_Transmit(pdev, CDC_ECM_CMD_EP, (uint8_t *)&(hcdc->Req), ReqSize); (void)USBD_LL_Transmit(pdev, CDC_ECM_CMD_EP, (uint8_t *) &(hcdc->Req), ReqSize);
} }
return (uint8_t)ret; return (uint8_t)ret;

View File

@@ -32,12 +32,12 @@
/* Private variables ---------------------------------------------------------*/ /* Private variables ---------------------------------------------------------*/
#if defined ( __ICCARM__ ) /*!< IAR Compiler */ #if defined ( __ICCARM__ ) /*!< IAR Compiler */
#pragma data_alignment=4 #pragma data_alignment=4
#endif #endif
__ALIGN_BEGIN static uint8_t UserRxBuffer[CDC_ECM_ETH_MAX_SEGSZE + 100]__ALIGN_END; /* Received Data over USB are stored in this buffer */ __ALIGN_BEGIN static uint8_t UserRxBuffer[CDC_ECM_ETH_MAX_SEGSZE + 100]__ALIGN_END; /* Received Data over USB are stored in this buffer */
#if defined ( __ICCARM__ ) /*!< IAR Compiler */ #if defined ( __ICCARM__ ) /*!< IAR Compiler */
#pragma data_alignment=4 #pragma data_alignment=4
#endif #endif
__ALIGN_BEGIN static uint8_t UserTxBuffer[CDC_ECM_ETH_MAX_SEGSZE + 100]__ALIGN_END; /* Received Data over CDC_ECM (CDC_ECM interface) are stored in this buffer */ __ALIGN_BEGIN static uint8_t UserTxBuffer[CDC_ECM_ETH_MAX_SEGSZE + 100]__ALIGN_END; /* Received Data over CDC_ECM (CDC_ECM interface) are stored in this buffer */
@@ -133,15 +133,15 @@ static int8_t CDC_ECM_Itf_Control(uint8_t cmd, uint8_t *pbuf, uint16_t length)
/* Add your code here */ /* Add your code here */
break; break;
case CDC_ECM_SET_ETH_PWRM_PATTERN_FILTER: case CDC_ECM_SET_ETH_PWRM_PATTERN_FILTER:
/* Add your code here */ /* Add your code here */
break; break;
case CDC_ECM_GET_ETH_PWRM_PATTERN_FILTER: case CDC_ECM_GET_ETH_PWRM_PATTERN_FILTER:
/* Add your code here */ /* Add your code here */
break; break;
case CDC_ECM_SET_ETH_PACKET_FILTER: case CDC_ECM_SET_ETH_PACKET_FILTER:
/* Check if this is the first time we enter */ /* Check if this is the first time we enter */
if (hcdc_cdc_ecm->LinkStatus == 0U) if (hcdc_cdc_ecm->LinkStatus == 0U)
{ {
@@ -164,7 +164,7 @@ static int8_t CDC_ECM_Itf_Control(uint8_t cmd, uint8_t *pbuf, uint16_t length)
/* Add your code here */ /* Add your code here */
break; break;
case CDC_ECM_GET_ETH_STATISTIC: case CDC_ECM_GET_ETH_STATISTIC:
/* Add your code here */ /* Add your code here */
break; break;
@@ -201,7 +201,7 @@ static int8_t CDC_ECM_Itf_Receive(uint8_t *Buf, uint32_t *Len)
/** /**
* @brief CDC_ECM_Itf_TransmitCplt * @brief CDC_ECM_Itf_TransmitCplt
* Data transmited callback * Data transmitted callback
* *
* @note * @note
* This function is IN transfer complete callback used to inform user that * This function is IN transfer complete callback used to inform user that

View File

@@ -243,7 +243,7 @@ typedef struct
typedef struct typedef struct
{ {
uint32_t data[2000 / 4]; /* Force 32bits alignment */ uint32_t data[CDC_RNDIS_MAX_DATA_SZE / 4U]; /* Force 32-bit alignment */
uint8_t CmdOpCode; uint8_t CmdOpCode;
uint8_t CmdLength; uint8_t CmdLength;
uint8_t ResponseRdy; /* Indicates if the Device Response to an CDC_RNDIS msg is ready */ uint8_t ResponseRdy; /* Indicates if the Device Response to an CDC_RNDIS msg is ready */

File diff suppressed because it is too large Load Diff

View File

@@ -38,12 +38,12 @@
/* Private macro -------------------------------------------------------------*/ /* Private macro -------------------------------------------------------------*/
/* Private variables ---------------------------------------------------------*/ /* Private variables ---------------------------------------------------------*/
#if defined ( __ICCARM__ ) /*!< IAR Compiler */ #if defined ( __ICCARM__ ) /*!< IAR Compiler */
#pragma data_alignment=4 #pragma data_alignment=4
#endif #endif
__ALIGN_BEGIN uint8_t UserRxBuffer[CDC_RNDIS_ETH_MAX_SEGSZE + 100] __ALIGN_END; /* Received Data over USB are stored in this buffer */ __ALIGN_BEGIN uint8_t UserRxBuffer[CDC_RNDIS_ETH_MAX_SEGSZE + 100] __ALIGN_END; /* Received Data over USB are stored in this buffer */
#if defined ( __ICCARM__ ) /*!< IAR Compiler */ #if defined ( __ICCARM__ ) /*!< IAR Compiler */
#pragma data_alignment=4 #pragma data_alignment=4
#endif #endif
__ALIGN_BEGIN static uint8_t UserTxBuffer[CDC_RNDIS_ETH_MAX_SEGSZE + 100] __ALIGN_END; /* Received Data over CDC_RNDIS (CDC_RNDIS interface) are stored in this buffer */ __ALIGN_BEGIN static uint8_t UserTxBuffer[CDC_RNDIS_ETH_MAX_SEGSZE + 100] __ALIGN_END; /* Received Data over CDC_RNDIS (CDC_RNDIS interface) are stored in this buffer */
@@ -179,14 +179,14 @@ static int8_t CDC_RNDIS_Itf_Receive(uint8_t *Buf, uint32_t *Len)
hcdc_cdc_rndis->RxState = 1U; hcdc_cdc_rndis->RxState = 1U;
UNUSED(Buf); UNUSED(Buf);
UNUSED(Len); UNUSED(Len);
return (0); return (0);
} }
/** /**
* @brief CDC_RNDIS_Itf_TransmitCplt * @brief CDC_RNDIS_Itf_TransmitCplt
* Data transmited callback * Data transmitted callback
* *
* @note * @note
* This function is IN transfer complete callback used to inform user that * This function is IN transfer complete callback used to inform user that

View File

@@ -42,10 +42,16 @@ extern "C" {
* @{ * @{
*/ */
#define CUSTOM_HID_EPIN_ADDR 0x81U #define CUSTOM_HID_EPIN_ADDR 0x81U
#ifndef CUSTOM_HID_EPIN_SIZE
#define CUSTOM_HID_EPIN_SIZE 0x02U #define CUSTOM_HID_EPIN_SIZE 0x02U
#endif
#define CUSTOM_HID_EPOUT_ADDR 0x01U #define CUSTOM_HID_EPOUT_ADDR 0x01U
#ifndef CUSTOM_HID_EPOUT_SIZE
#define CUSTOM_HID_EPOUT_SIZE 0x02U #define CUSTOM_HID_EPOUT_SIZE 0x02U
#endif
#define USB_CUSTOM_HID_CONFIG_DESC_SIZ 41U #define USB_CUSTOM_HID_CONFIG_DESC_SIZ 41U
#define USB_CUSTOM_HID_DESC_SIZ 9U #define USB_CUSTOM_HID_DESC_SIZ 9U

View File

@@ -128,14 +128,17 @@ __ALIGN_BEGIN static uint8_t USBD_CUSTOM_HID_CfgFSDesc[USB_CUSTOM_HID_CONFIG_DES
{ {
0x09, /* bLength: Configuration Descriptor size */ 0x09, /* bLength: Configuration Descriptor size */
USB_DESC_TYPE_CONFIGURATION, /* bDescriptorType: Configuration */ USB_DESC_TYPE_CONFIGURATION, /* bDescriptorType: Configuration */
USB_CUSTOM_HID_CONFIG_DESC_SIZ, USB_CUSTOM_HID_CONFIG_DESC_SIZ, /* wTotalLength: Bytes returned */
/* wTotalLength: Bytes returned */
0x00, 0x00,
0x01, /* bNumInterfaces: 1 interface */ 0x01, /* bNumInterfaces: 1 interface */
0x01, /* bConfigurationValue: Configuration value */ 0x01, /* bConfigurationValue: Configuration value */
0x00, /* iConfiguration: Index of string descriptor describing the configuration */ 0x00, /* iConfiguration: Index of string descriptor describing the configuration */
0xC0, /* bmAttributes: bus powered */ #if (USBD_SELF_POWERED == 1U)
0x32, /* MaxPower 100 mA: this current is used for detecting Vbus */ 0xC0, /* bmAttributes: Bus Powered according to user configuration */
#else
0x80, /* bmAttributes: Bus Powered according to user configuration */
#endif
USBD_MAX_POWER, /* MaxPower (mA) */
/************** Descriptor of CUSTOM HID interface ****************/ /************** Descriptor of CUSTOM HID interface ****************/
/* 09 */ /* 09 */
@@ -166,7 +169,7 @@ __ALIGN_BEGIN static uint8_t USBD_CUSTOM_HID_CfgFSDesc[USB_CUSTOM_HID_CONFIG_DES
CUSTOM_HID_EPIN_ADDR, /* bEndpointAddress: Endpoint Address (IN) */ CUSTOM_HID_EPIN_ADDR, /* bEndpointAddress: Endpoint Address (IN) */
0x03, /* bmAttributes: Interrupt endpoint */ 0x03, /* bmAttributes: Interrupt endpoint */
CUSTOM_HID_EPIN_SIZE, /* wMaxPacketSize: 2 Byte max */ CUSTOM_HID_EPIN_SIZE, /* wMaxPacketSize: 2 Bytes max */
0x00, 0x00,
CUSTOM_HID_FS_BINTERVAL, /* bInterval: Polling Interval */ CUSTOM_HID_FS_BINTERVAL, /* bInterval: Polling Interval */
/* 34 */ /* 34 */
@@ -186,14 +189,17 @@ __ALIGN_BEGIN static uint8_t USBD_CUSTOM_HID_CfgHSDesc[USB_CUSTOM_HID_CONFIG_DES
{ {
0x09, /* bLength: Configuration Descriptor size */ 0x09, /* bLength: Configuration Descriptor size */
USB_DESC_TYPE_CONFIGURATION, /* bDescriptorType: Configuration */ USB_DESC_TYPE_CONFIGURATION, /* bDescriptorType: Configuration */
USB_CUSTOM_HID_CONFIG_DESC_SIZ, USB_CUSTOM_HID_CONFIG_DESC_SIZ, /* wTotalLength: Bytes returned */
/* wTotalLength: Bytes returned */
0x00, 0x00,
0x01, /* bNumInterfaces: 1 interface */ 0x01, /* bNumInterfaces: 1 interface */
0x01, /* bConfigurationValue: Configuration value */ 0x01, /* bConfigurationValue: Configuration value */
0x00, /* iConfiguration: Index of string descriptor describing the configuration */ 0x00, /* iConfiguration: Index of string descriptor describing the configuration */
0xC0, /* bmAttributes: bus powered */ #if (USBD_SELF_POWERED == 1U)
0x32, /* MaxPower 100 mA: this current is used for detecting Vbus */ 0xC0, /* bmAttributes: Bus Powered according to user configuration */
#else
0x80, /* bmAttributes: Bus Powered according to user configuration */
#endif
USBD_MAX_POWER, /* MaxPower (mA) */
/************** Descriptor of CUSTOM HID interface ****************/ /************** Descriptor of CUSTOM HID interface ****************/
/* 09 */ /* 09 */
@@ -220,11 +226,11 @@ __ALIGN_BEGIN static uint8_t USBD_CUSTOM_HID_CfgHSDesc[USB_CUSTOM_HID_CONFIG_DES
/******************** Descriptor of Custom HID endpoints ********************/ /******************** Descriptor of Custom HID endpoints ********************/
/* 27 */ /* 27 */
0x07, /* bLength: Endpoint Descriptor size */ 0x07, /* bLength: Endpoint Descriptor size */
USB_DESC_TYPE_ENDPOINT, /* bDescriptorType: */ USB_DESC_TYPE_ENDPOINT, /* bDescriptorType */
CUSTOM_HID_EPIN_ADDR, /* bEndpointAddress: Endpoint Address (IN) */ CUSTOM_HID_EPIN_ADDR, /* bEndpointAddress: Endpoint Address (IN) */
0x03, /* bmAttributes: Interrupt endpoint */ 0x03, /* bmAttributes: Interrupt endpoint */
CUSTOM_HID_EPIN_SIZE, /* wMaxPacketSize: 2 Byte max */ CUSTOM_HID_EPIN_SIZE, /* wMaxPacketSize: 2 Bytes max */
0x00, 0x00,
CUSTOM_HID_HS_BINTERVAL, /* bInterval: Polling Interval */ CUSTOM_HID_HS_BINTERVAL, /* bInterval: Polling Interval */
/* 34 */ /* 34 */
@@ -244,14 +250,17 @@ __ALIGN_BEGIN static uint8_t USBD_CUSTOM_HID_OtherSpeedCfgDesc[USB_CUSTOM_HID_CO
{ {
0x09, /* bLength: Configuration Descriptor size */ 0x09, /* bLength: Configuration Descriptor size */
USB_DESC_TYPE_CONFIGURATION, /* bDescriptorType: Configuration */ USB_DESC_TYPE_CONFIGURATION, /* bDescriptorType: Configuration */
USB_CUSTOM_HID_CONFIG_DESC_SIZ, USB_CUSTOM_HID_CONFIG_DESC_SIZ, /* wTotalLength: Bytes returned */
/* wTotalLength: Bytes returned */
0x00, 0x00,
0x01, /* bNumInterfaces: 1 interface */ 0x01, /* bNumInterfaces: 1 interface */
0x01, /* bConfigurationValue: Configuration value */ 0x01, /* bConfigurationValue: Configuration value */
0x00, /* iConfiguration: Index of string descriptor describing the configuration */ 0x00, /* iConfiguration: Index of string descriptor describing the configuration */
0xC0, /* bmAttributes: bus powered */ #if (USBD_SELF_POWERED == 1U)
0x32, /* MaxPower 100 mA: this current is used for detecting Vbus */ 0xC0, /* bmAttributes: Bus Powered according to user configuration */
#else
0x80, /* bmAttributes: Bus Powered according to user configuration */
#endif
USBD_MAX_POWER, /* MaxPower (mA) */
/************** Descriptor of CUSTOM HID interface ****************/ /************** Descriptor of CUSTOM HID interface ****************/
/* 09 */ /* 09 */
@@ -282,7 +291,7 @@ __ALIGN_BEGIN static uint8_t USBD_CUSTOM_HID_OtherSpeedCfgDesc[USB_CUSTOM_HID_CO
CUSTOM_HID_EPIN_ADDR, /* bEndpointAddress: Endpoint Address (IN) */ CUSTOM_HID_EPIN_ADDR, /* bEndpointAddress: Endpoint Address (IN) */
0x03, /* bmAttributes: Interrupt endpoint */ 0x03, /* bmAttributes: Interrupt endpoint */
CUSTOM_HID_EPIN_SIZE, /* wMaxPacketSize: 2 Byte max */ CUSTOM_HID_EPIN_SIZE, /* wMaxPacketSize: 2 Bytes max */
0x00, 0x00,
CUSTOM_HID_FS_BINTERVAL, /* bInterval: Polling Interval */ CUSTOM_HID_FS_BINTERVAL, /* bInterval: Polling Interval */
/* 34 */ /* 34 */
@@ -347,7 +356,7 @@ static uint8_t USBD_CUSTOM_HID_Init(USBD_HandleTypeDef *pdev, uint8_t cfgidx)
UNUSED(cfgidx); UNUSED(cfgidx);
USBD_CUSTOM_HID_HandleTypeDef *hhid; USBD_CUSTOM_HID_HandleTypeDef *hhid;
hhid = USBD_malloc(sizeof(USBD_CUSTOM_HID_HandleTypeDef)); hhid = (USBD_CUSTOM_HID_HandleTypeDef *)USBD_malloc(sizeof(USBD_CUSTOM_HID_HandleTypeDef));
if (hhid == NULL) if (hhid == NULL)
{ {
@@ -412,7 +421,7 @@ static uint8_t USBD_CUSTOM_HID_DeInit(USBD_HandleTypeDef *pdev, uint8_t cfgidx)
pdev->ep_out[CUSTOM_HID_EPOUT_ADDR & 0xFU].is_used = 0U; pdev->ep_out[CUSTOM_HID_EPOUT_ADDR & 0xFU].is_used = 0U;
pdev->ep_out[CUSTOM_HID_EPOUT_ADDR & 0xFU].bInterval = 0U; pdev->ep_out[CUSTOM_HID_EPOUT_ADDR & 0xFU].bInterval = 0U;
/* FRee allocated memory */ /* Free allocated memory */
if (pdev->pClassData != NULL) if (pdev->pClassData != NULL)
{ {
((USBD_CUSTOM_HID_ItfTypeDef *)pdev->pUserData)->DeInit(); ((USBD_CUSTOM_HID_ItfTypeDef *)pdev->pUserData)->DeInit();
@@ -439,110 +448,116 @@ static uint8_t USBD_CUSTOM_HID_Setup(USBD_HandleTypeDef *pdev,
uint16_t status_info = 0U; uint16_t status_info = 0U;
USBD_StatusTypeDef ret = USBD_OK; USBD_StatusTypeDef ret = USBD_OK;
if (hhid == NULL)
{
return (uint8_t)USBD_FAIL;
}
switch (req->bmRequest & USB_REQ_TYPE_MASK) switch (req->bmRequest & USB_REQ_TYPE_MASK)
{ {
case USB_REQ_TYPE_CLASS: case USB_REQ_TYPE_CLASS:
switch (req->bRequest) switch (req->bRequest)
{ {
case CUSTOM_HID_REQ_SET_PROTOCOL: case CUSTOM_HID_REQ_SET_PROTOCOL:
hhid->Protocol = (uint8_t)(req->wValue); hhid->Protocol = (uint8_t)(req->wValue);
break;
case CUSTOM_HID_REQ_GET_PROTOCOL:
(void)USBD_CtlSendData(pdev, (uint8_t *)&hhid->Protocol, 1U);
break;
case CUSTOM_HID_REQ_SET_IDLE:
hhid->IdleState = (uint8_t)(req->wValue >> 8);
break;
case CUSTOM_HID_REQ_GET_IDLE:
(void)USBD_CtlSendData(pdev, (uint8_t *)&hhid->IdleState, 1U);
break;
case CUSTOM_HID_REQ_SET_REPORT:
hhid->IsReportAvailable = 1U;
(void)USBD_CtlPrepareRx(pdev, hhid->Report_buf,
MIN(req->wLength, USBD_CUSTOMHID_OUTREPORT_BUF_SIZE));
break;
default:
USBD_CtlError(pdev, req);
ret = USBD_FAIL;
break;
}
break; break;
case CUSTOM_HID_REQ_GET_PROTOCOL: case USB_REQ_TYPE_STANDARD:
(void)USBD_CtlSendData(pdev, (uint8_t *)&hhid->Protocol, 1U); switch (req->bRequest)
break; {
case USB_REQ_GET_STATUS:
if (pdev->dev_state == USBD_STATE_CONFIGURED)
{
(void)USBD_CtlSendData(pdev, (uint8_t *)&status_info, 2U);
}
else
{
USBD_CtlError(pdev, req);
ret = USBD_FAIL;
}
break;
case CUSTOM_HID_REQ_SET_IDLE: case USB_REQ_GET_DESCRIPTOR:
hhid->IdleState = (uint8_t)(req->wValue >> 8); if ((req->wValue >> 8) == CUSTOM_HID_REPORT_DESC)
break; {
len = MIN(USBD_CUSTOM_HID_REPORT_DESC_SIZE, req->wLength);
pbuf = ((USBD_CUSTOM_HID_ItfTypeDef *)pdev->pUserData)->pReport;
}
else
{
if ((req->wValue >> 8) == CUSTOM_HID_DESCRIPTOR_TYPE)
{
pbuf = USBD_CUSTOM_HID_Desc;
len = MIN(USB_CUSTOM_HID_DESC_SIZ, req->wLength);
}
}
case CUSTOM_HID_REQ_GET_IDLE: (void)USBD_CtlSendData(pdev, pbuf, len);
(void)USBD_CtlSendData(pdev, (uint8_t *)&hhid->IdleState, 1U); break;
break;
case CUSTOM_HID_REQ_SET_REPORT: case USB_REQ_GET_INTERFACE:
hhid->IsReportAvailable = 1U; if (pdev->dev_state == USBD_STATE_CONFIGURED)
(void)USBD_CtlPrepareRx(pdev, hhid->Report_buf, req->wLength); {
(void)USBD_CtlSendData(pdev, (uint8_t *)&hhid->AltSetting, 1U);
}
else
{
USBD_CtlError(pdev, req);
ret = USBD_FAIL;
}
break;
case USB_REQ_SET_INTERFACE:
if (pdev->dev_state == USBD_STATE_CONFIGURED)
{
hhid->AltSetting = (uint8_t)(req->wValue);
}
else
{
USBD_CtlError(pdev, req);
ret = USBD_FAIL;
}
break;
case USB_REQ_CLEAR_FEATURE:
break;
default:
USBD_CtlError(pdev, req);
ret = USBD_FAIL;
break;
}
break; break;
default: default:
USBD_CtlError(pdev, req); USBD_CtlError(pdev, req);
ret = USBD_FAIL; ret = USBD_FAIL;
break; break;
}
break;
case USB_REQ_TYPE_STANDARD:
switch (req->bRequest)
{
case USB_REQ_GET_STATUS:
if (pdev->dev_state == USBD_STATE_CONFIGURED)
{
(void)USBD_CtlSendData(pdev, (uint8_t *)&status_info, 2U);
}
else
{
USBD_CtlError(pdev, req);
ret = USBD_FAIL;
}
break;
case USB_REQ_GET_DESCRIPTOR:
if ((req->wValue >> 8) == CUSTOM_HID_REPORT_DESC)
{
len = MIN(USBD_CUSTOM_HID_REPORT_DESC_SIZE, req->wLength);
pbuf = ((USBD_CUSTOM_HID_ItfTypeDef *)pdev->pUserData)->pReport;
}
else
{
if ((req->wValue >> 8) == CUSTOM_HID_DESCRIPTOR_TYPE)
{
pbuf = USBD_CUSTOM_HID_Desc;
len = MIN(USB_CUSTOM_HID_DESC_SIZ, req->wLength);
}
}
(void)USBD_CtlSendData(pdev, pbuf, len);
break;
case USB_REQ_GET_INTERFACE:
if (pdev->dev_state == USBD_STATE_CONFIGURED)
{
(void)USBD_CtlSendData(pdev, (uint8_t *)&hhid->AltSetting, 1U);
}
else
{
USBD_CtlError(pdev, req);
ret = USBD_FAIL;
}
break;
case USB_REQ_SET_INTERFACE:
if (pdev->dev_state == USBD_STATE_CONFIGURED)
{
hhid->AltSetting = (uint8_t)(req->wValue);
}
else
{
USBD_CtlError(pdev, req);
ret = USBD_FAIL;
}
break;
case USB_REQ_CLEAR_FEATURE:
break;
default:
USBD_CtlError(pdev, req);
ret = USBD_FAIL;
break;
}
break;
default:
USBD_CtlError(pdev, req);
ret = USBD_FAIL;
break;
} }
return (uint8_t)ret; return (uint8_t)ret;
} }
@@ -564,7 +579,7 @@ uint8_t USBD_CUSTOM_HID_SendReport(USBD_HandleTypeDef *pdev,
return (uint8_t)USBD_FAIL; return (uint8_t)USBD_FAIL;
} }
hhid = (USBD_CUSTOM_HID_HandleTypeDef*)pdev->pClassData; hhid = (USBD_CUSTOM_HID_HandleTypeDef *)pdev->pClassData;
if (pdev->dev_state == USBD_STATE_CONFIGURED) if (pdev->dev_state == USBD_STATE_CONFIGURED)
{ {
@@ -658,7 +673,7 @@ static uint8_t USBD_CUSTOM_HID_DataOut(USBD_HandleTypeDef *pdev, uint8_t epnum)
return (uint8_t)USBD_FAIL; return (uint8_t)USBD_FAIL;
} }
hhid = (USBD_CUSTOM_HID_HandleTypeDef*)pdev->pClassData; hhid = (USBD_CUSTOM_HID_HandleTypeDef *)pdev->pClassData;
/* USB data will be immediately processed, this allow next USB traffic being /* USB data will be immediately processed, this allow next USB traffic being
NAKed till the end of the application processing */ NAKed till the end of the application processing */
@@ -684,7 +699,7 @@ uint8_t USBD_CUSTOM_HID_ReceivePacket(USBD_HandleTypeDef *pdev)
return (uint8_t)USBD_FAIL; return (uint8_t)USBD_FAIL;
} }
hhid = (USBD_CUSTOM_HID_HandleTypeDef*)pdev->pClassData; hhid = (USBD_CUSTOM_HID_HandleTypeDef *)pdev->pClassData;
/* Resume USB Out process */ /* Resume USB Out process */
(void)USBD_LL_PrepareReceive(pdev, CUSTOM_HID_EPOUT_ADDR, hhid->Report_buf, (void)USBD_LL_PrepareReceive(pdev, CUSTOM_HID_EPOUT_ADDR, hhid->Report_buf,
@@ -704,6 +719,11 @@ static uint8_t USBD_CUSTOM_HID_EP0_RxReady(USBD_HandleTypeDef *pdev)
{ {
USBD_CUSTOM_HID_HandleTypeDef *hhid = (USBD_CUSTOM_HID_HandleTypeDef *)pdev->pClassData; USBD_CUSTOM_HID_HandleTypeDef *hhid = (USBD_CUSTOM_HID_HandleTypeDef *)pdev->pClassData;
if (hhid == NULL)
{
return (uint8_t)USBD_FAIL;
}
if (hhid->IsReportAvailable == 1U) if (hhid->IsReportAvailable == 1U)
{ {
((USBD_CUSTOM_HID_ItfTypeDef *)pdev->pUserData)->OutEvent(hhid->Report_buf[0], ((USBD_CUSTOM_HID_ItfTypeDef *)pdev->pUserData)->OutEvent(hhid->Report_buf[0],
@@ -715,11 +735,11 @@ static uint8_t USBD_CUSTOM_HID_EP0_RxReady(USBD_HandleTypeDef *pdev)
} }
/** /**
* @brief DeviceQualifierDescriptor * @brief DeviceQualifierDescriptor
* return Device Qualifier descriptor * return Device Qualifier descriptor
* @param length : pointer data length * @param length : pointer data length
* @retval pointer to descriptor buffer * @retval pointer to descriptor buffer
*/ */
static uint8_t *USBD_CUSTOM_HID_GetDeviceQualifierDesc(uint16_t *length) static uint8_t *USBD_CUSTOM_HID_GetDeviceQualifierDesc(uint16_t *length)
{ {
*length = (uint16_t)sizeof(USBD_CUSTOM_HID_DeviceQualifierDesc); *length = (uint16_t)sizeof(USBD_CUSTOM_HID_DeviceQualifierDesc);
@@ -728,7 +748,7 @@ static uint8_t *USBD_CUSTOM_HID_GetDeviceQualifierDesc(uint16_t *length)
} }
/** /**
* @brief USBD_CUSTOM_HID_RegisterInterface * @brief USBD_CUSTOM_HID_RegisterInterface
* @param pdev: device instance * @param pdev: device instance
* @param fops: CUSTOMHID Interface callback * @param fops: CUSTOMHID Interface callback
* @retval status * @retval status

View File

@@ -83,7 +83,7 @@ static int8_t TEMPLATE_CUSTOM_HID_OutEvent(uint8_t event_idx, uint8_t state)
UNUSED(event_idx); UNUSED(event_idx);
UNUSED(state); UNUSED(state);
/* Start next USB packet transfer once data processing is completed */ /* Start next USB packet transfer once data processing is completed */
USBD_CUSTOM_HID_ReceivePacket(&USBD_Device); USBD_CUSTOM_HID_ReceivePacket(&USBD_Device);
return (0); return (0);

View File

@@ -92,6 +92,6 @@ extern USBD_DFU_MediaTypeDef USBD_DFU_MEDIA_Template_fops;
*/ */
/** /**
* @} * @}
*/ */
/************************ (C) COPYRIGHT STMicroelectronics *****END OF FILE****/ /************************ (C) COPYRIGHT STMicroelectronics *****END OF FILE****/

View File

@@ -153,16 +153,19 @@ USBD_ClassTypeDef USBD_DFU =
/* USB DFU device Configuration Descriptor */ /* USB DFU device Configuration Descriptor */
__ALIGN_BEGIN static uint8_t USBD_DFU_CfgDesc[USB_DFU_CONFIG_DESC_SIZ] __ALIGN_END = __ALIGN_BEGIN static uint8_t USBD_DFU_CfgDesc[USB_DFU_CONFIG_DESC_SIZ] __ALIGN_END =
{ {
0x09, /* bLength: Configuation Descriptor size */ 0x09, /* bLength: Configuration Descriptor size */
USB_DESC_TYPE_CONFIGURATION, /* bDescriptorType: Configuration */ USB_DESC_TYPE_CONFIGURATION, /* bDescriptorType: Configuration */
USB_DFU_CONFIG_DESC_SIZ, USB_DFU_CONFIG_DESC_SIZ, /* wTotalLength: Bytes returned */
/* wTotalLength: Bytes returned */
0x00, 0x00,
0x01, /* bNumInterfaces: 1 interface */ 0x01, /* bNumInterfaces: 1 interface */
0x01, /* bConfigurationValue: Configuration value */ 0x01, /* bConfigurationValue: Configuration value */
0x02, /* iConfiguration: Index of string descriptor describing the configuration */ 0x02, /* iConfiguration: Index of string descriptor describing the configuration */
0xC0, /* bmAttributes: bus powered and Supprts Remote Wakeup */ #if (USBD_SELF_POWERED == 1U)
0x32, /* MaxPower 100 mA: this current is used for detecting Vbus */ 0xC0, /* bmAttributes: Bus Powered according to user configuration */
#else
0x80, /* bmAttributes: Bus Powered according to user configuration */
#endif
USBD_MAX_POWER, /* MaxPower (mA) */
/* 09 */ /* 09 */
/********** Descriptor of DFU interface 0 Alternate setting 0 **************/ /********** Descriptor of DFU interface 0 Alternate setting 0 **************/
@@ -255,7 +258,7 @@ static uint8_t USBD_DFU_Init(USBD_HandleTypeDef *pdev, uint8_t cfgidx)
USBD_DFU_HandleTypeDef *hdfu; USBD_DFU_HandleTypeDef *hdfu;
/* Allocate Audio structure */ /* Allocate Audio structure */
hdfu = USBD_malloc(sizeof(USBD_DFU_HandleTypeDef)); hdfu = (USBD_DFU_HandleTypeDef *)USBD_malloc(sizeof(USBD_DFU_HandleTypeDef));
if (hdfu == NULL) if (hdfu == NULL)
{ {
@@ -337,118 +340,123 @@ static uint8_t USBD_DFU_Setup(USBD_HandleTypeDef *pdev, USBD_SetupReqTypedef *re
uint16_t len = 0U; uint16_t len = 0U;
uint16_t status_info = 0U; uint16_t status_info = 0U;
if (hdfu == NULL)
{
return (uint8_t)USBD_FAIL;
}
switch (req->bmRequest & USB_REQ_TYPE_MASK) switch (req->bmRequest & USB_REQ_TYPE_MASK)
{ {
case USB_REQ_TYPE_CLASS: case USB_REQ_TYPE_CLASS:
switch (req->bRequest) switch (req->bRequest)
{
case DFU_DNLOAD:
DFU_Download(pdev, req);
break;
case DFU_UPLOAD:
DFU_Upload(pdev, req);
break;
case DFU_GETSTATUS:
DFU_GetStatus(pdev);
break;
case DFU_CLRSTATUS:
DFU_ClearStatus(pdev);
break;
case DFU_GETSTATE:
DFU_GetState(pdev);
break;
case DFU_ABORT:
DFU_Abort(pdev);
break;
case DFU_DETACH:
DFU_Detach(pdev, req);
break;
default:
USBD_CtlError(pdev, req);
ret = USBD_FAIL;
break;
}
break;
case USB_REQ_TYPE_STANDARD:
switch (req->bRequest)
{
case USB_REQ_GET_STATUS:
if (pdev->dev_state == USBD_STATE_CONFIGURED)
{ {
(void)USBD_CtlSendData(pdev, (uint8_t *)&status_info, 2U); case DFU_DNLOAD:
} DFU_Download(pdev, req);
else break;
{
USBD_CtlError(pdev, req);
ret = USBD_FAIL;
}
break;
case USB_REQ_GET_DESCRIPTOR: case DFU_UPLOAD:
if ((req->wValue >> 8) == DFU_DESCRIPTOR_TYPE) DFU_Upload(pdev, req);
{ break;
pbuf = USBD_DFU_CfgDesc + (9U * (USBD_DFU_MAX_ITF_NUM + 1U));
len = MIN(USB_DFU_DESC_SIZ, req->wLength);
}
(void)USBD_CtlSendData(pdev, pbuf, len); case DFU_GETSTATUS:
break; DFU_GetStatus(pdev);
break;
case USB_REQ_GET_INTERFACE: case DFU_CLRSTATUS:
if (pdev->dev_state == USBD_STATE_CONFIGURED) DFU_ClearStatus(pdev);
{ break;
(void)USBD_CtlSendData(pdev, (uint8_t *)hdfu->alt_setting, 1U);
}
else
{
USBD_CtlError(pdev, req);
ret = USBD_FAIL;
}
break;
case USB_REQ_SET_INTERFACE: case DFU_GETSTATE:
if ((uint8_t)(req->wValue) < USBD_DFU_MAX_ITF_NUM) DFU_GetState(pdev);
{ break;
if (pdev->dev_state == USBD_STATE_CONFIGURED)
{ case DFU_ABORT:
hdfu->alt_setting = (uint8_t)(req->wValue); DFU_Abort(pdev);
} break;
else
{ case DFU_DETACH:
DFU_Detach(pdev, req);
break;
default:
USBD_CtlError(pdev, req); USBD_CtlError(pdev, req);
ret = USBD_FAIL; ret = USBD_FAIL;
} break;
}
else
{
/* Call the error management function (command will be nacked */
USBD_CtlError(pdev, req);
ret = USBD_FAIL;
} }
break; break;
case USB_REQ_CLEAR_FEATURE: case USB_REQ_TYPE_STANDARD:
switch (req->bRequest)
{
case USB_REQ_GET_STATUS:
if (pdev->dev_state == USBD_STATE_CONFIGURED)
{
(void)USBD_CtlSendData(pdev, (uint8_t *)&status_info, 2U);
}
else
{
USBD_CtlError(pdev, req);
ret = USBD_FAIL;
}
break;
case USB_REQ_GET_DESCRIPTOR:
if ((req->wValue >> 8) == DFU_DESCRIPTOR_TYPE)
{
pbuf = USBD_DFU_CfgDesc + (9U * (USBD_DFU_MAX_ITF_NUM + 1U));
len = MIN(USB_DFU_DESC_SIZ, req->wLength);
}
(void)USBD_CtlSendData(pdev, pbuf, len);
break;
case USB_REQ_GET_INTERFACE:
if (pdev->dev_state == USBD_STATE_CONFIGURED)
{
(void)USBD_CtlSendData(pdev, (uint8_t *)&hdfu->alt_setting, 1U);
}
else
{
USBD_CtlError(pdev, req);
ret = USBD_FAIL;
}
break;
case USB_REQ_SET_INTERFACE:
if ((uint8_t)(req->wValue) < USBD_DFU_MAX_ITF_NUM)
{
if (pdev->dev_state == USBD_STATE_CONFIGURED)
{
hdfu->alt_setting = (uint8_t)(req->wValue);
}
else
{
USBD_CtlError(pdev, req);
ret = USBD_FAIL;
}
}
else
{
/* Call the error management function (command will be NAKed */
USBD_CtlError(pdev, req);
ret = USBD_FAIL;
}
break;
case USB_REQ_CLEAR_FEATURE:
break;
default:
USBD_CtlError(pdev, req);
ret = USBD_FAIL;
break;
}
break; break;
default: default:
USBD_CtlError(pdev, req); USBD_CtlError(pdev, req);
ret = USBD_FAIL; ret = USBD_FAIL;
break; break;
}
break;
default:
USBD_CtlError(pdev, req);
ret = USBD_FAIL;
break;
} }
return (uint8_t)ret; return (uint8_t)ret;
@@ -495,16 +503,21 @@ static uint8_t USBD_DFU_EP0_TxReady(USBD_HandleTypeDef *pdev)
USBD_DFU_HandleTypeDef *hdfu = (USBD_DFU_HandleTypeDef *)pdev->pClassData; USBD_DFU_HandleTypeDef *hdfu = (USBD_DFU_HandleTypeDef *)pdev->pClassData;
USBD_DFU_MediaTypeDef *DfuInterface = (USBD_DFU_MediaTypeDef *)pdev->pUserData; USBD_DFU_MediaTypeDef *DfuInterface = (USBD_DFU_MediaTypeDef *)pdev->pUserData;
if (hdfu == NULL)
{
return (uint8_t)USBD_FAIL;
}
if (hdfu->dev_state == DFU_STATE_DNLOAD_BUSY) if (hdfu->dev_state == DFU_STATE_DNLOAD_BUSY)
{ {
/* Decode the Special Command*/ /* Decode the Special Command */
if (hdfu->wblock_num == 0U) if (hdfu->wblock_num == 0U)
{ {
if(hdfu->wlength == 1U) if (hdfu->wlength == 1U)
{ {
if (hdfu->buffer.d8[0] == DFU_CMD_GETCOMMANDS) if (hdfu->buffer.d8[0] == DFU_CMD_GETCOMMANDS)
{ {
/* nothink to do */ /* Nothing to do */
} }
} }
else if (hdfu->wlength == 5U) else if (hdfu->wlength == 5U)
@@ -530,7 +543,7 @@ static uint8_t USBD_DFU_EP0_TxReady(USBD_HandleTypeDef *pdev)
} }
else else
{ {
/* .. */ return (uint8_t)USBD_FAIL;
} }
} }
else else
@@ -538,7 +551,7 @@ static uint8_t USBD_DFU_EP0_TxReady(USBD_HandleTypeDef *pdev)
/* Reset the global length and block number */ /* Reset the global length and block number */
hdfu->wlength = 0U; hdfu->wlength = 0U;
hdfu->wblock_num = 0U; hdfu->wblock_num = 0U;
/* Call the error management function (command will be nacked) */ /* Call the error management function (command will be NAKed) */
req.bmRequest = 0U; req.bmRequest = 0U;
req.wLength = 1U; req.wLength = 1U;
USBD_CtlError(pdev, &req); USBD_CtlError(pdev, &req);
@@ -552,7 +565,7 @@ static uint8_t USBD_DFU_EP0_TxReady(USBD_HandleTypeDef *pdev)
/* Decode the required address */ /* Decode the required address */
addr = ((hdfu->wblock_num - 2U) * USBD_DFU_XFER_SIZE) + hdfu->data_ptr; addr = ((hdfu->wblock_num - 2U) * USBD_DFU_XFER_SIZE) + hdfu->data_ptr;
/* Preform the write operation */ /* Perform the write operation */
if (DfuInterface->Write(hdfu->buffer.d8, (uint8_t *)addr, hdfu->wlength) != USBD_OK) if (DfuInterface->Write(hdfu->buffer.d8, (uint8_t *)addr, hdfu->wlength) != USBD_OK)
{ {
return (uint8_t)USBD_FAIL; return (uint8_t)USBD_FAIL;
@@ -579,7 +592,7 @@ static uint8_t USBD_DFU_EP0_TxReady(USBD_HandleTypeDef *pdev)
} }
else else
{ {
/* .. */ return (uint8_t)USBD_FAIL;
} }
return (uint8_t)USBD_OK; return (uint8_t)USBD_OK;
@@ -599,11 +612,11 @@ static uint8_t USBD_DFU_SOF(USBD_HandleTypeDef *pdev)
/** /**
* @brief DeviceQualifierDescriptor * @brief DeviceQualifierDescriptor
* return Device Qualifier descriptor * return Device Qualifier descriptor
* @param length : pointer data length * @param length : pointer data length
* @retval pointer to descriptor buffer * @retval pointer to descriptor buffer
*/ */
static uint8_t *USBD_DFU_GetDeviceQualifierDesc(uint16_t *length) static uint8_t *USBD_DFU_GetDeviceQualifierDesc(uint16_t *length)
{ {
*length = (uint16_t)sizeof(USBD_DFU_DeviceQualifierDesc); *length = (uint16_t)sizeof(USBD_DFU_DeviceQualifierDesc);
@@ -615,7 +628,7 @@ static uint8_t *USBD_DFU_GetDeviceQualifierDesc(uint16_t *length)
* @brief USBD_DFU_GetUsrStringDesc * @brief USBD_DFU_GetUsrStringDesc
* Manages the transfer of memory interfaces string descriptors. * Manages the transfer of memory interfaces string descriptors.
* @param speed : current device speed * @param speed : current device speed
* @param index: desciptor index * @param index: descriptor index
* @param length : pointer data length * @param length : pointer data length
* @retval pointer to the descriptor table or NULL if the descriptor is not supported. * @retval pointer to the descriptor table or NULL if the descriptor is not supported.
*/ */
@@ -640,10 +653,10 @@ static uint8_t *USBD_DFU_GetUsrStringDesc(USBD_HandleTypeDef *pdev, uint8_t inde
#endif #endif
/** /**
* @brief USBD_MSC_RegisterStorage * @brief USBD_MSC_RegisterStorage
* @param fops: storage callback * @param fops: storage callback
* @retval status * @retval status
*/ */
uint8_t USBD_DFU_RegisterMedia(USBD_HandleTypeDef *pdev, uint8_t USBD_DFU_RegisterMedia(USBD_HandleTypeDef *pdev,
USBD_DFU_MediaTypeDef *fops) USBD_DFU_MediaTypeDef *fops)
{ {
@@ -659,7 +672,7 @@ uint8_t USBD_DFU_RegisterMedia(USBD_HandleTypeDef *pdev,
/****************************************************************************** /******************************************************************************
DFU Class requests management DFU Class requests management
******************************************************************************/ ******************************************************************************/
/** /**
* @brief DFU_Detach * @brief DFU_Detach
* Handles the DFU DETACH request. * Handles the DFU DETACH request.
@@ -671,6 +684,11 @@ static void DFU_Detach(USBD_HandleTypeDef *pdev, USBD_SetupReqTypedef *req)
{ {
USBD_DFU_HandleTypeDef *hdfu = (USBD_DFU_HandleTypeDef *)pdev->pClassData; USBD_DFU_HandleTypeDef *hdfu = (USBD_DFU_HandleTypeDef *)pdev->pClassData;
if (hdfu == NULL)
{
return;
}
if ((hdfu->dev_state == DFU_STATE_IDLE) || if ((hdfu->dev_state == DFU_STATE_IDLE) ||
(hdfu->dev_state == DFU_STATE_DNLOAD_SYNC) || (hdfu->dev_state == DFU_STATE_DNLOAD_SYNC) ||
(hdfu->dev_state == DFU_STATE_DNLOAD_IDLE) || (hdfu->dev_state == DFU_STATE_DNLOAD_IDLE) ||
@@ -714,6 +732,11 @@ static void DFU_Download(USBD_HandleTypeDef *pdev, USBD_SetupReqTypedef *req)
{ {
USBD_DFU_HandleTypeDef *hdfu = (USBD_DFU_HandleTypeDef *)pdev->pClassData; USBD_DFU_HandleTypeDef *hdfu = (USBD_DFU_HandleTypeDef *)pdev->pClassData;
if (hdfu == NULL)
{
return;
}
/* Data setup request */ /* Data setup request */
if (req->wLength > 0U) if (req->wLength > 0U)
{ {
@@ -721,7 +744,7 @@ static void DFU_Download(USBD_HandleTypeDef *pdev, USBD_SetupReqTypedef *req)
{ {
/* Update the global length and block number */ /* Update the global length and block number */
hdfu->wblock_num = req->wValue; hdfu->wblock_num = req->wValue;
hdfu->wlength = req->wLength; hdfu->wlength = MIN(req->wLength, USBD_DFU_XFER_SIZE);
/* Update the state machine */ /* Update the state machine */
hdfu->dev_state = DFU_STATE_DNLOAD_SYNC; hdfu->dev_state = DFU_STATE_DNLOAD_SYNC;
@@ -733,7 +756,7 @@ static void DFU_Download(USBD_HandleTypeDef *pdev, USBD_SetupReqTypedef *req)
/* Unsupported state */ /* Unsupported state */
else else
{ {
/* Call the error management function (command will be nacked */ /* Call the error management function (command will be NAKed */
USBD_CtlError(pdev, req); USBD_CtlError(pdev, req);
} }
} }
@@ -752,7 +775,7 @@ static void DFU_Download(USBD_HandleTypeDef *pdev, USBD_SetupReqTypedef *req)
} }
else else
{ {
/* Call the error management function (command will be nacked */ /* Call the error management function (command will be NAKed */
USBD_CtlError(pdev, req); USBD_CtlError(pdev, req);
} }
} }
@@ -772,6 +795,11 @@ static void DFU_Upload(USBD_HandleTypeDef *pdev, USBD_SetupReqTypedef *req)
uint8_t *phaddr; uint8_t *phaddr;
uint32_t addr; uint32_t addr;
if (hdfu == NULL)
{
return;
}
/* Data setup request */ /* Data setup request */
if (req->wLength > 0U) if (req->wLength > 0U)
{ {
@@ -779,7 +807,7 @@ static void DFU_Upload(USBD_HandleTypeDef *pdev, USBD_SetupReqTypedef *req)
{ {
/* Update the global length and block number */ /* Update the global length and block number */
hdfu->wblock_num = req->wValue; hdfu->wblock_num = req->wValue;
hdfu->wlength = req->wLength; hdfu->wlength = MIN(req->wLength, USBD_DFU_XFER_SIZE);
/* DFU Get Command */ /* DFU Get Command */
if (hdfu->wblock_num == 0U) if (hdfu->wblock_num == 0U)
@@ -826,7 +854,7 @@ static void DFU_Upload(USBD_HandleTypeDef *pdev, USBD_SetupReqTypedef *req)
hdfu->dev_status[3] = 0U; hdfu->dev_status[3] = 0U;
hdfu->dev_status[4] = hdfu->dev_state; hdfu->dev_status[4] = hdfu->dev_state;
/* Call the error management function (command will be nacked */ /* Call the error management function (command will be NAKed */
USBD_CtlError(pdev, req); USBD_CtlError(pdev, req);
} }
} }
@@ -836,7 +864,7 @@ static void DFU_Upload(USBD_HandleTypeDef *pdev, USBD_SetupReqTypedef *req)
hdfu->wlength = 0U; hdfu->wlength = 0U;
hdfu->wblock_num = 0U; hdfu->wblock_num = 0U;
/* Call the error management function (command will be nacked */ /* Call the error management function (command will be NAKed */
USBD_CtlError(pdev, req); USBD_CtlError(pdev, req);
} }
} }
@@ -863,65 +891,70 @@ static void DFU_GetStatus(USBD_HandleTypeDef *pdev)
USBD_DFU_HandleTypeDef *hdfu = (USBD_DFU_HandleTypeDef *)pdev->pClassData; USBD_DFU_HandleTypeDef *hdfu = (USBD_DFU_HandleTypeDef *)pdev->pClassData;
USBD_DFU_MediaTypeDef *DfuInterface = (USBD_DFU_MediaTypeDef *)pdev->pUserData; USBD_DFU_MediaTypeDef *DfuInterface = (USBD_DFU_MediaTypeDef *)pdev->pUserData;
if (hdfu == NULL)
{
return;
}
switch (hdfu->dev_state) switch (hdfu->dev_state)
{ {
case DFU_STATE_DNLOAD_SYNC: case DFU_STATE_DNLOAD_SYNC:
if (hdfu->wlength != 0U) if (hdfu->wlength != 0U)
{
hdfu->dev_state = DFU_STATE_DNLOAD_BUSY;
hdfu->dev_status[1] = 0U;
hdfu->dev_status[2] = 0U;
hdfu->dev_status[3] = 0U;
hdfu->dev_status[4] = hdfu->dev_state;
if ((hdfu->wblock_num == 0U) && (hdfu->buffer.d8[0] == DFU_CMD_ERASE))
{ {
DfuInterface->GetStatus(hdfu->data_ptr, DFU_MEDIA_ERASE, hdfu->dev_status); hdfu->dev_state = DFU_STATE_DNLOAD_BUSY;
hdfu->dev_status[1] = 0U;
hdfu->dev_status[2] = 0U;
hdfu->dev_status[3] = 0U;
hdfu->dev_status[4] = hdfu->dev_state;
if ((hdfu->wblock_num == 0U) && (hdfu->buffer.d8[0] == DFU_CMD_ERASE))
{
DfuInterface->GetStatus(hdfu->data_ptr, DFU_MEDIA_ERASE, hdfu->dev_status);
}
else
{
DfuInterface->GetStatus(hdfu->data_ptr, DFU_MEDIA_PROGRAM, hdfu->dev_status);
}
} }
else else /* (hdfu->wlength==0)*/
{ {
DfuInterface->GetStatus(hdfu->data_ptr, DFU_MEDIA_PROGRAM, hdfu->dev_status); hdfu->dev_state = DFU_STATE_DNLOAD_IDLE;
}
}
else /* (hdfu->wlength==0)*/
{
hdfu->dev_state = DFU_STATE_DNLOAD_IDLE;
hdfu->dev_status[1] = 0U;
hdfu->dev_status[2] = 0U;
hdfu->dev_status[3] = 0U;
hdfu->dev_status[4] = hdfu->dev_state;
}
break;
case DFU_STATE_MANIFEST_SYNC:
if (hdfu->manif_state == DFU_MANIFEST_IN_PROGRESS)
{
hdfu->dev_state = DFU_STATE_MANIFEST;
hdfu->dev_status[1] = 1U; /*bwPollTimeout = 1ms*/
hdfu->dev_status[2] = 0U;
hdfu->dev_status[3] = 0U;
hdfu->dev_status[4] = hdfu->dev_state;
}
else
{
if ((hdfu->manif_state == DFU_MANIFEST_COMPLETE) &&
(((USBD_DFU_CfgDesc[(11U + (9U * USBD_DFU_MAX_ITF_NUM))]) & 0x04U) != 0U))
{
hdfu->dev_state = DFU_STATE_IDLE;
hdfu->dev_status[1] = 0U; hdfu->dev_status[1] = 0U;
hdfu->dev_status[2] = 0U; hdfu->dev_status[2] = 0U;
hdfu->dev_status[3] = 0U; hdfu->dev_status[3] = 0U;
hdfu->dev_status[4] = hdfu->dev_state; hdfu->dev_status[4] = hdfu->dev_state;
} }
} break;
break;
default: case DFU_STATE_MANIFEST_SYNC:
break; if (hdfu->manif_state == DFU_MANIFEST_IN_PROGRESS)
{
hdfu->dev_state = DFU_STATE_MANIFEST;
hdfu->dev_status[1] = 1U; /*bwPollTimeout = 1ms*/
hdfu->dev_status[2] = 0U;
hdfu->dev_status[3] = 0U;
hdfu->dev_status[4] = hdfu->dev_state;
}
else
{
if ((hdfu->manif_state == DFU_MANIFEST_COMPLETE) &&
(((USBD_DFU_CfgDesc[(11U + (9U * USBD_DFU_MAX_ITF_NUM))]) & 0x04U) != 0U))
{
hdfu->dev_state = DFU_STATE_IDLE;
hdfu->dev_status[1] = 0U;
hdfu->dev_status[2] = 0U;
hdfu->dev_status[3] = 0U;
hdfu->dev_status[4] = hdfu->dev_state;
}
}
break;
default:
break;
} }
/* Send the status data over EP0 */ /* Send the status data over EP0 */
@@ -938,26 +971,31 @@ static void DFU_ClearStatus(USBD_HandleTypeDef *pdev)
{ {
USBD_DFU_HandleTypeDef *hdfu = (USBD_DFU_HandleTypeDef *)pdev->pClassData; USBD_DFU_HandleTypeDef *hdfu = (USBD_DFU_HandleTypeDef *)pdev->pClassData;
if (hdfu == NULL)
{
return;
}
if (hdfu->dev_state == DFU_STATE_ERROR) if (hdfu->dev_state == DFU_STATE_ERROR)
{ {
hdfu->dev_state = DFU_STATE_IDLE; hdfu->dev_state = DFU_STATE_IDLE;
hdfu->dev_status[0] = DFU_ERROR_NONE; /*bStatus*/ hdfu->dev_status[0] = DFU_ERROR_NONE; /* bStatus */
hdfu->dev_status[1] = 0U; hdfu->dev_status[1] = 0U;
hdfu->dev_status[2] = 0U; hdfu->dev_status[2] = 0U;
hdfu->dev_status[3] = 0U; /*bwPollTimeout=0ms*/ hdfu->dev_status[3] = 0U; /* bwPollTimeout=0ms */
hdfu->dev_status[4] = hdfu->dev_state; /*bState*/ hdfu->dev_status[4] = hdfu->dev_state; /* bState */
hdfu->dev_status[5] = 0U; /*iString*/ hdfu->dev_status[5] = 0U; /* iString */
} }
else else
{ {
/*State Error*/ /* State Error */
hdfu->dev_state = DFU_STATE_ERROR; hdfu->dev_state = DFU_STATE_ERROR;
hdfu->dev_status[0] = DFU_ERROR_UNKNOWN; /*bStatus*/ hdfu->dev_status[0] = DFU_ERROR_UNKNOWN; /* bStatus */
hdfu->dev_status[1] = 0U; hdfu->dev_status[1] = 0U;
hdfu->dev_status[2] = 0U; hdfu->dev_status[2] = 0U;
hdfu->dev_status[3] = 0U; /*bwPollTimeout=0ms*/ hdfu->dev_status[3] = 0U; /* bwPollTimeout=0ms */
hdfu->dev_status[4] = hdfu->dev_state; /*bState*/ hdfu->dev_status[4] = hdfu->dev_state; /* bState */
hdfu->dev_status[5] = 0U; /*iString*/ hdfu->dev_status[5] = 0U; /* iString */
} }
} }
@@ -971,6 +1009,11 @@ static void DFU_GetState(USBD_HandleTypeDef *pdev)
{ {
USBD_DFU_HandleTypeDef *hdfu = (USBD_DFU_HandleTypeDef *)pdev->pClassData; USBD_DFU_HandleTypeDef *hdfu = (USBD_DFU_HandleTypeDef *)pdev->pClassData;
if (hdfu == NULL)
{
return;
}
/* Return the current state of the DFU interface */ /* Return the current state of the DFU interface */
(void)USBD_CtlSendData(pdev, &hdfu->dev_state, 1U); (void)USBD_CtlSendData(pdev, &hdfu->dev_state, 1U);
} }
@@ -985,6 +1028,10 @@ static void DFU_Abort(USBD_HandleTypeDef *pdev)
{ {
USBD_DFU_HandleTypeDef *hdfu = (USBD_DFU_HandleTypeDef *)pdev->pClassData; USBD_DFU_HandleTypeDef *hdfu = (USBD_DFU_HandleTypeDef *)pdev->pClassData;
if (hdfu == NULL)
{
return;
}
if ((hdfu->dev_state == DFU_STATE_IDLE) || if ((hdfu->dev_state == DFU_STATE_IDLE) ||
(hdfu->dev_state == DFU_STATE_DNLOAD_SYNC) || (hdfu->dev_state == DFU_STATE_DNLOAD_SYNC) ||
@@ -996,9 +1043,9 @@ static void DFU_Abort(USBD_HandleTypeDef *pdev)
hdfu->dev_status[0] = DFU_ERROR_NONE; hdfu->dev_status[0] = DFU_ERROR_NONE;
hdfu->dev_status[1] = 0U; hdfu->dev_status[1] = 0U;
hdfu->dev_status[2] = 0U; hdfu->dev_status[2] = 0U;
hdfu->dev_status[3] = 0U; /*bwPollTimeout=0ms*/ hdfu->dev_status[3] = 0U; /* bwPollTimeout=0ms */
hdfu->dev_status[4] = hdfu->dev_state; hdfu->dev_status[4] = hdfu->dev_state;
hdfu->dev_status[5] = 0U; /*iString*/ hdfu->dev_status[5] = 0U; /* iString */
hdfu->wblock_num = 0U; hdfu->wblock_num = 0U;
hdfu->wlength = 0U; hdfu->wlength = 0U;
} }
@@ -1015,6 +1062,11 @@ static void DFU_Leave(USBD_HandleTypeDef *pdev)
{ {
USBD_DFU_HandleTypeDef *hdfu = (USBD_DFU_HandleTypeDef *)pdev->pClassData; USBD_DFU_HandleTypeDef *hdfu = (USBD_DFU_HandleTypeDef *)pdev->pClassData;
if (hdfu == NULL)
{
return;
}
hdfu->manif_state = DFU_MANIFEST_COMPLETE; hdfu->manif_state = DFU_MANIFEST_COMPLETE;
if (((USBD_DFU_CfgDesc[(11U + (9U * USBD_DFU_MAX_ITF_NUM))]) & 0x04U) != 0U) if (((USBD_DFU_CfgDesc[(11U + (9U * USBD_DFU_MAX_ITF_NUM))]) & 0x04U) != 0U)

View File

@@ -116,7 +116,7 @@ extern USBD_ClassTypeDef USBD_HID;
/** @defgroup USB_CORE_Exported_Functions /** @defgroup USB_CORE_Exported_Functions
* @{ * @{
*/ */
uint8_t USBD_HID_SendReport(USBD_HandleTypeDef *pdev, uint8_t *report,uint16_t len); uint8_t USBD_HID_SendReport(USBD_HandleTypeDef *pdev, uint8_t *report, uint16_t len);
uint32_t USBD_HID_GetPollingInterval(USBD_HandleTypeDef *pdev); uint32_t USBD_HID_GetPollingInterval(USBD_HandleTypeDef *pdev);
/** /**

View File

@@ -105,7 +105,8 @@ static uint8_t *USBD_HID_GetDeviceQualifierDesc(uint16_t *length);
* @{ * @{
*/ */
USBD_ClassTypeDef USBD_HID = { USBD_ClassTypeDef USBD_HID =
{
USBD_HID_Init, USBD_HID_Init,
USBD_HID_DeInit, USBD_HID_DeInit,
USBD_HID_Setup, USBD_HID_Setup,
@@ -123,17 +124,21 @@ USBD_ClassTypeDef USBD_HID = {
}; };
/* USB HID device FS Configuration Descriptor */ /* USB HID device FS Configuration Descriptor */
__ALIGN_BEGIN static uint8_t USBD_HID_CfgFSDesc[USB_HID_CONFIG_DESC_SIZ] __ALIGN_END = { __ALIGN_BEGIN static uint8_t USBD_HID_CfgFSDesc[USB_HID_CONFIG_DESC_SIZ] __ALIGN_END =
{
0x09, /* bLength: Configuration Descriptor size */ 0x09, /* bLength: Configuration Descriptor size */
USB_DESC_TYPE_CONFIGURATION, /* bDescriptorType: Configuration */ USB_DESC_TYPE_CONFIGURATION, /* bDescriptorType: Configuration */
USB_HID_CONFIG_DESC_SIZ, USB_HID_CONFIG_DESC_SIZ, /* wTotalLength: Bytes returned */
/* wTotalLength: Bytes returned */
0x00, 0x00,
0x01, /* bNumInterfaces: 1 interface */ 0x01, /* bNumInterfaces: 1 interface */
0x01, /* bConfigurationValue: Configuration value */ 0x01, /* bConfigurationValue: Configuration value */
0x00, /* iConfiguration: Index of string descriptor describing the configuration */ 0x00, /* iConfiguration: Index of string descriptor describing the configuration */
0xE0, /* bmAttributes: bus powered and Support Remote Wake-up */ #if (USBD_SELF_POWERED == 1U)
0x32, /* MaxPower 100 mA: this current is used for detecting Vbus */ 0xE0, /* bmAttributes: Bus Powered according to user configuration */
#else
0xA0, /* bmAttributes: Bus Powered according to user configuration */
#endif
USBD_MAX_POWER, /* MaxPower (mA) */
/************** Descriptor of Joystick Mouse interface ****************/ /************** Descriptor of Joystick Mouse interface ****************/
/* 09 */ /* 09 */
@@ -164,24 +169,28 @@ __ALIGN_BEGIN static uint8_t USBD_HID_CfgFSDesc[USB_HID_CONFIG_DESC_SIZ] __ALIGN
HID_EPIN_ADDR, /* bEndpointAddress: Endpoint Address (IN) */ HID_EPIN_ADDR, /* bEndpointAddress: Endpoint Address (IN) */
0x03, /* bmAttributes: Interrupt endpoint */ 0x03, /* bmAttributes: Interrupt endpoint */
HID_EPIN_SIZE, /* wMaxPacketSize: 4 Byte max */ HID_EPIN_SIZE, /* wMaxPacketSize: 4 Bytes max */
0x00, 0x00,
HID_FS_BINTERVAL, /* bInterval: Polling Interval */ HID_FS_BINTERVAL, /* bInterval: Polling Interval */
/* 34 */ /* 34 */
}; };
/* USB HID device HS Configuration Descriptor */ /* USB HID device HS Configuration Descriptor */
__ALIGN_BEGIN static uint8_t USBD_HID_CfgHSDesc[USB_HID_CONFIG_DESC_SIZ] __ALIGN_END = { __ALIGN_BEGIN static uint8_t USBD_HID_CfgHSDesc[USB_HID_CONFIG_DESC_SIZ] __ALIGN_END =
{
0x09, /* bLength: Configuration Descriptor size */ 0x09, /* bLength: Configuration Descriptor size */
USB_DESC_TYPE_CONFIGURATION, /* bDescriptorType: Configuration */ USB_DESC_TYPE_CONFIGURATION, /* bDescriptorType: Configuration */
USB_HID_CONFIG_DESC_SIZ, USB_HID_CONFIG_DESC_SIZ, /* wTotalLength: Bytes returned */
/* wTotalLength: Bytes returned */
0x00, 0x00,
0x01, /* bNumInterfaces: 1 interface */ 0x01, /* bNumInterfaces: 1 interface */
0x01, /* bConfigurationValue: Configuration value */ 0x01, /* bConfigurationValue: Configuration value */
0x00, /* iConfiguration: Index of string descriptor describing the configuration */ 0x00, /* iConfiguration: Index of string descriptor describing the configuration */
0xE0, /* bmAttributes: bus powered and Support Remote Wake-up */ #if (USBD_SELF_POWERED == 1U)
0x32, /* MaxPower 100 mA: this current is used for detecting Vbus */ 0xE0, /* bmAttributes: Bus Powered according to user configuration */
#else
0xA0, /* bmAttributes: Bus Powered according to user configuration */
#endif
USBD_MAX_POWER, /* MaxPower (mA) */
/************** Descriptor of Joystick Mouse interface ****************/ /************** Descriptor of Joystick Mouse interface ****************/
/* 09 */ /* 09 */
@@ -212,24 +221,28 @@ __ALIGN_BEGIN static uint8_t USBD_HID_CfgHSDesc[USB_HID_CONFIG_DESC_SIZ] __ALIGN
HID_EPIN_ADDR, /* bEndpointAddress: Endpoint Address (IN) */ HID_EPIN_ADDR, /* bEndpointAddress: Endpoint Address (IN) */
0x03, /* bmAttributes: Interrupt endpoint */ 0x03, /* bmAttributes: Interrupt endpoint */
HID_EPIN_SIZE, /* wMaxPacketSize: 4 Byte max */ HID_EPIN_SIZE, /* wMaxPacketSize: 4 Bytes max */
0x00, 0x00,
HID_HS_BINTERVAL, /* bInterval: Polling Interval */ HID_HS_BINTERVAL, /* bInterval: Polling Interval */
/* 34 */ /* 34 */
}; };
/* USB HID device Other Speed Configuration Descriptor */ /* USB HID device Other Speed Configuration Descriptor */
__ALIGN_BEGIN static uint8_t USBD_HID_OtherSpeedCfgDesc[USB_HID_CONFIG_DESC_SIZ] __ALIGN_END = { __ALIGN_BEGIN static uint8_t USBD_HID_OtherSpeedCfgDesc[USB_HID_CONFIG_DESC_SIZ] __ALIGN_END =
{
0x09, /* bLength: Configuration Descriptor size */ 0x09, /* bLength: Configuration Descriptor size */
USB_DESC_TYPE_CONFIGURATION, /* bDescriptorType: Configuration */ USB_DESC_TYPE_CONFIGURATION, /* bDescriptorType: Configuration */
USB_HID_CONFIG_DESC_SIZ, USB_HID_CONFIG_DESC_SIZ, /* wTotalLength: Bytes returned */
/* wTotalLength: Bytes returned */
0x00, 0x00,
0x01, /* bNumInterfaces: 1 interface */ 0x01, /* bNumInterfaces: 1 interface */
0x01, /* bConfigurationValue: Configuration value */ 0x01, /* bConfigurationValue: Configuration value */
0x00, /* iConfiguration: Index of string descriptor describing the configuration */ 0x00, /* iConfiguration: Index of string descriptor describing the configuration */
0xE0, /* bmAttributes: bus powered and Support Remote Wake-up */ #if (USBD_SELF_POWERED == 1U)
0x32, /* MaxPower 100 mA: this current is used for detecting Vbus */ 0xE0, /* bmAttributes: Bus Powered according to user configuration */
#else
0xA0, /* bmAttributes: Bus Powered according to user configuration */
#endif
USBD_MAX_POWER, /* MaxPower (mA) */
/************** Descriptor of Joystick Mouse interface ****************/ /************** Descriptor of Joystick Mouse interface ****************/
/* 09 */ /* 09 */
@@ -260,7 +273,7 @@ __ALIGN_BEGIN static uint8_t USBD_HID_OtherSpeedCfgDesc[USB_HID_CONFIG_DESC_SIZ]
HID_EPIN_ADDR, /* bEndpointAddress: Endpoint Address (IN) */ HID_EPIN_ADDR, /* bEndpointAddress: Endpoint Address (IN) */
0x03, /* bmAttributes: Interrupt endpoint */ 0x03, /* bmAttributes: Interrupt endpoint */
HID_EPIN_SIZE, /* wMaxPacketSize: 4 Byte max */ HID_EPIN_SIZE, /* wMaxPacketSize: 4 Bytes max */
0x00, 0x00,
HID_FS_BINTERVAL, /* bInterval: Polling Interval */ HID_FS_BINTERVAL, /* bInterval: Polling Interval */
/* 34 */ /* 34 */
@@ -268,7 +281,8 @@ __ALIGN_BEGIN static uint8_t USBD_HID_OtherSpeedCfgDesc[USB_HID_CONFIG_DESC_SIZ]
/* USB HID device Configuration Descriptor */ /* USB HID device Configuration Descriptor */
__ALIGN_BEGIN static uint8_t USBD_HID_Desc[USB_HID_DESC_SIZ] __ALIGN_END = { __ALIGN_BEGIN static uint8_t USBD_HID_Desc[USB_HID_DESC_SIZ] __ALIGN_END =
{
/* 18 */ /* 18 */
0x09, /* bLength: HID Descriptor size */ 0x09, /* bLength: HID Descriptor size */
HID_DESCRIPTOR_TYPE, /* bDescriptorType: HID */ HID_DESCRIPTOR_TYPE, /* bDescriptorType: HID */
@@ -282,7 +296,8 @@ __ALIGN_BEGIN static uint8_t USBD_HID_Desc[USB_HID_DESC_SIZ] __ALIGN_END = {
}; };
/* USB Standard Device Descriptor */ /* USB Standard Device Descriptor */
__ALIGN_BEGIN static uint8_t USBD_HID_DeviceQualifierDesc[USB_LEN_DEV_QUALIFIER_DESC] __ALIGN_END = { __ALIGN_BEGIN static uint8_t USBD_HID_DeviceQualifierDesc[USB_LEN_DEV_QUALIFIER_DESC] __ALIGN_END =
{
USB_LEN_DEV_QUALIFIER_DESC, USB_LEN_DEV_QUALIFIER_DESC,
USB_DESC_TYPE_DEVICE_QUALIFIER, USB_DESC_TYPE_DEVICE_QUALIFIER,
0x00, 0x00,
@@ -295,53 +310,46 @@ __ALIGN_BEGIN static uint8_t USBD_HID_DeviceQualifierDesc[USB_LEN_DEV_QUALIFIER_
0x00, 0x00,
}; };
__ALIGN_BEGIN static uint8_t HID_MOUSE_ReportDesc[HID_MOUSE_REPORT_DESC_SIZE] __ALIGN_END = { __ALIGN_BEGIN static uint8_t HID_MOUSE_ReportDesc[HID_MOUSE_REPORT_DESC_SIZE] __ALIGN_END =
0x05, 0x01, {
0x09, 0x02, 0x05, 0x01, /* Usage Page (Generic Desktop Ctrls) */
0xA1, 0x01, 0x09, 0x02, /* Usage (Mouse) */
0x09, 0x01, 0xA1, 0x01, /* Collection (Application) */
0x09, 0x01, /* Usage (Pointer) */
0xA1, 0x00, 0xA1, 0x00, /* Collection (Physical) */
0x05, 0x09, 0x05, 0x09, /* Usage Page (Button) */
0x19, 0x01, 0x19, 0x01, /* Usage Minimum (0x01) */
0x29, 0x03, 0x29, 0x03, /* Usage Maximum (0x03) */
0x15, 0x00, /* Logical Minimum (0) */
0x15, 0x00, 0x25, 0x01, /* Logical Maximum (1) */
0x25, 0x01, 0x95, 0x03, /* Report Count (3) */
0x95, 0x03, 0x75, 0x01, /* Report Size (1) */
0x75, 0x01, 0x81, 0x02, /* Input (Data,Var,Abs) */
0x95, 0x01, /* Report Count (1) */
0x81, 0x02, 0x75, 0x05, /* Report Size (5) */
0x95, 0x01, 0x81, 0x01, /* Input (Const,Array,Abs) */
0x75, 0x05, 0x05, 0x01, /* Usage Page (Generic Desktop Ctrls) */
0x81, 0x01, 0x09, 0x30, /* Usage (X) */
0x09, 0x31, /* Usage (Y) */
0x05, 0x01, 0x09, 0x38, /* Usage (Wheel) */
0x09, 0x30, 0x15, 0x81, /* Logical Minimum (-127) */
0x09, 0x31, 0x25, 0x7F, /* Logical Maximum (127) */
0x09, 0x38, 0x75, 0x08, /* Report Size (8) */
0x95, 0x03, /* Report Count (3) */
0x15, 0x81, 0x81, 0x06, /* Input (Data,Var,Rel) */
0x25, 0x7F, 0xC0, /* End Collection */
0x75, 0x08, 0x09, 0x3C, /* Usage (Motion Wakeup) */
0x95, 0x03, 0x05, 0xFF, /* Usage Page (Reserved 0xFF) */
0x09, 0x01, /* Usage (0x01) */
0x81, 0x06, 0x15, 0x00, /* Logical Minimum (0) */
0xC0, 0x09, 0x25, 0x01, /* Logical Maximum (1) */
0x3c, 0x05, 0x75, 0x01, /* Report Size (1) */
0xff, 0x09, 0x95, 0x02, /* Report Count (2) */
0xB1, 0x22, /* Feature (Data,Var,Abs,NoWrp) */
0x01, 0x15, 0x75, 0x06, /* Report Size (6) */
0x00, 0x25, 0x95, 0x01, /* Report Count (1) */
0x01, 0x75, 0xB1, 0x01, /* Feature (Const,Array,Abs,NoWrp) */
0x01, 0x95, 0xC0 /* End Collection */
0x02, 0xb1,
0x22, 0x75,
0x06, 0x95,
0x01, 0xb1,
0x01, 0xc0
}; };
/** /**
@@ -365,7 +373,7 @@ static uint8_t USBD_HID_Init(USBD_HandleTypeDef *pdev, uint8_t cfgidx)
USBD_HID_HandleTypeDef *hhid; USBD_HID_HandleTypeDef *hhid;
hhid = USBD_malloc(sizeof(USBD_HID_HandleTypeDef)); hhid = (USBD_HID_HandleTypeDef *)USBD_malloc(sizeof(USBD_HID_HandleTypeDef));
if (hhid == NULL) if (hhid == NULL)
{ {
@@ -384,7 +392,7 @@ static uint8_t USBD_HID_Init(USBD_HandleTypeDef *pdev, uint8_t cfgidx)
pdev->ep_in[HID_EPIN_ADDR & 0xFU].bInterval = HID_FS_BINTERVAL; pdev->ep_in[HID_EPIN_ADDR & 0xFU].bInterval = HID_FS_BINTERVAL;
} }
/* Open EP IN */ /* Open EP IN */
(void)USBD_LL_OpenEP(pdev, HID_EPIN_ADDR, USBD_EP_TYPE_INTR, HID_EPIN_SIZE); (void)USBD_LL_OpenEP(pdev, HID_EPIN_ADDR, USBD_EP_TYPE_INTR, HID_EPIN_SIZE);
pdev->ep_in[HID_EPIN_ADDR & 0xFU].is_used = 1U; pdev->ep_in[HID_EPIN_ADDR & 0xFU].is_used = 1U;
@@ -409,7 +417,7 @@ static uint8_t USBD_HID_DeInit(USBD_HandleTypeDef *pdev, uint8_t cfgidx)
pdev->ep_in[HID_EPIN_ADDR & 0xFU].is_used = 0U; pdev->ep_in[HID_EPIN_ADDR & 0xFU].is_used = 0U;
pdev->ep_in[HID_EPIN_ADDR & 0xFU].bInterval = 0U; pdev->ep_in[HID_EPIN_ADDR & 0xFU].bInterval = 0U;
/* FRee allocated memory */ /* Free allocated memory */
if (pdev->pClassData != NULL) if (pdev->pClassData != NULL)
{ {
(void)USBD_free(pdev->pClassData); (void)USBD_free(pdev->pClassData);
@@ -434,106 +442,111 @@ static uint8_t USBD_HID_Setup(USBD_HandleTypeDef *pdev, USBD_SetupReqTypedef *re
uint8_t *pbuf; uint8_t *pbuf;
uint16_t status_info = 0U; uint16_t status_info = 0U;
if (hhid == NULL)
{
return (uint8_t)USBD_FAIL;
}
switch (req->bmRequest & USB_REQ_TYPE_MASK) switch (req->bmRequest & USB_REQ_TYPE_MASK)
{ {
case USB_REQ_TYPE_CLASS : case USB_REQ_TYPE_CLASS :
switch (req->bRequest) switch (req->bRequest)
{ {
case HID_REQ_SET_PROTOCOL: case HID_REQ_SET_PROTOCOL:
hhid->Protocol = (uint8_t)(req->wValue); hhid->Protocol = (uint8_t)(req->wValue);
break; break;
case HID_REQ_GET_PROTOCOL: case HID_REQ_GET_PROTOCOL:
(void)USBD_CtlSendData(pdev, (uint8_t *)&hhid->Protocol, 1U); (void)USBD_CtlSendData(pdev, (uint8_t *)&hhid->Protocol, 1U);
break; break;
case HID_REQ_SET_IDLE: case HID_REQ_SET_IDLE:
hhid->IdleState = (uint8_t)(req->wValue >> 8); hhid->IdleState = (uint8_t)(req->wValue >> 8);
break; break;
case HID_REQ_GET_IDLE: case HID_REQ_GET_IDLE:
(void)USBD_CtlSendData(pdev, (uint8_t *)&hhid->IdleState, 1U); (void)USBD_CtlSendData(pdev, (uint8_t *)&hhid->IdleState, 1U);
break;
default:
USBD_CtlError(pdev, req);
ret = USBD_FAIL;
break;
}
break;
case USB_REQ_TYPE_STANDARD:
switch (req->bRequest)
{
case USB_REQ_GET_STATUS:
if (pdev->dev_state == USBD_STATE_CONFIGURED)
{
(void)USBD_CtlSendData(pdev, (uint8_t *)&status_info, 2U);
}
else
{
USBD_CtlError(pdev, req);
ret = USBD_FAIL;
}
break;
case USB_REQ_GET_DESCRIPTOR:
if ((req->wValue >> 8) == HID_REPORT_DESC)
{
len = MIN(HID_MOUSE_REPORT_DESC_SIZE, req->wLength);
pbuf = HID_MOUSE_ReportDesc;
}
else if ((req->wValue >> 8) == HID_DESCRIPTOR_TYPE)
{
pbuf = USBD_HID_Desc;
len = MIN(USB_HID_DESC_SIZ, req->wLength);
}
else
{
USBD_CtlError(pdev, req);
ret = USBD_FAIL;
break;
}
(void)USBD_CtlSendData(pdev, pbuf, len);
break;
case USB_REQ_GET_INTERFACE :
if (pdev->dev_state == USBD_STATE_CONFIGURED)
{
(void)USBD_CtlSendData(pdev, (uint8_t *)&hhid->AltSetting, 1U);
}
else
{
USBD_CtlError(pdev, req);
ret = USBD_FAIL;
}
break;
case USB_REQ_SET_INTERFACE:
if (pdev->dev_state == USBD_STATE_CONFIGURED)
{
hhid->AltSetting = (uint8_t)(req->wValue);
}
else
{
USBD_CtlError(pdev, req);
ret = USBD_FAIL;
}
break;
case USB_REQ_CLEAR_FEATURE:
break;
default:
USBD_CtlError(pdev, req);
ret = USBD_FAIL;
break;
}
break; break;
default: default:
USBD_CtlError(pdev, req); USBD_CtlError(pdev, req);
ret = USBD_FAIL; ret = USBD_FAIL;
break; break;
}
break;
case USB_REQ_TYPE_STANDARD:
switch (req->bRequest)
{
case USB_REQ_GET_STATUS:
if (pdev->dev_state == USBD_STATE_CONFIGURED)
{
(void)USBD_CtlSendData(pdev, (uint8_t *)&status_info, 2U);
}
else
{
USBD_CtlError(pdev, req);
ret = USBD_FAIL;
}
break;
case USB_REQ_GET_DESCRIPTOR:
if ((req->wValue >> 8) == HID_REPORT_DESC)
{
len = MIN(HID_MOUSE_REPORT_DESC_SIZE, req->wLength);
pbuf = HID_MOUSE_ReportDesc;
}
else if ((req->wValue >> 8) == HID_DESCRIPTOR_TYPE)
{
pbuf = USBD_HID_Desc;
len = MIN(USB_HID_DESC_SIZ, req->wLength);
}
else
{
USBD_CtlError(pdev, req);
ret = USBD_FAIL;
break;
}
(void)USBD_CtlSendData(pdev, pbuf, len);
break;
case USB_REQ_GET_INTERFACE :
if (pdev->dev_state == USBD_STATE_CONFIGURED)
{
(void)USBD_CtlSendData(pdev, (uint8_t *)&hhid->AltSetting, 1U);
}
else
{
USBD_CtlError(pdev, req);
ret = USBD_FAIL;
}
break;
case USB_REQ_SET_INTERFACE:
if (pdev->dev_state == USBD_STATE_CONFIGURED)
{
hhid->AltSetting = (uint8_t)(req->wValue);
}
else
{
USBD_CtlError(pdev, req);
ret = USBD_FAIL;
}
break;
case USB_REQ_CLEAR_FEATURE:
break;
default:
USBD_CtlError(pdev, req);
ret = USBD_FAIL;
break;
}
break;
default:
USBD_CtlError(pdev, req);
ret = USBD_FAIL;
break;
} }
return (uint8_t)ret; return (uint8_t)ret;
@@ -550,6 +563,11 @@ uint8_t USBD_HID_SendReport(USBD_HandleTypeDef *pdev, uint8_t *report, uint16_t
{ {
USBD_HID_HandleTypeDef *hhid = (USBD_HID_HandleTypeDef *)pdev->pClassData; USBD_HID_HandleTypeDef *hhid = (USBD_HID_HandleTypeDef *)pdev->pClassData;
if (hhid == NULL)
{
return (uint8_t)USBD_FAIL;
}
if (pdev->dev_state == USBD_STATE_CONFIGURED) if (pdev->dev_state == USBD_STATE_CONFIGURED)
{ {
if (hhid->state == HID_IDLE) if (hhid->state == HID_IDLE)
@@ -651,11 +669,11 @@ static uint8_t USBD_HID_DataIn(USBD_HandleTypeDef *pdev, uint8_t epnum)
/** /**
* @brief DeviceQualifierDescriptor * @brief DeviceQualifierDescriptor
* return Device Qualifier descriptor * return Device Qualifier descriptor
* @param length : pointer data length * @param length : pointer data length
* @retval pointer to descriptor buffer * @retval pointer to descriptor buffer
*/ */
static uint8_t *USBD_HID_GetDeviceQualifierDesc(uint16_t *length) static uint8_t *USBD_HID_GetDeviceQualifierDesc(uint16_t *length)
{ {
*length = (uint16_t)sizeof(USBD_HID_DeviceQualifierDesc); *length = (uint16_t)sizeof(USBD_HID_DeviceQualifierDesc);

View File

@@ -144,7 +144,7 @@ void MSC_BOT_CplClrFeature(USBD_HandleTypeDef *pdev,
*/ */
/** /**
* @} * @}
*/ */
/************************ (C) COPYRIGHT STMicroelectronics *****END OF FILE****/ /************************ (C) COPYRIGHT STMicroelectronics *****END OF FILE****/

View File

@@ -99,7 +99,7 @@ extern uint8_t MSC_Mode_Sense10_data[MODE_SENSE10_LEN];
*/ */
/** /**
* @} * @}
*/ */
/************************ (C) COPYRIGHT STMicroelectronics *****END OF FILE****/ /************************ (C) COPYRIGHT STMicroelectronics *****END OF FILE****/

View File

@@ -178,8 +178,8 @@ void SCSI_SenseCode(USBD_HandleTypeDef *pdev, uint8_t lun, uint8_t sKey,
*/ */
/** /**
* @} * @}
*/ */
/************************ (C) COPYRIGHT STMicroelectronics *****END OF FILE****/ /************************ (C) COPYRIGHT STMicroelectronics *****END OF FILE****/

View File

@@ -92,6 +92,6 @@ extern USBD_StorageTypeDef USBD_MSC_Template_fops;
*/ */
/** /**
* @} * @}
*/ */
/************************ (C) COPYRIGHT STMicroelectronics *****END OF FILE****/ /************************ (C) COPYRIGHT STMicroelectronics *****END OF FILE****/

View File

@@ -123,16 +123,20 @@ USBD_ClassTypeDef USBD_MSC =
/* All Descriptors (Configuration, Interface, Endpoint, Class, Vendor */ /* All Descriptors (Configuration, Interface, Endpoint, Class, Vendor */
__ALIGN_BEGIN static uint8_t USBD_MSC_CfgHSDesc[USB_MSC_CONFIG_DESC_SIZ] __ALIGN_END = __ALIGN_BEGIN static uint8_t USBD_MSC_CfgHSDesc[USB_MSC_CONFIG_DESC_SIZ] __ALIGN_END =
{ {
0x09, /* bLength: Configuation Descriptor size */ 0x09, /* bLength: Configuration Descriptor size */
USB_DESC_TYPE_CONFIGURATION, /* bDescriptorType: Configuration */ USB_DESC_TYPE_CONFIGURATION, /* bDescriptorType: Configuration */
USB_MSC_CONFIG_DESC_SIZ, USB_MSC_CONFIG_DESC_SIZ,
0x00, 0x00,
0x01, /* bNumInterfaces: 1 interface */ 0x01, /* bNumInterfaces: 1 interface */
0x01, /* bConfigurationValue: */ 0x01, /* bConfigurationValue */
0x04, /* iConfiguration: */ 0x04, /* iConfiguration */
0xC0, /* bmAttributes: */ #if (USBD_SELF_POWERED == 1U)
0x32, /* MaxPower 100 mA */ 0xC0, /* bmAttributes: Bus Powered according to user configuration */
#else
0x80, /* bmAttributes: Bus Powered according to user configuration */
#endif
USBD_MAX_POWER, /* MaxPower (mA) */
/******************** Mass Storage interface ********************/ /******************** Mass Storage interface ********************/
0x09, /* bLength: Interface Descriptor size */ 0x09, /* bLength: Interface Descriptor size */
@@ -143,7 +147,7 @@ __ALIGN_BEGIN static uint8_t USBD_MSC_CfgHSDesc[USB_MSC_CONFIG_DESC_SIZ] __ALIG
0x08, /* bInterfaceClass: MSC Class */ 0x08, /* bInterfaceClass: MSC Class */
0x06, /* bInterfaceSubClass : SCSI transparent */ 0x06, /* bInterfaceSubClass : SCSI transparent */
0x50, /* nInterfaceProtocol */ 0x50, /* nInterfaceProtocol */
0x05, /* iInterface: */ 0x05, /* iInterface */
/******************** Mass Storage Endpoints ********************/ /******************** Mass Storage Endpoints ********************/
0x07, /* Endpoint descriptor length = 7 */ 0x07, /* Endpoint descriptor length = 7 */
0x05, /* Endpoint descriptor type */ 0x05, /* Endpoint descriptor type */
@@ -166,23 +170,27 @@ __ALIGN_BEGIN static uint8_t USBD_MSC_CfgHSDesc[USB_MSC_CONFIG_DESC_SIZ] __ALIG
/* All Descriptors (Configuration, Interface, Endpoint, Class, Vendor */ /* All Descriptors (Configuration, Interface, Endpoint, Class, Vendor */
__ALIGN_BEGIN static uint8_t USBD_MSC_CfgFSDesc[USB_MSC_CONFIG_DESC_SIZ] __ALIGN_END = __ALIGN_BEGIN static uint8_t USBD_MSC_CfgFSDesc[USB_MSC_CONFIG_DESC_SIZ] __ALIGN_END =
{ {
0x09, /* bLength: Configuation Descriptor size */ 0x09, /* bLength: Configuration Descriptor size */
USB_DESC_TYPE_CONFIGURATION, /* bDescriptorType: Configuration */ USB_DESC_TYPE_CONFIGURATION, /* bDescriptorType: Configuration */
USB_MSC_CONFIG_DESC_SIZ, USB_MSC_CONFIG_DESC_SIZ,
0x00, 0x00,
0x01, /* bNumInterfaces: 1 interface */ 0x01, /* bNumInterfaces: 1 interface */
0x01, /* bConfigurationValue: */ 0x01, /* bConfigurationValue */
0x04, /* iConfiguration: */ 0x04, /* iConfiguration */
0xC0, /* bmAttributes: */ #if (USBD_SELF_POWERED == 1U)
0x32, /* MaxPower 100 mA */ 0xC0, /* bmAttributes: Bus Powered according to user configuration */
#else
0x80, /* bmAttributes: Bus Powered according to user configuration */
#endif
USBD_MAX_POWER, /* MaxPower (mA) */
/******************** Mass Storage interface ********************/ /******************** Mass Storage interface ********************/
0x09, /* bLength: Interface Descriptor size */ 0x09, /* bLength: Interface Descriptor size */
0x04, /* bDescriptorType: */ 0x04, /* bDescriptorType: */
0x00, /* bInterfaceNumber: Number of Interface */ 0x00, /* bInterfaceNumber: Number of Interface */
0x00, /* bAlternateSetting: Alternate setting */ 0x00, /* bAlternateSetting: Alternate setting */
0x02, /* bNumEndpoints*/ 0x02, /* bNumEndpoints */
0x08, /* bInterfaceClass: MSC Class */ 0x08, /* bInterfaceClass: MSC Class */
0x06, /* bInterfaceSubClass : SCSI transparent*/ 0x06, /* bInterfaceSubClass : SCSI transparent*/
0x50, /* nInterfaceProtocol */ 0x50, /* nInterfaceProtocol */
@@ -207,27 +215,31 @@ __ALIGN_BEGIN static uint8_t USBD_MSC_CfgFSDesc[USB_MSC_CONFIG_DESC_SIZ] __ALIG
__ALIGN_BEGIN static uint8_t USBD_MSC_OtherSpeedCfgDesc[USB_MSC_CONFIG_DESC_SIZ] __ALIGN_END = __ALIGN_BEGIN static uint8_t USBD_MSC_OtherSpeedCfgDesc[USB_MSC_CONFIG_DESC_SIZ] __ALIGN_END =
{ {
0x09, /* bLength: Configuation Descriptor size */ 0x09, /* bLength: Configuration Descriptor size */
USB_DESC_TYPE_OTHER_SPEED_CONFIGURATION, USB_DESC_TYPE_OTHER_SPEED_CONFIGURATION,
USB_MSC_CONFIG_DESC_SIZ, USB_MSC_CONFIG_DESC_SIZ,
0x00, 0x00,
0x01, /* bNumInterfaces: 1 interface */ 0x01, /* bNumInterfaces: 1 interface */
0x01, /* bConfigurationValue: */ 0x01, /* bConfigurationValue */
0x04, /* iConfiguration: */ 0x04, /* iConfiguration */
0xC0, /* bmAttributes: */ #if (USBD_SELF_POWERED == 1U)
0x32, /* MaxPower 100 mA */ 0xC0, /* bmAttributes: Bus Powered according to user configuration */
#else
0x80, /* bmAttributes: Bus Powered according to user configuration */
#endif
USBD_MAX_POWER, /* MaxPower (mA) */
/******************** Mass Storage interface ********************/ /******************** Mass Storage interface ********************/
0x09, /* bLength: Interface Descriptor size */ 0x09, /* bLength: Interface Descriptor size */
0x04, /* bDescriptorType: */ 0x04, /* bDescriptorType */
0x00, /* bInterfaceNumber: Number of Interface */ 0x00, /* bInterfaceNumber: Number of Interface */
0x00, /* bAlternateSetting: Alternate setting */ 0x00, /* bAlternateSetting: Alternate setting */
0x02, /* bNumEndpoints */ 0x02, /* bNumEndpoints */
0x08, /* bInterfaceClass: MSC Class */ 0x08, /* bInterfaceClass: MSC Class */
0x06, /* bInterfaceSubClass : SCSI transparent command set */ 0x06, /* bInterfaceSubClass : SCSI transparent command set */
0x50, /* nInterfaceProtocol */ 0x50, /* nInterfaceProtocol */
0x05, /* iInterface: */ 0x05, /* iInterface */
/******************** Mass Storage Endpoints ********************/ /******************** Mass Storage Endpoints ********************/
0x07, /* Endpoint descriptor length = 7 */ 0x07, /* Endpoint descriptor length = 7 */
0x05, /* Endpoint descriptor type */ 0x05, /* Endpoint descriptor type */
@@ -281,7 +293,7 @@ uint8_t USBD_MSC_Init(USBD_HandleTypeDef *pdev, uint8_t cfgidx)
UNUSED(cfgidx); UNUSED(cfgidx);
USBD_MSC_BOT_HandleTypeDef *hmsc; USBD_MSC_BOT_HandleTypeDef *hmsc;
hmsc = USBD_malloc(sizeof(USBD_MSC_BOT_HandleTypeDef)); hmsc = (USBD_MSC_BOT_HandleTypeDef *)USBD_malloc(sizeof(USBD_MSC_BOT_HandleTypeDef));
if (hmsc == NULL) if (hmsc == NULL)
{ {
@@ -320,7 +332,7 @@ uint8_t USBD_MSC_Init(USBD_HandleTypeDef *pdev, uint8_t cfgidx)
/** /**
* @brief USBD_MSC_DeInit * @brief USBD_MSC_DeInit
* DeInitilaize the mass storage configuration * DeInitialize the mass storage configuration
* @param pdev: device instance * @param pdev: device instance
* @param cfgidx: configuration index * @param cfgidx: configuration index
* @retval status * @retval status
@@ -337,12 +349,12 @@ uint8_t USBD_MSC_DeInit(USBD_HandleTypeDef *pdev, uint8_t cfgidx)
(void)USBD_LL_CloseEP(pdev, MSC_EPIN_ADDR); (void)USBD_LL_CloseEP(pdev, MSC_EPIN_ADDR);
pdev->ep_in[MSC_EPIN_ADDR & 0xFU].is_used = 0U; pdev->ep_in[MSC_EPIN_ADDR & 0xFU].is_used = 0U;
/* De-Init the BOT layer */
MSC_BOT_DeInit(pdev);
/* Free MSC Class Resources */ /* Free MSC Class Resources */
if (pdev->pClassData != NULL) if (pdev->pClassData != NULL)
{ {
/* De-Init the BOT layer */
MSC_BOT_DeInit(pdev);
(void)USBD_free(pdev->pClassData); (void)USBD_free(pdev->pClassData);
pdev->pClassData = NULL; pdev->pClassData = NULL;
} }
@@ -350,108 +362,120 @@ uint8_t USBD_MSC_DeInit(USBD_HandleTypeDef *pdev, uint8_t cfgidx)
return (uint8_t)USBD_OK; return (uint8_t)USBD_OK;
} }
/** /**
* @brief USBD_MSC_Setup * @brief USBD_MSC_Setup
* Handle the MSC specific requests * Handle the MSC specific requests
* @param pdev: device instance * @param pdev: device instance
* @param req: USB request * @param req: USB request
* @retval status * @retval status
*/ */
uint8_t USBD_MSC_Setup(USBD_HandleTypeDef *pdev, USBD_SetupReqTypedef *req) uint8_t USBD_MSC_Setup(USBD_HandleTypeDef *pdev, USBD_SetupReqTypedef *req)
{ {
USBD_MSC_BOT_HandleTypeDef *hmsc = (USBD_MSC_BOT_HandleTypeDef *)pdev->pClassData; USBD_MSC_BOT_HandleTypeDef *hmsc = (USBD_MSC_BOT_HandleTypeDef *)pdev->pClassData;
USBD_StatusTypeDef ret = USBD_OK; USBD_StatusTypeDef ret = USBD_OK;
uint16_t status_info = 0U; uint16_t status_info = 0U;
if (hmsc == NULL)
{
return (uint8_t)USBD_FAIL;
}
switch (req->bmRequest & USB_REQ_TYPE_MASK) switch (req->bmRequest & USB_REQ_TYPE_MASK)
{ {
/* Class request */ /* Class request */
case USB_REQ_TYPE_CLASS: case USB_REQ_TYPE_CLASS:
switch (req->bRequest) switch (req->bRequest)
{
case BOT_GET_MAX_LUN:
if ((req->wValue == 0U) && (req->wLength == 1U) &&
((req->bmRequest & 0x80U) == 0x80U))
{ {
hmsc->max_lun = (uint32_t)((USBD_StorageTypeDef *)pdev->pUserData)->GetMaxLun(); case BOT_GET_MAX_LUN:
(void)USBD_CtlSendData(pdev, (uint8_t *)&hmsc->max_lun, 1U); if ((req->wValue == 0U) && (req->wLength == 1U) &&
} ((req->bmRequest & 0x80U) == 0x80U))
else {
{ hmsc->max_lun = (uint32_t)((USBD_StorageTypeDef *)pdev->pUserData)->GetMaxLun();
USBD_CtlError(pdev, req); (void)USBD_CtlSendData(pdev, (uint8_t *)&hmsc->max_lun, 1U);
ret = USBD_FAIL; }
} else
break; {
USBD_CtlError(pdev, req);
ret = USBD_FAIL;
}
break;
case BOT_RESET : case BOT_RESET :
if ((req->wValue == 0U) && (req->wLength == 0U) && if ((req->wValue == 0U) && (req->wLength == 0U) &&
((req->bmRequest & 0x80U) != 0x80U)) ((req->bmRequest & 0x80U) != 0x80U))
{ {
MSC_BOT_Reset(pdev); MSC_BOT_Reset(pdev);
} }
else else
{ {
USBD_CtlError(pdev, req); USBD_CtlError(pdev, req);
ret = USBD_FAIL; ret = USBD_FAIL;
} }
break; break;
default: default:
USBD_CtlError(pdev, req); USBD_CtlError(pdev, req);
ret = USBD_FAIL; ret = USBD_FAIL;
break;
}
break; break;
}
break;
/* Interface & Endpoint request */ /* Interface & Endpoint request */
case USB_REQ_TYPE_STANDARD: case USB_REQ_TYPE_STANDARD:
switch (req->bRequest) switch (req->bRequest)
{
case USB_REQ_GET_STATUS:
if (pdev->dev_state == USBD_STATE_CONFIGURED)
{ {
(void)USBD_CtlSendData(pdev, (uint8_t *)&status_info, 2U); case USB_REQ_GET_STATUS:
} if (pdev->dev_state == USBD_STATE_CONFIGURED)
else {
{ (void)USBD_CtlSendData(pdev, (uint8_t *)&status_info, 2U);
USBD_CtlError(pdev, req); }
ret = USBD_FAIL; else
} {
break; USBD_CtlError(pdev, req);
ret = USBD_FAIL;
}
break;
case USB_REQ_GET_INTERFACE: case USB_REQ_GET_INTERFACE:
if (pdev->dev_state == USBD_STATE_CONFIGURED) if (pdev->dev_state == USBD_STATE_CONFIGURED)
{ {
(void)USBD_CtlSendData(pdev, (uint8_t *)&hmsc->interface, 1U); (void)USBD_CtlSendData(pdev, (uint8_t *)&hmsc->interface, 1U);
} }
else else
{ {
USBD_CtlError(pdev, req); USBD_CtlError(pdev, req);
ret = USBD_FAIL; ret = USBD_FAIL;
} }
break; break;
case USB_REQ_SET_INTERFACE: case USB_REQ_SET_INTERFACE:
if (pdev->dev_state == USBD_STATE_CONFIGURED) if (pdev->dev_state == USBD_STATE_CONFIGURED)
{ {
hmsc->interface = (uint8_t)(req->wValue); hmsc->interface = (uint8_t)(req->wValue);
} }
else else
{ {
USBD_CtlError(pdev, req); USBD_CtlError(pdev, req);
ret = USBD_FAIL; ret = USBD_FAIL;
} }
break; break;
case USB_REQ_CLEAR_FEATURE: case USB_REQ_CLEAR_FEATURE:
if (pdev->dev_state == USBD_STATE_CONFIGURED) if (pdev->dev_state == USBD_STATE_CONFIGURED)
{ {
if (req->wValue == USB_FEATURE_EP_HALT) if (req->wValue == USB_FEATURE_EP_HALT)
{ {
/* Flush the FIFO */ /* Flush the FIFO */
(void)USBD_LL_FlushEP(pdev, (uint8_t)req->wIndex); (void)USBD_LL_FlushEP(pdev, (uint8_t)req->wIndex);
/* Handle BOT error */ /* Handle BOT error */
MSC_BOT_CplClrFeature(pdev, (uint8_t)req->wIndex); MSC_BOT_CplClrFeature(pdev, (uint8_t)req->wIndex);
} }
}
break;
default:
USBD_CtlError(pdev, req);
ret = USBD_FAIL;
break;
} }
break; break;
@@ -459,25 +483,18 @@ uint8_t USBD_MSC_Setup(USBD_HandleTypeDef *pdev, USBD_SetupReqTypedef *req)
USBD_CtlError(pdev, req); USBD_CtlError(pdev, req);
ret = USBD_FAIL; ret = USBD_FAIL;
break; break;
}
break;
default:
USBD_CtlError(pdev, req);
ret = USBD_FAIL;
break;
} }
return (uint8_t)ret; return (uint8_t)ret;
} }
/** /**
* @brief USBD_MSC_DataIn * @brief USBD_MSC_DataIn
* handle data IN Stage * handle data IN Stage
* @param pdev: device instance * @param pdev: device instance
* @param epnum: endpoint index * @param epnum: endpoint index
* @retval status * @retval status
*/ */
uint8_t USBD_MSC_DataIn(USBD_HandleTypeDef *pdev, uint8_t epnum) uint8_t USBD_MSC_DataIn(USBD_HandleTypeDef *pdev, uint8_t epnum)
{ {
MSC_BOT_DataIn(pdev, epnum); MSC_BOT_DataIn(pdev, epnum);
@@ -486,12 +503,12 @@ uint8_t USBD_MSC_DataIn(USBD_HandleTypeDef *pdev, uint8_t epnum)
} }
/** /**
* @brief USBD_MSC_DataOut * @brief USBD_MSC_DataOut
* handle data OUT Stage * handle data OUT Stage
* @param pdev: device instance * @param pdev: device instance
* @param epnum: endpoint index * @param epnum: endpoint index
* @retval status * @retval status
*/ */
uint8_t USBD_MSC_DataOut(USBD_HandleTypeDef *pdev, uint8_t epnum) uint8_t USBD_MSC_DataOut(USBD_HandleTypeDef *pdev, uint8_t epnum)
{ {
MSC_BOT_DataOut(pdev, epnum); MSC_BOT_DataOut(pdev, epnum);
@@ -500,11 +517,11 @@ uint8_t USBD_MSC_DataOut(USBD_HandleTypeDef *pdev, uint8_t epnum)
} }
/** /**
* @brief USBD_MSC_GetHSCfgDesc * @brief USBD_MSC_GetHSCfgDesc
* return configuration descriptor * return configuration descriptor
* @param length : pointer data length * @param length : pointer data length
* @retval pointer to descriptor buffer * @retval pointer to descriptor buffer
*/ */
uint8_t *USBD_MSC_GetHSCfgDesc(uint16_t *length) uint8_t *USBD_MSC_GetHSCfgDesc(uint16_t *length)
{ {
*length = (uint16_t)sizeof(USBD_MSC_CfgHSDesc); *length = (uint16_t)sizeof(USBD_MSC_CfgHSDesc);
@@ -513,11 +530,11 @@ uint8_t *USBD_MSC_GetHSCfgDesc(uint16_t *length)
} }
/** /**
* @brief USBD_MSC_GetFSCfgDesc * @brief USBD_MSC_GetFSCfgDesc
* return configuration descriptor * return configuration descriptor
* @param length : pointer data length * @param length : pointer data length
* @retval pointer to descriptor buffer * @retval pointer to descriptor buffer
*/ */
uint8_t *USBD_MSC_GetFSCfgDesc(uint16_t *length) uint8_t *USBD_MSC_GetFSCfgDesc(uint16_t *length)
{ {
*length = (uint16_t)sizeof(USBD_MSC_CfgFSDesc); *length = (uint16_t)sizeof(USBD_MSC_CfgFSDesc);
@@ -526,11 +543,11 @@ uint8_t *USBD_MSC_GetFSCfgDesc(uint16_t *length)
} }
/** /**
* @brief USBD_MSC_GetOtherSpeedCfgDesc * @brief USBD_MSC_GetOtherSpeedCfgDesc
* return other speed configuration descriptor * return other speed configuration descriptor
* @param length : pointer data length * @param length : pointer data length
* @retval pointer to descriptor buffer * @retval pointer to descriptor buffer
*/ */
uint8_t *USBD_MSC_GetOtherSpeedCfgDesc(uint16_t *length) uint8_t *USBD_MSC_GetOtherSpeedCfgDesc(uint16_t *length)
{ {
*length = (uint16_t)sizeof(USBD_MSC_OtherSpeedCfgDesc); *length = (uint16_t)sizeof(USBD_MSC_OtherSpeedCfgDesc);
@@ -538,11 +555,11 @@ uint8_t *USBD_MSC_GetOtherSpeedCfgDesc(uint16_t *length)
return USBD_MSC_OtherSpeedCfgDesc; return USBD_MSC_OtherSpeedCfgDesc;
} }
/** /**
* @brief DeviceQualifierDescriptor * @brief DeviceQualifierDescriptor
* return Device Qualifier descriptor * return Device Qualifier descriptor
* @param length : pointer data length * @param length : pointer data length
* @retval pointer to descriptor buffer * @retval pointer to descriptor buffer
*/ */
uint8_t *USBD_MSC_GetDeviceQualifierDescriptor(uint16_t *length) uint8_t *USBD_MSC_GetDeviceQualifierDescriptor(uint16_t *length)
{ {
*length = (uint16_t)sizeof(USBD_MSC_DeviceQualifierDesc); *length = (uint16_t)sizeof(USBD_MSC_DeviceQualifierDesc);
@@ -551,10 +568,10 @@ uint8_t *USBD_MSC_GetDeviceQualifierDescriptor(uint16_t *length)
} }
/** /**
* @brief USBD_MSC_RegisterStorage * @brief USBD_MSC_RegisterStorage
* @param fops: storage callback * @param fops: storage callback
* @retval status * @retval status
*/ */
uint8_t USBD_MSC_RegisterStorage(USBD_HandleTypeDef *pdev, USBD_StorageTypeDef *fops) uint8_t USBD_MSC_RegisterStorage(USBD_HandleTypeDef *pdev, USBD_StorageTypeDef *fops)
{ {
if (fops == NULL) if (fops == NULL)

View File

@@ -90,15 +90,20 @@ static void MSC_BOT_Abort(USBD_HandleTypeDef *pdev);
/** /**
* @brief MSC_BOT_Init * @brief MSC_BOT_Init
* Initialize the BOT Process * Initialize the BOT Process
* @param pdev: device instance * @param pdev: device instance
* @retval None * @retval None
*/ */
void MSC_BOT_Init(USBD_HandleTypeDef *pdev) void MSC_BOT_Init(USBD_HandleTypeDef *pdev)
{ {
USBD_MSC_BOT_HandleTypeDef *hmsc = (USBD_MSC_BOT_HandleTypeDef *)pdev->pClassData; USBD_MSC_BOT_HandleTypeDef *hmsc = (USBD_MSC_BOT_HandleTypeDef *)pdev->pClassData;
if (hmsc == NULL)
{
return;
}
hmsc->bot_state = USBD_BOT_IDLE; hmsc->bot_state = USBD_BOT_IDLE;
hmsc->bot_status = USBD_BOT_STATUS_NORMAL; hmsc->bot_status = USBD_BOT_STATUS_NORMAL;
@@ -111,88 +116,107 @@ void MSC_BOT_Init(USBD_HandleTypeDef *pdev)
(void)USBD_LL_FlushEP(pdev, MSC_EPOUT_ADDR); (void)USBD_LL_FlushEP(pdev, MSC_EPOUT_ADDR);
(void)USBD_LL_FlushEP(pdev, MSC_EPIN_ADDR); (void)USBD_LL_FlushEP(pdev, MSC_EPIN_ADDR);
/* Prapare EP to Receive First BOT Cmd */ /* Prepare EP to Receive First BOT Cmd */
(void)USBD_LL_PrepareReceive(pdev, MSC_EPOUT_ADDR, (uint8_t *)&hmsc->cbw, (void)USBD_LL_PrepareReceive(pdev, MSC_EPOUT_ADDR, (uint8_t *)&hmsc->cbw,
USBD_BOT_CBW_LENGTH); USBD_BOT_CBW_LENGTH);
} }
/** /**
* @brief MSC_BOT_Reset * @brief MSC_BOT_Reset
* Reset the BOT Machine * Reset the BOT Machine
* @param pdev: device instance * @param pdev: device instance
* @retval None * @retval None
*/ */
void MSC_BOT_Reset(USBD_HandleTypeDef *pdev) void MSC_BOT_Reset(USBD_HandleTypeDef *pdev)
{ {
USBD_MSC_BOT_HandleTypeDef *hmsc = (USBD_MSC_BOT_HandleTypeDef *)pdev->pClassData; USBD_MSC_BOT_HandleTypeDef *hmsc = (USBD_MSC_BOT_HandleTypeDef *)pdev->pClassData;
if (hmsc == NULL)
{
return;
}
hmsc->bot_state = USBD_BOT_IDLE; hmsc->bot_state = USBD_BOT_IDLE;
hmsc->bot_status = USBD_BOT_STATUS_RECOVERY; hmsc->bot_status = USBD_BOT_STATUS_RECOVERY;
(void)USBD_LL_ClearStallEP(pdev, MSC_EPIN_ADDR); (void)USBD_LL_ClearStallEP(pdev, MSC_EPIN_ADDR);
(void)USBD_LL_ClearStallEP(pdev, MSC_EPOUT_ADDR); (void)USBD_LL_ClearStallEP(pdev, MSC_EPOUT_ADDR);
/* Prapare EP to Receive First BOT Cmd */ /* Prepare EP to Receive First BOT Cmd */
(void)USBD_LL_PrepareReceive(pdev, MSC_EPOUT_ADDR, (uint8_t *)&hmsc->cbw, (void)USBD_LL_PrepareReceive(pdev, MSC_EPOUT_ADDR, (uint8_t *)&hmsc->cbw,
USBD_BOT_CBW_LENGTH); USBD_BOT_CBW_LENGTH);
} }
/** /**
* @brief MSC_BOT_DeInit * @brief MSC_BOT_DeInit
* Deinitialize the BOT Machine * DeInitialize the BOT Machine
* @param pdev: device instance * @param pdev: device instance
* @retval None * @retval None
*/ */
void MSC_BOT_DeInit(USBD_HandleTypeDef *pdev) void MSC_BOT_DeInit(USBD_HandleTypeDef *pdev)
{ {
USBD_MSC_BOT_HandleTypeDef *hmsc = (USBD_MSC_BOT_HandleTypeDef *)pdev->pClassData; USBD_MSC_BOT_HandleTypeDef *hmsc = (USBD_MSC_BOT_HandleTypeDef *)pdev->pClassData;
hmsc->bot_state = USBD_BOT_IDLE;
if (hmsc != NULL)
{
hmsc->bot_state = USBD_BOT_IDLE;
}
} }
/** /**
* @brief MSC_BOT_DataIn * @brief MSC_BOT_DataIn
* Handle BOT IN data stage * Handle BOT IN data stage
* @param pdev: device instance * @param pdev: device instance
* @param epnum: endpoint index * @param epnum: endpoint index
* @retval None * @retval None
*/ */
void MSC_BOT_DataIn(USBD_HandleTypeDef *pdev, uint8_t epnum) void MSC_BOT_DataIn(USBD_HandleTypeDef *pdev, uint8_t epnum)
{ {
UNUSED(epnum); UNUSED(epnum);
USBD_MSC_BOT_HandleTypeDef *hmsc = (USBD_MSC_BOT_HandleTypeDef *)pdev->pClassData; USBD_MSC_BOT_HandleTypeDef *hmsc = (USBD_MSC_BOT_HandleTypeDef *)pdev->pClassData;
if (hmsc == NULL)
{
return;
}
switch (hmsc->bot_state) switch (hmsc->bot_state)
{ {
case USBD_BOT_DATA_IN: case USBD_BOT_DATA_IN:
if (SCSI_ProcessCmd(pdev, hmsc->cbw.bLUN, &hmsc->cbw.CB[0]) < 0) if (SCSI_ProcessCmd(pdev, hmsc->cbw.bLUN, &hmsc->cbw.CB[0]) < 0)
{ {
MSC_BOT_SendCSW(pdev, USBD_CSW_CMD_FAILED); MSC_BOT_SendCSW(pdev, USBD_CSW_CMD_FAILED);
} }
break; break;
case USBD_BOT_SEND_DATA: case USBD_BOT_SEND_DATA:
case USBD_BOT_LAST_DATA_IN: case USBD_BOT_LAST_DATA_IN:
MSC_BOT_SendCSW(pdev, USBD_CSW_CMD_PASSED); MSC_BOT_SendCSW(pdev, USBD_CSW_CMD_PASSED);
break; break;
default: default:
break; break;
} }
} }
/** /**
* @brief MSC_BOT_DataOut * @brief MSC_BOT_DataOut
* Process MSC OUT data * Process MSC OUT data
* @param pdev: device instance * @param pdev: device instance
* @param epnum: endpoint index * @param epnum: endpoint index
* @retval None * @retval None
*/ */
void MSC_BOT_DataOut(USBD_HandleTypeDef *pdev, uint8_t epnum) void MSC_BOT_DataOut(USBD_HandleTypeDef *pdev, uint8_t epnum)
{ {
UNUSED(epnum); UNUSED(epnum);
USBD_MSC_BOT_HandleTypeDef *hmsc = (USBD_MSC_BOT_HandleTypeDef *)pdev->pClassData; USBD_MSC_BOT_HandleTypeDef *hmsc = (USBD_MSC_BOT_HandleTypeDef *)pdev->pClassData;
if (hmsc == NULL)
{
return;
}
switch (hmsc->bot_state) switch (hmsc->bot_state)
{ {
case USBD_BOT_IDLE: case USBD_BOT_IDLE:
@@ -212,15 +236,20 @@ void MSC_BOT_DataOut(USBD_HandleTypeDef *pdev, uint8_t epnum)
} }
/** /**
* @brief MSC_BOT_CBW_Decode * @brief MSC_BOT_CBW_Decode
* Decode the CBW command and set the BOT state machine accordingly * Decode the CBW command and set the BOT state machine accordingly
* @param pdev: device instance * @param pdev: device instance
* @retval None * @retval None
*/ */
static void MSC_BOT_CBW_Decode(USBD_HandleTypeDef *pdev) static void MSC_BOT_CBW_Decode(USBD_HandleTypeDef *pdev)
{ {
USBD_MSC_BOT_HandleTypeDef *hmsc = (USBD_MSC_BOT_HandleTypeDef *)pdev->pClassData; USBD_MSC_BOT_HandleTypeDef *hmsc = (USBD_MSC_BOT_HandleTypeDef *)pdev->pClassData;
if (hmsc == NULL)
{
return;
}
hmsc->csw.dTag = hmsc->cbw.dTag; hmsc->csw.dTag = hmsc->cbw.dTag;
hmsc->csw.dDataResidue = hmsc->cbw.dDataLength; hmsc->csw.dDataResidue = hmsc->cbw.dDataLength;
@@ -273,19 +302,24 @@ static void MSC_BOT_CBW_Decode(USBD_HandleTypeDef *pdev)
} }
/** /**
* @brief MSC_BOT_SendData * @brief MSC_BOT_SendData
* Send the requested data * Send the requested data
* @param pdev: device instance * @param pdev: device instance
* @param buf: pointer to data buffer * @param buf: pointer to data buffer
* @param len: Data Length * @param len: Data Length
* @retval None * @retval None
*/ */
static void MSC_BOT_SendData(USBD_HandleTypeDef *pdev, uint8_t *pbuf, uint32_t len) static void MSC_BOT_SendData(USBD_HandleTypeDef *pdev, uint8_t *pbuf, uint32_t len)
{ {
USBD_MSC_BOT_HandleTypeDef *hmsc = (USBD_MSC_BOT_HandleTypeDef *)pdev->pClassData; USBD_MSC_BOT_HandleTypeDef *hmsc = (USBD_MSC_BOT_HandleTypeDef *)pdev->pClassData;
uint32_t length = MIN(hmsc->cbw.dDataLength, len); uint32_t length = MIN(hmsc->cbw.dDataLength, len);
if (hmsc == NULL)
{
return;
}
hmsc->csw.dDataResidue -= len; hmsc->csw.dDataResidue -= len;
hmsc->csw.bStatus = USBD_CSW_CMD_PASSED; hmsc->csw.bStatus = USBD_CSW_CMD_PASSED;
hmsc->bot_state = USBD_BOT_SEND_DATA; hmsc->bot_state = USBD_BOT_SEND_DATA;
@@ -294,16 +328,21 @@ static void MSC_BOT_SendData(USBD_HandleTypeDef *pdev, uint8_t *pbuf, uint32_t
} }
/** /**
* @brief MSC_BOT_SendCSW * @brief MSC_BOT_SendCSW
* Send the Command Status Wrapper * Send the Command Status Wrapper
* @param pdev: device instance * @param pdev: device instance
* @param status : CSW status * @param status : CSW status
* @retval None * @retval None
*/ */
void MSC_BOT_SendCSW(USBD_HandleTypeDef *pdev, uint8_t CSW_Status) void MSC_BOT_SendCSW(USBD_HandleTypeDef *pdev, uint8_t CSW_Status)
{ {
USBD_MSC_BOT_HandleTypeDef *hmsc = (USBD_MSC_BOT_HandleTypeDef *)pdev->pClassData; USBD_MSC_BOT_HandleTypeDef *hmsc = (USBD_MSC_BOT_HandleTypeDef *)pdev->pClassData;
if (hmsc == NULL)
{
return;
}
hmsc->csw.dSignature = USBD_BOT_CSW_SIGNATURE; hmsc->csw.dSignature = USBD_BOT_CSW_SIGNATURE;
hmsc->csw.bStatus = CSW_Status; hmsc->csw.bStatus = CSW_Status;
hmsc->bot_state = USBD_BOT_IDLE; hmsc->bot_state = USBD_BOT_IDLE;
@@ -317,16 +356,21 @@ void MSC_BOT_SendCSW(USBD_HandleTypeDef *pdev, uint8_t CSW_Status)
} }
/** /**
* @brief MSC_BOT_Abort * @brief MSC_BOT_Abort
* Abort the current transfer * Abort the current transfer
* @param pdev: device instance * @param pdev: device instance
* @retval status * @retval status
*/ */
static void MSC_BOT_Abort(USBD_HandleTypeDef *pdev) static void MSC_BOT_Abort(USBD_HandleTypeDef *pdev)
{ {
USBD_MSC_BOT_HandleTypeDef *hmsc = (USBD_MSC_BOT_HandleTypeDef *)pdev->pClassData; USBD_MSC_BOT_HandleTypeDef *hmsc = (USBD_MSC_BOT_HandleTypeDef *)pdev->pClassData;
if (hmsc == NULL)
{
return;
}
if ((hmsc->cbw.bmFlags == 0U) && if ((hmsc->cbw.bmFlags == 0U) &&
(hmsc->cbw.dDataLength != 0U) && (hmsc->cbw.dDataLength != 0U) &&
(hmsc->bot_status == USBD_BOT_STATUS_NORMAL)) (hmsc->bot_status == USBD_BOT_STATUS_NORMAL))
@@ -344,17 +388,22 @@ static void MSC_BOT_Abort(USBD_HandleTypeDef *pdev)
} }
/** /**
* @brief MSC_BOT_CplClrFeature * @brief MSC_BOT_CplClrFeature
* Complete the clear feature request * Complete the clear feature request
* @param pdev: device instance * @param pdev: device instance
* @param epnum: endpoint index * @param epnum: endpoint index
* @retval None * @retval None
*/ */
void MSC_BOT_CplClrFeature(USBD_HandleTypeDef *pdev, uint8_t epnum) void MSC_BOT_CplClrFeature(USBD_HandleTypeDef *pdev, uint8_t epnum)
{ {
USBD_MSC_BOT_HandleTypeDef *hmsc = (USBD_MSC_BOT_HandleTypeDef *)pdev->pClassData; USBD_MSC_BOT_HandleTypeDef *hmsc = (USBD_MSC_BOT_HandleTypeDef *)pdev->pClassData;
if (hmsc == NULL)
{
return;
}
if (hmsc->bot_status == USBD_BOT_STATUS_ERROR) /* Bad CBW Signature */ if (hmsc->bot_status == USBD_BOT_STATUS_ERROR) /* Bad CBW Signature */
{ {
(void)USBD_LL_StallEP(pdev, MSC_EPIN_ADDR); (void)USBD_LL_StallEP(pdev, MSC_EPIN_ADDR);

View File

@@ -87,7 +87,7 @@ uint8_t MSC_Page80_Inquiry_Data[LENGTH_INQUIRY_PAGE80] =
0x20, 0x20,
0x20, 0x20,
0x20 0x20
}; };
/* USB Mass storage sense 6 Data */ /* USB Mass storage sense 6 Data */
uint8_t MSC_Mode_Sense6_data[MODE_SENSE6_LEN] = uint8_t MSC_Mode_Sense6_data[MODE_SENSE6_LEN] =

View File

@@ -111,85 +111,90 @@ static int8_t SCSI_UpdateBotData(USBD_MSC_BOT_HandleTypeDef *hmsc,
/** /**
* @brief SCSI_ProcessCmd * @brief SCSI_ProcessCmd
* Process SCSI commands * Process SCSI commands
* @param pdev: device instance * @param pdev: device instance
* @param lun: Logical unit number * @param lun: Logical unit number
* @param params: Command parameters * @param params: Command parameters
* @retval status * @retval status
*/ */
int8_t SCSI_ProcessCmd(USBD_HandleTypeDef *pdev, uint8_t lun, uint8_t *cmd) int8_t SCSI_ProcessCmd(USBD_HandleTypeDef *pdev, uint8_t lun, uint8_t *cmd)
{ {
int8_t ret; int8_t ret;
USBD_MSC_BOT_HandleTypeDef *hmsc = (USBD_MSC_BOT_HandleTypeDef *)pdev->pClassData; USBD_MSC_BOT_HandleTypeDef *hmsc = (USBD_MSC_BOT_HandleTypeDef *)pdev->pClassData;
if (hmsc == NULL)
{
return -1;
}
switch (cmd[0]) switch (cmd[0])
{ {
case SCSI_TEST_UNIT_READY: case SCSI_TEST_UNIT_READY:
ret = SCSI_TestUnitReady(pdev, lun, cmd); ret = SCSI_TestUnitReady(pdev, lun, cmd);
break; break;
case SCSI_REQUEST_SENSE: case SCSI_REQUEST_SENSE:
ret = SCSI_RequestSense(pdev, lun, cmd); ret = SCSI_RequestSense(pdev, lun, cmd);
break; break;
case SCSI_INQUIRY: case SCSI_INQUIRY:
ret = SCSI_Inquiry(pdev, lun, cmd); ret = SCSI_Inquiry(pdev, lun, cmd);
break; break;
case SCSI_START_STOP_UNIT: case SCSI_START_STOP_UNIT:
ret = SCSI_StartStopUnit(pdev, lun, cmd); ret = SCSI_StartStopUnit(pdev, lun, cmd);
break; break;
case SCSI_ALLOW_MEDIUM_REMOVAL: case SCSI_ALLOW_MEDIUM_REMOVAL:
ret = SCSI_AllowPreventRemovable(pdev, lun, cmd); ret = SCSI_AllowPreventRemovable(pdev, lun, cmd);
break; break;
case SCSI_MODE_SENSE6: case SCSI_MODE_SENSE6:
ret = SCSI_ModeSense6(pdev, lun, cmd); ret = SCSI_ModeSense6(pdev, lun, cmd);
break; break;
case SCSI_MODE_SENSE10: case SCSI_MODE_SENSE10:
ret = SCSI_ModeSense10(pdev, lun, cmd); ret = SCSI_ModeSense10(pdev, lun, cmd);
break; break;
case SCSI_READ_FORMAT_CAPACITIES: case SCSI_READ_FORMAT_CAPACITIES:
ret = SCSI_ReadFormatCapacity(pdev, lun, cmd); ret = SCSI_ReadFormatCapacity(pdev, lun, cmd);
break; break;
case SCSI_READ_CAPACITY10: case SCSI_READ_CAPACITY10:
ret = SCSI_ReadCapacity10(pdev, lun, cmd); ret = SCSI_ReadCapacity10(pdev, lun, cmd);
break; break;
case SCSI_READ_CAPACITY16: case SCSI_READ_CAPACITY16:
ret = SCSI_ReadCapacity16(pdev, lun, cmd); ret = SCSI_ReadCapacity16(pdev, lun, cmd);
break; break;
case SCSI_READ10: case SCSI_READ10:
ret = SCSI_Read10(pdev, lun, cmd); ret = SCSI_Read10(pdev, lun, cmd);
break; break;
case SCSI_READ12: case SCSI_READ12:
ret = SCSI_Read12(pdev, lun, cmd); ret = SCSI_Read12(pdev, lun, cmd);
break; break;
case SCSI_WRITE10: case SCSI_WRITE10:
ret = SCSI_Write10(pdev, lun, cmd); ret = SCSI_Write10(pdev, lun, cmd);
break; break;
case SCSI_WRITE12: case SCSI_WRITE12:
ret = SCSI_Write12(pdev, lun, cmd); ret = SCSI_Write12(pdev, lun, cmd);
break; break;
case SCSI_VERIFY10: case SCSI_VERIFY10:
ret = SCSI_Verify10(pdev, lun, cmd); ret = SCSI_Verify10(pdev, lun, cmd);
break; break;
default: default:
SCSI_SenseCode(pdev, lun, ILLEGAL_REQUEST, INVALID_CDB); SCSI_SenseCode(pdev, lun, ILLEGAL_REQUEST, INVALID_CDB);
hmsc->bot_status = USBD_BOT_STATUS_ERROR; hmsc->bot_status = USBD_BOT_STATUS_ERROR;
ret = -1; ret = -1;
break; break;
} }
return ret; return ret;
@@ -197,17 +202,22 @@ int8_t SCSI_ProcessCmd(USBD_HandleTypeDef *pdev, uint8_t lun, uint8_t *cmd)
/** /**
* @brief SCSI_TestUnitReady * @brief SCSI_TestUnitReady
* Process SCSI Test Unit Ready Command * Process SCSI Test Unit Ready Command
* @param lun: Logical unit number * @param lun: Logical unit number
* @param params: Command parameters * @param params: Command parameters
* @retval status * @retval status
*/ */
static int8_t SCSI_TestUnitReady(USBD_HandleTypeDef *pdev, uint8_t lun, uint8_t *params) static int8_t SCSI_TestUnitReady(USBD_HandleTypeDef *pdev, uint8_t lun, uint8_t *params)
{ {
UNUSED(params); UNUSED(params);
USBD_MSC_BOT_HandleTypeDef *hmsc = (USBD_MSC_BOT_HandleTypeDef *)pdev->pClassData; USBD_MSC_BOT_HandleTypeDef *hmsc = (USBD_MSC_BOT_HandleTypeDef *)pdev->pClassData;
if (hmsc == NULL)
{
return -1;
}
/* case 9 : Hi > D0 */ /* case 9 : Hi > D0 */
if (hmsc->cbw.dDataLength != 0U) if (hmsc->cbw.dDataLength != 0U)
{ {
@@ -237,18 +247,23 @@ static int8_t SCSI_TestUnitReady(USBD_HandleTypeDef *pdev, uint8_t lun, uint8_t
/** /**
* @brief SCSI_Inquiry * @brief SCSI_Inquiry
* Process Inquiry command * Process Inquiry command
* @param lun: Logical unit number * @param lun: Logical unit number
* @param params: Command parameters * @param params: Command parameters
* @retval status * @retval status
*/ */
static int8_t SCSI_Inquiry(USBD_HandleTypeDef *pdev, uint8_t lun, uint8_t *params) static int8_t SCSI_Inquiry(USBD_HandleTypeDef *pdev, uint8_t lun, uint8_t *params)
{ {
uint8_t *pPage; uint8_t *pPage;
uint16_t len; uint16_t len;
USBD_MSC_BOT_HandleTypeDef *hmsc = (USBD_MSC_BOT_HandleTypeDef *)pdev->pClassData; USBD_MSC_BOT_HandleTypeDef *hmsc = (USBD_MSC_BOT_HandleTypeDef *)pdev->pClassData;
if (hmsc == NULL)
{
return -1;
}
if (hmsc->cbw.dDataLength == 0U) if (hmsc->cbw.dDataLength == 0U)
{ {
SCSI_SenseCode(pdev, hmsc->cbw.bLUN, ILLEGAL_REQUEST, INVALID_CDB); SCSI_SenseCode(pdev, hmsc->cbw.bLUN, ILLEGAL_REQUEST, INVALID_CDB);
@@ -275,7 +290,7 @@ static int8_t SCSI_Inquiry(USBD_HandleTypeDef *pdev, uint8_t lun, uint8_t *param
} }
else else
{ {
pPage = (uint8_t *)&((USBD_StorageTypeDef *)pdev->pUserData)->pInquiry[lun * STANDARD_INQUIRY_DATA_LEN]; pPage = (uint8_t *) &((USBD_StorageTypeDef *)pdev->pUserData)->pInquiry[lun * STANDARD_INQUIRY_DATA_LEN];
len = (uint16_t)pPage[4] + 5U; len = (uint16_t)pPage[4] + 5U;
if (params[4] <= len) if (params[4] <= len)
@@ -291,18 +306,23 @@ static int8_t SCSI_Inquiry(USBD_HandleTypeDef *pdev, uint8_t lun, uint8_t *param
/** /**
* @brief SCSI_ReadCapacity10 * @brief SCSI_ReadCapacity10
* Process Read Capacity 10 command * Process Read Capacity 10 command
* @param lun: Logical unit number * @param lun: Logical unit number
* @param params: Command parameters * @param params: Command parameters
* @retval status * @retval status
*/ */
static int8_t SCSI_ReadCapacity10(USBD_HandleTypeDef *pdev, uint8_t lun, uint8_t *params) static int8_t SCSI_ReadCapacity10(USBD_HandleTypeDef *pdev, uint8_t lun, uint8_t *params)
{ {
UNUSED(params); UNUSED(params);
int8_t ret; int8_t ret;
USBD_MSC_BOT_HandleTypeDef *hmsc = (USBD_MSC_BOT_HandleTypeDef *)pdev->pClassData; USBD_MSC_BOT_HandleTypeDef *hmsc = (USBD_MSC_BOT_HandleTypeDef *)pdev->pClassData;
if (hmsc == NULL)
{
return -1;
}
ret = ((USBD_StorageTypeDef *)pdev->pUserData)->GetCapacity(lun, &hmsc->scsi_blk_nbr, &hmsc->scsi_blk_size); ret = ((USBD_StorageTypeDef *)pdev->pUserData)->GetCapacity(lun, &hmsc->scsi_blk_nbr, &hmsc->scsi_blk_size);
if ((ret != 0) || (hmsc->scsi_medium_state == SCSI_MEDIUM_EJECTED)) if ((ret != 0) || (hmsc->scsi_medium_state == SCSI_MEDIUM_EJECTED))
@@ -329,12 +349,12 @@ static int8_t SCSI_ReadCapacity10(USBD_HandleTypeDef *pdev, uint8_t lun, uint8_t
/** /**
* @brief SCSI_ReadCapacity16 * @brief SCSI_ReadCapacity16
* Process Read Capacity 16 command * Process Read Capacity 16 command
* @param lun: Logical unit number * @param lun: Logical unit number
* @param params: Command parameters * @param params: Command parameters
* @retval status * @retval status
*/ */
static int8_t SCSI_ReadCapacity16(USBD_HandleTypeDef *pdev, uint8_t lun, uint8_t *params) static int8_t SCSI_ReadCapacity16(USBD_HandleTypeDef *pdev, uint8_t lun, uint8_t *params)
{ {
UNUSED(params); UNUSED(params);
@@ -342,6 +362,11 @@ static int8_t SCSI_ReadCapacity16(USBD_HandleTypeDef *pdev, uint8_t lun, uint8_t
int8_t ret; int8_t ret;
USBD_MSC_BOT_HandleTypeDef *hmsc = (USBD_MSC_BOT_HandleTypeDef *)pdev->pClassData; USBD_MSC_BOT_HandleTypeDef *hmsc = (USBD_MSC_BOT_HandleTypeDef *)pdev->pClassData;
if (hmsc == NULL)
{
return -1;
}
ret = ((USBD_StorageTypeDef *)pdev->pUserData)->GetCapacity(lun, &hmsc->scsi_blk_nbr, &hmsc->scsi_blk_size); ret = ((USBD_StorageTypeDef *)pdev->pUserData)->GetCapacity(lun, &hmsc->scsi_blk_nbr, &hmsc->scsi_blk_size);
if ((ret != 0) || (hmsc->scsi_medium_state == SCSI_MEDIUM_EJECTED)) if ((ret != 0) || (hmsc->scsi_medium_state == SCSI_MEDIUM_EJECTED))
@@ -353,7 +378,7 @@ static int8_t SCSI_ReadCapacity16(USBD_HandleTypeDef *pdev, uint8_t lun, uint8_t
hmsc->bot_data_length = ((uint32_t)params[10] << 24) | hmsc->bot_data_length = ((uint32_t)params[10] << 24) |
((uint32_t)params[11] << 16) | ((uint32_t)params[11] << 16) |
((uint32_t)params[12] << 8) | ((uint32_t)params[12] << 8) |
(uint32_t)params[13]; (uint32_t)params[13];
for (idx = 0U; idx < hmsc->bot_data_length; idx++) for (idx = 0U; idx < hmsc->bot_data_length; idx++)
{ {
@@ -373,19 +398,19 @@ static int8_t SCSI_ReadCapacity16(USBD_HandleTypeDef *pdev, uint8_t lun, uint8_t
hmsc->bot_data_length = ((uint32_t)params[10] << 24) | hmsc->bot_data_length = ((uint32_t)params[10] << 24) |
((uint32_t)params[11] << 16) | ((uint32_t)params[11] << 16) |
((uint32_t)params[12] << 8) | ((uint32_t)params[12] << 8) |
(uint32_t)params[13]; (uint32_t)params[13];
return 0; return 0;
} }
/** /**
* @brief SCSI_ReadFormatCapacity * @brief SCSI_ReadFormatCapacity
* Process Read Format Capacity command * Process Read Format Capacity command
* @param lun: Logical unit number * @param lun: Logical unit number
* @param params: Command parameters * @param params: Command parameters
* @retval status * @retval status
*/ */
static int8_t SCSI_ReadFormatCapacity(USBD_HandleTypeDef *pdev, uint8_t lun, uint8_t *params) static int8_t SCSI_ReadFormatCapacity(USBD_HandleTypeDef *pdev, uint8_t lun, uint8_t *params)
{ {
UNUSED(params); UNUSED(params);
@@ -395,6 +420,11 @@ static int8_t SCSI_ReadFormatCapacity(USBD_HandleTypeDef *pdev, uint8_t lun, uin
int8_t ret; int8_t ret;
USBD_MSC_BOT_HandleTypeDef *hmsc = (USBD_MSC_BOT_HandleTypeDef *)pdev->pClassData; USBD_MSC_BOT_HandleTypeDef *hmsc = (USBD_MSC_BOT_HandleTypeDef *)pdev->pClassData;
if (hmsc == NULL)
{
return -1;
}
ret = ((USBD_StorageTypeDef *)pdev->pUserData)->GetCapacity(lun, &blk_nbr, &blk_size); ret = ((USBD_StorageTypeDef *)pdev->pUserData)->GetCapacity(lun, &blk_nbr, &blk_size);
if ((ret != 0) || (hmsc->scsi_medium_state == SCSI_MEDIUM_EJECTED)) if ((ret != 0) || (hmsc->scsi_medium_state == SCSI_MEDIUM_EJECTED))
@@ -426,18 +456,23 @@ static int8_t SCSI_ReadFormatCapacity(USBD_HandleTypeDef *pdev, uint8_t lun, uin
/** /**
* @brief SCSI_ModeSense6 * @brief SCSI_ModeSense6
* Process Mode Sense6 command * Process Mode Sense6 command
* @param lun: Logical unit number * @param lun: Logical unit number
* @param params: Command parameters * @param params: Command parameters
* @retval status * @retval status
*/ */
static int8_t SCSI_ModeSense6(USBD_HandleTypeDef *pdev, uint8_t lun, uint8_t *params) static int8_t SCSI_ModeSense6(USBD_HandleTypeDef *pdev, uint8_t lun, uint8_t *params)
{ {
UNUSED(lun); UNUSED(lun);
USBD_MSC_BOT_HandleTypeDef *hmsc = (USBD_MSC_BOT_HandleTypeDef *)pdev->pClassData; USBD_MSC_BOT_HandleTypeDef *hmsc = (USBD_MSC_BOT_HandleTypeDef *)pdev->pClassData;
uint16_t len = MODE_SENSE6_LEN; uint16_t len = MODE_SENSE6_LEN;
if (hmsc == NULL)
{
return -1;
}
if (params[4] <= len) if (params[4] <= len)
{ {
len = params[4]; len = params[4];
@@ -450,18 +485,23 @@ static int8_t SCSI_ModeSense6(USBD_HandleTypeDef *pdev, uint8_t lun, uint8_t *pa
/** /**
* @brief SCSI_ModeSense10 * @brief SCSI_ModeSense10
* Process Mode Sense10 command * Process Mode Sense10 command
* @param lun: Logical unit number * @param lun: Logical unit number
* @param params: Command parameters * @param params: Command parameters
* @retval status * @retval status
*/ */
static int8_t SCSI_ModeSense10(USBD_HandleTypeDef *pdev, uint8_t lun, uint8_t *params) static int8_t SCSI_ModeSense10(USBD_HandleTypeDef *pdev, uint8_t lun, uint8_t *params)
{ {
UNUSED(lun); UNUSED(lun);
USBD_MSC_BOT_HandleTypeDef *hmsc = (USBD_MSC_BOT_HandleTypeDef *)pdev->pClassData; USBD_MSC_BOT_HandleTypeDef *hmsc = (USBD_MSC_BOT_HandleTypeDef *)pdev->pClassData;
uint16_t len = MODE_SENSE10_LEN; uint16_t len = MODE_SENSE10_LEN;
if (hmsc == NULL)
{
return -1;
}
if (params[8] <= len) if (params[8] <= len)
{ {
len = params[8]; len = params[8];
@@ -474,18 +514,23 @@ static int8_t SCSI_ModeSense10(USBD_HandleTypeDef *pdev, uint8_t lun, uint8_t *p
/** /**
* @brief SCSI_RequestSense * @brief SCSI_RequestSense
* Process Request Sense command * Process Request Sense command
* @param lun: Logical unit number * @param lun: Logical unit number
* @param params: Command parameters * @param params: Command parameters
* @retval status * @retval status
*/ */
static int8_t SCSI_RequestSense(USBD_HandleTypeDef *pdev, uint8_t lun, uint8_t *params) static int8_t SCSI_RequestSense(USBD_HandleTypeDef *pdev, uint8_t lun, uint8_t *params)
{ {
UNUSED(lun); UNUSED(lun);
uint8_t i; uint8_t i;
USBD_MSC_BOT_HandleTypeDef *hmsc = (USBD_MSC_BOT_HandleTypeDef *)pdev->pClassData; USBD_MSC_BOT_HandleTypeDef *hmsc = (USBD_MSC_BOT_HandleTypeDef *)pdev->pClassData;
if (hmsc == NULL)
{
return -1;
}
if (hmsc->cbw.dDataLength == 0U) if (hmsc->cbw.dDataLength == 0U)
{ {
SCSI_SenseCode(pdev, hmsc->cbw.bLUN, ILLEGAL_REQUEST, INVALID_CDB); SCSI_SenseCode(pdev, hmsc->cbw.bLUN, ILLEGAL_REQUEST, INVALID_CDB);
@@ -525,19 +570,24 @@ static int8_t SCSI_RequestSense(USBD_HandleTypeDef *pdev, uint8_t lun, uint8_t *
/** /**
* @brief SCSI_SenseCode * @brief SCSI_SenseCode
* Load the last error code in the error list * Load the last error code in the error list
* @param lun: Logical unit number * @param lun: Logical unit number
* @param sKey: Sense Key * @param sKey: Sense Key
* @param ASC: Additional Sense Code * @param ASC: Additional Sense Code
* @retval none * @retval none
*/ */
void SCSI_SenseCode(USBD_HandleTypeDef *pdev, uint8_t lun, uint8_t sKey, uint8_t ASC) void SCSI_SenseCode(USBD_HandleTypeDef *pdev, uint8_t lun, uint8_t sKey, uint8_t ASC)
{ {
UNUSED(lun); UNUSED(lun);
USBD_MSC_BOT_HandleTypeDef *hmsc = (USBD_MSC_BOT_HandleTypeDef *)pdev->pClassData; USBD_MSC_BOT_HandleTypeDef *hmsc = (USBD_MSC_BOT_HandleTypeDef *)pdev->pClassData;
if (hmsc == NULL)
{
return;
}
hmsc->scsi_sense[hmsc->scsi_sense_tail].Skey = sKey; hmsc->scsi_sense[hmsc->scsi_sense_tail].Skey = sKey;
hmsc->scsi_sense[hmsc->scsi_sense_tail].w.b.ASC = ASC; hmsc->scsi_sense[hmsc->scsi_sense_tail].w.b.ASC = ASC;
hmsc->scsi_sense[hmsc->scsi_sense_tail].w.b.ASCQ = 0U; hmsc->scsi_sense[hmsc->scsi_sense_tail].w.b.ASCQ = 0U;
@@ -551,17 +601,22 @@ void SCSI_SenseCode(USBD_HandleTypeDef *pdev, uint8_t lun, uint8_t sKey, uint8_t
/** /**
* @brief SCSI_StartStopUnit * @brief SCSI_StartStopUnit
* Process Start Stop Unit command * Process Start Stop Unit command
* @param lun: Logical unit number * @param lun: Logical unit number
* @param params: Command parameters * @param params: Command parameters
* @retval status * @retval status
*/ */
static int8_t SCSI_StartStopUnit(USBD_HandleTypeDef *pdev, uint8_t lun, uint8_t *params) static int8_t SCSI_StartStopUnit(USBD_HandleTypeDef *pdev, uint8_t lun, uint8_t *params)
{ {
UNUSED(lun); UNUSED(lun);
USBD_MSC_BOT_HandleTypeDef *hmsc = (USBD_MSC_BOT_HandleTypeDef *)pdev->pClassData; USBD_MSC_BOT_HandleTypeDef *hmsc = (USBD_MSC_BOT_HandleTypeDef *)pdev->pClassData;
if (hmsc == NULL)
{
return -1;
}
if ((hmsc->scsi_medium_state == SCSI_MEDIUM_LOCKED) && ((params[4] & 0x3U) == 2U)) if ((hmsc->scsi_medium_state == SCSI_MEDIUM_LOCKED) && ((params[4] & 0x3U) == 2U))
{ {
SCSI_SenseCode(pdev, lun, ILLEGAL_REQUEST, INVALID_FIELED_IN_COMMAND); SCSI_SenseCode(pdev, lun, ILLEGAL_REQUEST, INVALID_FIELED_IN_COMMAND);
@@ -592,17 +647,22 @@ static int8_t SCSI_StartStopUnit(USBD_HandleTypeDef *pdev, uint8_t lun, uint8_t
/** /**
* @brief SCSI_AllowPreventRemovable * @brief SCSI_AllowPreventRemovable
* Process Allow Prevent Removable medium command * Process Allow Prevent Removable medium command
* @param lun: Logical unit number * @param lun: Logical unit number
* @param params: Command parameters * @param params: Command parameters
* @retval status * @retval status
*/ */
static int8_t SCSI_AllowPreventRemovable(USBD_HandleTypeDef *pdev, uint8_t lun, uint8_t *params) static int8_t SCSI_AllowPreventRemovable(USBD_HandleTypeDef *pdev, uint8_t lun, uint8_t *params)
{ {
UNUSED(lun); UNUSED(lun);
USBD_MSC_BOT_HandleTypeDef *hmsc = (USBD_MSC_BOT_HandleTypeDef *)pdev->pClassData; USBD_MSC_BOT_HandleTypeDef *hmsc = (USBD_MSC_BOT_HandleTypeDef *)pdev->pClassData;
if (hmsc == NULL)
{
return -1;
}
if (params[4] == 0U) if (params[4] == 0U)
{ {
hmsc->scsi_medium_state = SCSI_MEDIUM_UNLOCKED; hmsc->scsi_medium_state = SCSI_MEDIUM_UNLOCKED;
@@ -619,16 +679,21 @@ static int8_t SCSI_AllowPreventRemovable(USBD_HandleTypeDef *pdev, uint8_t lun,
/** /**
* @brief SCSI_Read10 * @brief SCSI_Read10
* Process Read10 command * Process Read10 command
* @param lun: Logical unit number * @param lun: Logical unit number
* @param params: Command parameters * @param params: Command parameters
* @retval status * @retval status
*/ */
static int8_t SCSI_Read10(USBD_HandleTypeDef *pdev, uint8_t lun, uint8_t *params) static int8_t SCSI_Read10(USBD_HandleTypeDef *pdev, uint8_t lun, uint8_t *params)
{ {
USBD_MSC_BOT_HandleTypeDef *hmsc = (USBD_MSC_BOT_HandleTypeDef *)pdev->pClassData; USBD_MSC_BOT_HandleTypeDef *hmsc = (USBD_MSC_BOT_HandleTypeDef *)pdev->pClassData;
if (hmsc == NULL)
{
return -1;
}
if (hmsc->bot_state == USBD_BOT_IDLE) /* Idle */ if (hmsc->bot_state == USBD_BOT_IDLE) /* Idle */
{ {
/* case 10 : Ho <> Di */ /* case 10 : Ho <> Di */
@@ -680,16 +745,21 @@ static int8_t SCSI_Read10(USBD_HandleTypeDef *pdev, uint8_t lun, uint8_t *params
/** /**
* @brief SCSI_Read12 * @brief SCSI_Read12
* Process Read12 command * Process Read12 command
* @param lun: Logical unit number * @param lun: Logical unit number
* @param params: Command parameters * @param params: Command parameters
* @retval status * @retval status
*/ */
static int8_t SCSI_Read12(USBD_HandleTypeDef *pdev, uint8_t lun, uint8_t *params) static int8_t SCSI_Read12(USBD_HandleTypeDef *pdev, uint8_t lun, uint8_t *params)
{ {
USBD_MSC_BOT_HandleTypeDef *hmsc = (USBD_MSC_BOT_HandleTypeDef *)pdev->pClassData; USBD_MSC_BOT_HandleTypeDef *hmsc = (USBD_MSC_BOT_HandleTypeDef *)pdev->pClassData;
if (hmsc == NULL)
{
return -1;
}
if (hmsc->bot_state == USBD_BOT_IDLE) /* Idle */ if (hmsc->bot_state == USBD_BOT_IDLE) /* Idle */
{ {
/* case 10 : Ho <> Di */ /* case 10 : Ho <> Di */
@@ -743,17 +813,22 @@ static int8_t SCSI_Read12(USBD_HandleTypeDef *pdev, uint8_t lun, uint8_t *params
/** /**
* @brief SCSI_Write10 * @brief SCSI_Write10
* Process Write10 command * Process Write10 command
* @param lun: Logical unit number * @param lun: Logical unit number
* @param params: Command parameters * @param params: Command parameters
* @retval status * @retval status
*/ */
static int8_t SCSI_Write10(USBD_HandleTypeDef *pdev, uint8_t lun, uint8_t *params) static int8_t SCSI_Write10(USBD_HandleTypeDef *pdev, uint8_t lun, uint8_t *params)
{ {
USBD_MSC_BOT_HandleTypeDef *hmsc = (USBD_MSC_BOT_HandleTypeDef *)pdev->pClassData; USBD_MSC_BOT_HandleTypeDef *hmsc = (USBD_MSC_BOT_HandleTypeDef *)pdev->pClassData;
uint32_t len; uint32_t len;
if (hmsc == NULL)
{
return -1;
}
if (hmsc->bot_state == USBD_BOT_IDLE) /* Idle */ if (hmsc->bot_state == USBD_BOT_IDLE) /* Idle */
{ {
if (hmsc->cbw.dDataLength == 0U) if (hmsc->cbw.dDataLength == 0U)
@@ -823,17 +898,22 @@ static int8_t SCSI_Write10(USBD_HandleTypeDef *pdev, uint8_t lun, uint8_t *param
/** /**
* @brief SCSI_Write12 * @brief SCSI_Write12
* Process Write12 command * Process Write12 command
* @param lun: Logical unit number * @param lun: Logical unit number
* @param params: Command parameters * @param params: Command parameters
* @retval status * @retval status
*/ */
static int8_t SCSI_Write12(USBD_HandleTypeDef *pdev, uint8_t lun, uint8_t *params) static int8_t SCSI_Write12(USBD_HandleTypeDef *pdev, uint8_t lun, uint8_t *params)
{ {
USBD_MSC_BOT_HandleTypeDef *hmsc = (USBD_MSC_BOT_HandleTypeDef *)pdev->pClassData; USBD_MSC_BOT_HandleTypeDef *hmsc = (USBD_MSC_BOT_HandleTypeDef *)pdev->pClassData;
uint32_t len; uint32_t len;
if (hmsc == NULL)
{
return -1;
}
if (hmsc->bot_state == USBD_BOT_IDLE) /* Idle */ if (hmsc->bot_state == USBD_BOT_IDLE) /* Idle */
{ {
if (hmsc->cbw.dDataLength == 0U) if (hmsc->cbw.dDataLength == 0U)
@@ -907,16 +987,21 @@ static int8_t SCSI_Write12(USBD_HandleTypeDef *pdev, uint8_t lun, uint8_t *param
/** /**
* @brief SCSI_Verify10 * @brief SCSI_Verify10
* Process Verify10 command * Process Verify10 command
* @param lun: Logical unit number * @param lun: Logical unit number
* @param params: Command parameters * @param params: Command parameters
* @retval status * @retval status
*/ */
static int8_t SCSI_Verify10(USBD_HandleTypeDef *pdev, uint8_t lun, uint8_t *params) static int8_t SCSI_Verify10(USBD_HandleTypeDef *pdev, uint8_t lun, uint8_t *params)
{ {
USBD_MSC_BOT_HandleTypeDef *hmsc = (USBD_MSC_BOT_HandleTypeDef *)pdev->pClassData; USBD_MSC_BOT_HandleTypeDef *hmsc = (USBD_MSC_BOT_HandleTypeDef *)pdev->pClassData;
if (hmsc == NULL)
{
return -1;
}
if ((params[1] & 0x02U) == 0x02U) if ((params[1] & 0x02U) == 0x02U)
{ {
SCSI_SenseCode(pdev, lun, ILLEGAL_REQUEST, INVALID_FIELED_IN_COMMAND); SCSI_SenseCode(pdev, lun, ILLEGAL_REQUEST, INVALID_FIELED_IN_COMMAND);
@@ -934,18 +1019,23 @@ static int8_t SCSI_Verify10(USBD_HandleTypeDef *pdev, uint8_t lun, uint8_t *para
} }
/** /**
* @brief SCSI_CheckAddressRange * @brief SCSI_CheckAddressRange
* Check address range * Check address range
* @param lun: Logical unit number * @param lun: Logical unit number
* @param blk_offset: first block address * @param blk_offset: first block address
* @param blk_nbr: number of block to be processed * @param blk_nbr: number of block to be processed
* @retval status * @retval status
*/ */
static int8_t SCSI_CheckAddressRange(USBD_HandleTypeDef *pdev, uint8_t lun, static int8_t SCSI_CheckAddressRange(USBD_HandleTypeDef *pdev, uint8_t lun,
uint32_t blk_offset, uint32_t blk_nbr) uint32_t blk_offset, uint32_t blk_nbr)
{ {
USBD_MSC_BOT_HandleTypeDef *hmsc = (USBD_MSC_BOT_HandleTypeDef *)pdev->pClassData; USBD_MSC_BOT_HandleTypeDef *hmsc = (USBD_MSC_BOT_HandleTypeDef *)pdev->pClassData;
if (hmsc == NULL)
{
return -1;
}
if ((blk_offset + blk_nbr) > hmsc->scsi_blk_nbr) if ((blk_offset + blk_nbr) > hmsc->scsi_blk_nbr)
{ {
SCSI_SenseCode(pdev, lun, ILLEGAL_REQUEST, ADDRESS_OUT_OF_RANGE); SCSI_SenseCode(pdev, lun, ILLEGAL_REQUEST, ADDRESS_OUT_OF_RANGE);
@@ -956,16 +1046,21 @@ static int8_t SCSI_CheckAddressRange(USBD_HandleTypeDef *pdev, uint8_t lun,
} }
/** /**
* @brief SCSI_ProcessRead * @brief SCSI_ProcessRead
* Handle Read Process * Handle Read Process
* @param lun: Logical unit number * @param lun: Logical unit number
* @retval status * @retval status
*/ */
static int8_t SCSI_ProcessRead(USBD_HandleTypeDef *pdev, uint8_t lun) static int8_t SCSI_ProcessRead(USBD_HandleTypeDef *pdev, uint8_t lun)
{ {
USBD_MSC_BOT_HandleTypeDef *hmsc = (USBD_MSC_BOT_HandleTypeDef *)pdev->pClassData; USBD_MSC_BOT_HandleTypeDef *hmsc = (USBD_MSC_BOT_HandleTypeDef *)pdev->pClassData;
uint32_t len = hmsc->scsi_blk_len * hmsc->scsi_blk_size; uint32_t len = hmsc->scsi_blk_len * hmsc->scsi_blk_size;
if (hmsc == NULL)
{
return -1;
}
len = MIN(len, MSC_MEDIA_PACKET); len = MIN(len, MSC_MEDIA_PACKET);
if (((USBD_StorageTypeDef *)pdev->pUserData)->Read(lun, hmsc->bot_data, if (((USBD_StorageTypeDef *)pdev->pUserData)->Read(lun, hmsc->bot_data,
@@ -993,16 +1088,21 @@ static int8_t SCSI_ProcessRead(USBD_HandleTypeDef *pdev, uint8_t lun)
} }
/** /**
* @brief SCSI_ProcessWrite * @brief SCSI_ProcessWrite
* Handle Write Process * Handle Write Process
* @param lun: Logical unit number * @param lun: Logical unit number
* @retval status * @retval status
*/ */
static int8_t SCSI_ProcessWrite(USBD_HandleTypeDef *pdev, uint8_t lun) static int8_t SCSI_ProcessWrite(USBD_HandleTypeDef *pdev, uint8_t lun)
{ {
USBD_MSC_BOT_HandleTypeDef *hmsc = (USBD_MSC_BOT_HandleTypeDef *)pdev->pClassData; USBD_MSC_BOT_HandleTypeDef *hmsc = (USBD_MSC_BOT_HandleTypeDef *)pdev->pClassData;
uint32_t len = hmsc->scsi_blk_len * hmsc->scsi_blk_size; uint32_t len = hmsc->scsi_blk_len * hmsc->scsi_blk_size;
if (hmsc == NULL)
{
return -1;
}
len = MIN(len, MSC_MEDIA_PACKET); len = MIN(len, MSC_MEDIA_PACKET);
if (((USBD_StorageTypeDef *)pdev->pUserData)->Write(lun, hmsc->bot_data, if (((USBD_StorageTypeDef *)pdev->pUserData)->Write(lun, hmsc->bot_data,
@@ -1036,18 +1136,23 @@ static int8_t SCSI_ProcessWrite(USBD_HandleTypeDef *pdev, uint8_t lun)
/** /**
* @brief SCSI_UpdateBotData * @brief SCSI_UpdateBotData
* fill the requested Data to transmit buffer * fill the requested Data to transmit buffer
* @param hmsc handler * @param hmsc handler
* @param params: Data buffer * @param pBuff: Data buffer
* @param length: Data length * @param length: Data length
* @retval status * @retval status
*/ */
static int8_t SCSI_UpdateBotData(USBD_MSC_BOT_HandleTypeDef *hmsc, static int8_t SCSI_UpdateBotData(USBD_MSC_BOT_HandleTypeDef *hmsc,
uint8_t *pBuff, uint16_t length) uint8_t *pBuff, uint16_t length)
{ {
uint16_t len = length; uint16_t len = length;
if (hmsc == NULL)
{
return -1;
}
hmsc->bot_data_length = len; hmsc->bot_data_length = len;
while (len != 0U) while (len != 0U)

View File

@@ -88,24 +88,24 @@ USBD_StorageTypeDef USBD_MSC_Template_fops =
}; };
/******************************************************************************* /*******************************************************************************
* Function Name : Read_Memory * Function Name : Read_Memory
* Description : Handle the Read operation from the microSD card. * Description : Handle the Read operation from the microSD card.
* Input : None. * Input : None.
* Output : None. * Output : None.
* Return : None. * Return : None.
*******************************************************************************/ *******************************************************************************/
int8_t STORAGE_Init(uint8_t lun) int8_t STORAGE_Init(uint8_t lun)
{ {
return (0); return (0);
} }
/******************************************************************************* /*******************************************************************************
* Function Name : Read_Memory * Function Name : Read_Memory
* Description : Handle the Read operation from the STORAGE card. * Description : Handle the Read operation from the STORAGE card.
* Input : None. * Input : None.
* Output : None. * Output : None.
* Return : None. * Return : None.
*******************************************************************************/ *******************************************************************************/
int8_t STORAGE_GetCapacity(uint8_t lun, uint32_t *block_num, uint16_t *block_size) int8_t STORAGE_GetCapacity(uint8_t lun, uint32_t *block_num, uint16_t *block_size)
{ {
*block_num = STORAGE_BLK_NBR; *block_num = STORAGE_BLK_NBR;
@@ -114,60 +114,60 @@ int8_t STORAGE_GetCapacity(uint8_t lun, uint32_t *block_num, uint16_t *block_siz
} }
/******************************************************************************* /*******************************************************************************
* Function Name : Read_Memory * Function Name : Read_Memory
* Description : Handle the Read operation from the STORAGE card. * Description : Handle the Read operation from the STORAGE card.
* Input : None. * Input : None.
* Output : None. * Output : None.
* Return : None. * Return : None.
*******************************************************************************/ *******************************************************************************/
int8_t STORAGE_IsReady(uint8_t lun) int8_t STORAGE_IsReady(uint8_t lun)
{ {
return (0); return (0);
} }
/******************************************************************************* /*******************************************************************************
* Function Name : Read_Memory * Function Name : Read_Memory
* Description : Handle the Read operation from the STORAGE card. * Description : Handle the Read operation from the STORAGE card.
* Input : None. * Input : None.
* Output : None. * Output : None.
* Return : None. * Return : None.
*******************************************************************************/ *******************************************************************************/
int8_t STORAGE_IsWriteProtected(uint8_t lun) int8_t STORAGE_IsWriteProtected(uint8_t lun)
{ {
return 0; return 0;
} }
/******************************************************************************* /*******************************************************************************
* Function Name : Read_Memory * Function Name : Read_Memory
* Description : Handle the Read operation from the STORAGE card. * Description : Handle the Read operation from the STORAGE card.
* Input : None. * Input : None.
* Output : None. * Output : None.
* Return : None. * Return : None.
*******************************************************************************/ *******************************************************************************/
int8_t STORAGE_Read(uint8_t lun, uint8_t *buf, int8_t STORAGE_Read(uint8_t lun, uint8_t *buf,
uint32_t blk_addr, uint16_t blk_len) uint32_t blk_addr, uint16_t blk_len)
{ {
return 0; return 0;
} }
/******************************************************************************* /*******************************************************************************
* Function Name : Write_Memory * Function Name : Write_Memory
* Description : Handle the Write operation to the STORAGE card. * Description : Handle the Write operation to the STORAGE card.
* Input : None. * Input : None.
* Output : None. * Output : None.
* Return : None. * Return : None.
*******************************************************************************/ *******************************************************************************/
int8_t STORAGE_Write(uint8_t lun, uint8_t *buf, int8_t STORAGE_Write(uint8_t lun, uint8_t *buf,
uint32_t blk_addr, uint16_t blk_len) uint32_t blk_addr, uint16_t blk_len)
{ {
return (0); return (0);
} }
/******************************************************************************* /*******************************************************************************
* Function Name : Write_Memory * Function Name : Write_Memory
* Description : Handle the Write operation to the STORAGE card. * Description : Handle the Write operation to the STORAGE card.
* Input : None. * Input : None.
* Output : None. * Output : None.
* Return : None. * Return : None.
*******************************************************************************/ *******************************************************************************/
int8_t STORAGE_GetMaxLun(void) int8_t STORAGE_GetMaxLun(void)
{ {
return (STORAGE_LUN_NBR - 1); return (STORAGE_LUN_NBR - 1);

View File

@@ -0,0 +1,164 @@
/**
******************************************************************************
* @file usbd_printer.h
* @author MCD Application Team
* @brief header file for the usbd_printer.c file.
******************************************************************************
* @attention
*
* <h2><center>&copy; Copyright (c) 2021 STMicroelectronics.
* All rights reserved.</center></h2>
*
* This software component is licensed by ST under Ultimate Liberty license
* SLA0044, the "License"; You may not use this file except in compliance with
* the License. You may obtain a copy of the License at:
* www.st.com/SLA0044
*
******************************************************************************
*/
/* Define to prevent recursive inclusion -------------------------------------*/
#ifndef __USB_PRNT_H
#define __USB_PRNT_H
#ifdef __cplusplus
extern "C" {
#endif
/* Includes ------------------------------------------------------------------*/
#include "usbd_ioreq.h"
/** @addtogroup STM32_USB_DEVICE_LIBRARY
* @{
*/
/** @defgroup usbd_PRNT
* @brief This file is the Header file for usbd_PRNT.c
* @{
*/
/** @defgroup usbd_PRNT_Exported_Defines
* @{
*/
#ifndef PRNT_IN_EP
#define PRNT_IN_EP 0x81U /* Default: EP1 for data IN */
#endif /* PRNT_IN_EP */
#ifndef PRNT_OUT_EP
#define PRNT_OUT_EP 0x01U /* Default: EP1 for data OUT */
#endif /* PRNT_OUT_EP */
#ifndef PRNT_DATA_HS_MAX_PACKET_SIZE
#define PRNT_DATA_HS_MAX_PACKET_SIZE 512U /* Endpoint IN & OUT Packet size */
#endif /* PRNT_DATA_HS_MAX_PACKET_SIZE */
#ifndef PRNT_DATA_FS_MAX_PACKET_SIZE
#define PRNT_DATA_FS_MAX_PACKET_SIZE 64U /* Endpoint IN & OUT Packet size */
#endif /* PRNT_DATA_FS_MAX_PACKET_SIZE */
#define USB_PRNT_CONFIG_DESC_SIZ 32U
#define PRNT_DATA_HS_IN_PACKET_SIZE PRNT_DATA_HS_MAX_PACKET_SIZE
#define PRNT_DATA_HS_OUT_PACKET_SIZE PRNT_DATA_HS_MAX_PACKET_SIZE
#define PRNT_DATA_FS_IN_PACKET_SIZE PRNT_DATA_FS_MAX_PACKET_SIZE
#define PRNT_DATA_FS_OUT_PACKET_SIZE PRNT_DATA_FS_MAX_PACKET_SIZE
/*---------------------------------------------------------------------*/
/* PRNT definitions */
/*---------------------------------------------------------------------*/
#define PRNT_STATUS_PAPER_EMPTY 0x10U
#define PRNT_STATUS_SELECTED 0x08U
#define PRNT_STATUS_NO_ERROR 0x00U
#define USB_PRNT_SUBCLASS 0x01U
#define USB_PRNT_UNIDIRECTIONAL 0x01U
#define USB_PRNT_BIDIRECTIONAL 0x02U
/* USB PRNT Request types */
#define PRNT_GET_DEVICE_ID 0x00U
#define PRNT_GET_PORT_STATUS 0x01U
#define PRNT_SOFT_RESET 0x02U
/**
* @}
*/
/** @defgroup USBD_CORE_Exported_TypesDefinitions
* @{
*/
/**
* @}
*/
typedef struct _USBD_PRNT_Itf
{
int8_t (* Init)(void);
int8_t (* DeInit)(void);
int8_t (* Control_req)(uint8_t req, uint8_t *pbuf, uint16_t *length);
int8_t (* Receive)(uint8_t *Buf, uint32_t *Len);
} USBD_PRNT_ItfTypeDef;
typedef struct
{
uint32_t data[PRNT_DATA_HS_MAX_PACKET_SIZE / 4U]; /* Force 32-bit alignment */
uint8_t CmdOpCode;
uint8_t CmdLength;
uint8_t *RxBuffer;
uint8_t *TxBuffer;
uint32_t RxLength;
uint32_t TxLength;
__IO uint32_t TxState;
__IO uint32_t RxState;
}
USBD_PRNT_HandleTypeDef;
/** @defgroup USBD_CORE_Exported_Macros
* @{
*/
/**
* @}
*/
/** @defgroup USBD_CORE_Exported_Variables
* @{
*/
extern USBD_ClassTypeDef USBD_PRNT;
#define USBD_PRNT_CLASS &USBD_PRNT
/**
* @}
*/
/** @defgroup USB_CORE_Exported_Functions
* @{
*/
uint8_t USBD_PRNT_RegisterInterface(USBD_HandleTypeDef *pdev, USBD_PRNT_ItfTypeDef *fops);
uint8_t USBD_PRNT_SetRxBuffer(USBD_HandleTypeDef *pdev, uint8_t *pbuff);
uint8_t USBD_PRNT_ReceivePacket(USBD_HandleTypeDef *pdev);
/**
* @}
*/
#ifdef __cplusplus
}
#endif
#endif /* __USB_PRNT_H */
/**
* @}
*/
/**
* @}
*/
/************************ (C) COPYRIGHT STMicroelectronics *****END OF FILE****/

View File

@@ -0,0 +1,45 @@
/**
******************************************************************************
* @file usbd_printer_if_template.h
* @author MCD Application Team
* @brief Header for usbd_PRNT_if_template.c file.
******************************************************************************
* @attention
*
* <h2><center>&copy; Copyright (c) 2021 STMicroelectronics.
* All rights reserved.</center></h2>
*
* This software component is licensed by ST under Ultimate Liberty license
* SLA0044, the "License"; You may not use this file except in compliance with
* the License. You may obtain a copy of the License at:
* http://www.st.com/SLA0044
*
******************************************************************************
*/
/* Define to prevent recursive inclusion -------------------------------------*/
#ifndef __USBD_PRNT_IF_TEMPLATE_H
#define __USBD_PRNT_IF_TEMPLATE_H
#ifdef __cplusplus
extern "C" {
#endif
/* Includes ------------------------------------------------------------------*/
#include "usbd_printer.h"
/* Exported types ------------------------------------------------------------*/
/* Exported constants --------------------------------------------------------*/
extern USBD_PRNT_ItfTypeDef USBD_PRNT_Template_fops;
/* Exported macro ------------------------------------------------------------*/
/* Exported functions ------------------------------------------------------- */
#ifdef __cplusplus
}
#endif
#endif /* __USBD_PRNT_IF_TEMPLATE_H */
/************************ (C) COPYRIGHT STMicroelectronics *****END OF FILE****/

View File

@@ -0,0 +1,673 @@
/**
******************************************************************************
* @file usbd_printer.c
* @author MCD Application Team
* @brief This file provides the high layer firmware functions to manage the
* following functionalities of the USB printer Class:
* - Initialization and Configuration of high and low layer
* - Enumeration as printer Device (and enumeration for each implemented memory interface)
* - OUT data transfer
* - Command OUT transfer (class requests management)
* - Error management
*
* @verbatim
*
* ===================================================================
* PRINTER Class Driver Description
* ===================================================================
* This driver manages the "Universal Serial Bus Class Definitions for Communications Devices
* Revision 1.2 November 16, 2007" and the sub-protocol specification of "Universal Serial Bus
* printer Class Subclass Specification for PSTN Devices Revision 1.2 February 9, 2007"
* This driver implements the following aspects of the specification:
* - Device descriptor management
* - Configuration descriptor management
* - Enumeration as printer device with 2 data endpoints (IN and OUT)
* - Control Requests management (PRNT_GET_DEVICE_ID,PRNT_GET_PORT_STATUS,PRNT_SOFT_RESET)
* - protocol USB_PRNT_BIDIRECTIONAL
*
*
*
* These aspects may be enriched or modified for a specific user application.
*
* This driver doesn't implement the following aspects of the specification
* (but it is possible to manage these features with some modifications on this driver):
* - Any class-specific aspect relative to communication classes should be managed by user application.
* - All communication classes other than PSTN are not managed
*
* @endverbatim
*
******************************************************************************
* @attention
*
* <h2><center>&copy; Copyright (c) 2021 STMicroelectronics.
* All rights reserved.</center></h2>
*
* This software component is licensed by ST under Ultimate Liberty license
* SLA0044, the "License"; You may not use this file except in compliance with
* the License. You may obtain a copy of the License at:
* www.st.com/SLA0044
*
******************************************************************************
*/
/* BSPDependencies
- "stm32xxxxx_{eval}{discovery}{nucleo_144}.c"
- "stm32xxxxx_{eval}{discovery}_io.c"
EndBSPDependencies */
/* Includes ------------------------------------------------------------------*/
#include "usbd_printer.h"
#include "usbd_ctlreq.h"
/** @addtogroup STM32_USB_DEVICE_LIBRARY
* @{
*/
/** @defgroup USBD_PRNT
* @brief usbd core module
* @{
*/
/** @defgroup USBD_PRNT_Private_TypesDefinitions
* @{
*/
/**
* @}
*/
static uint32_t usbd_PRNT_altset = 0U;
/** @defgroup USBD_PRNT_Private_Defines
* @{
*/
/**
* @}
*/
/** @defgroup USBD_PRNT_Private_Macros
* @{
*/
/**
* @}
*/
/** @defgroup USBD_PRNT_Private_FunctionPrototypes
* @{
*/
static uint8_t USBD_PRNT_Init(USBD_HandleTypeDef *pdev, uint8_t cfgidx);
static uint8_t USBD_PRNT_DeInit(USBD_HandleTypeDef *pdev, uint8_t cfgidx);
static uint8_t USBD_PRNT_Setup(USBD_HandleTypeDef *pdev, USBD_SetupReqTypedef *req);
static uint8_t USBD_PRNT_DataIn(USBD_HandleTypeDef *pdev, uint8_t epnum);
static uint8_t USBD_PRNT_DataOut(USBD_HandleTypeDef *pdev, uint8_t epnum);
static uint8_t *USBD_PRNT_GetFSCfgDesc(uint16_t *length);
static uint8_t *USBD_PRNT_GetHSCfgDesc(uint16_t *length);
static uint8_t *USBD_PRNT_GetOtherSpeedCfgDesc(uint16_t *length);
static uint8_t *USBD_PRNT_GetOtherSpeedCfgDesc(uint16_t *length);
uint8_t *USBD_PRNT_GetDeviceQualifierDescriptor(uint16_t *length);
/* USB Standard Device Descriptor */
__ALIGN_BEGIN static uint8_t USBD_PRNT_DeviceQualifierDesc[USB_LEN_DEV_QUALIFIER_DESC] __ALIGN_END =
{
USB_LEN_DEV_QUALIFIER_DESC,
USB_DESC_TYPE_DEVICE_QUALIFIER,
0x00,
0x02,
0x00,
0x00,
0x00,
0x40,
0x01,
0x00,
};
/**
* @}
*/
/** @defgroup USBD_PRNT_Private_Variables
* @{
*/
/* PRNT interface class callbacks structure */
USBD_ClassTypeDef USBD_PRNT =
{
USBD_PRNT_Init,
USBD_PRNT_DeInit,
USBD_PRNT_Setup,
NULL,
NULL,
USBD_PRNT_DataIn,
USBD_PRNT_DataOut,
NULL,
NULL,
NULL,
USBD_PRNT_GetHSCfgDesc,
USBD_PRNT_GetFSCfgDesc,
USBD_PRNT_GetOtherSpeedCfgDesc,
USBD_PRNT_GetDeviceQualifierDescriptor,
};
/* USB PRNT device Configuration Descriptor */
__ALIGN_BEGIN static uint8_t USBD_PRNT_CfgHSDesc[] __ALIGN_END =
{
/*Configuration Descriptor*/
0x09, /* bLength: Configuration Descriptor size */
USB_DESC_TYPE_CONFIGURATION, /* bDescriptorType: Configuration */
USB_PRNT_CONFIG_DESC_SIZ, /* wTotalLength:no of returned bytes */
0x00,
0x01, /* bNumInterfaces: 1 interface */
0x01, /* bConfigurationValue: Configuration value */
0x00, /* iConfiguration: Index of string descriptor describing the configuration */
#if (USBD_SELF_POWERED == 1U)
0xC0, /* bmAttributes: Self Powered according to user configuration */
#else
0x80, /* bmAttributes: Bus Powered according to user configuration */
#endif
USBD_MAX_POWER, /* MaxPower in mA */
/* Interface Descriptor */
0x09, /* bLength: Interface Descriptor size */
USB_DESC_TYPE_INTERFACE, /* bDescriptorType: Interface */
0x00, /* bInterfaceNumber: Number of Interface */
0x00, /* bAlternateSetting: Alternate setting */
0x02, /* bNumEndpoints: 2 endpoints used */
0x07, /* bInterfaceClass: Communication Interface Class */
0x01, /* bInterfaceSubClass: Abstract Control Model */
USB_PRNT_BIDIRECTIONAL, /* bDeviceProtocol */
0x00, /* iInterface */
/* Endpoint IN Descriptor */
0x07, /* bLength: Endpoint Descriptor size */
USB_DESC_TYPE_ENDPOINT, /* bDescriptorType: Endpoint */
PRNT_IN_EP, /* bEndpointAddress */
0x02, /* bmAttributes: Bulk */
LOBYTE(PRNT_DATA_HS_IN_PACKET_SIZE), /* wMaxPacketSize */
HIBYTE(PRNT_DATA_HS_IN_PACKET_SIZE),
0x00, /* bInterval */
/* Endpoint OUT Descriptor */
0x07, /* bLength: Endpoint Descriptor size */
USB_DESC_TYPE_ENDPOINT, /* bDescriptorType: Endpoint */
PRNT_OUT_EP, /* bEndpointAddress */
0x02, /* bmAttributes: Bulk */
LOBYTE(PRNT_DATA_HS_OUT_PACKET_SIZE),/* wMaxPacketSize */
HIBYTE(PRNT_DATA_HS_OUT_PACKET_SIZE),
0x00 /* bInterval */
};
/* USB PRNT device Configuration Descriptor */
__ALIGN_BEGIN static uint8_t USBD_PRNT_CfgFSDesc[] __ALIGN_END =
{
/*Configuration Descriptor*/
0x09, /* bLength: Configuration Descriptor size */
USB_DESC_TYPE_CONFIGURATION, /* bDescriptorType: Configuration */
USB_PRNT_CONFIG_DESC_SIZ, /* wTotalLength:no of returned bytes */
0x00,
0x01, /* bNumInterfaces: 1 interface */
0x01, /* bConfigurationValue: Configuration value */
0x00, /* iConfiguration: Index of string descriptor describing the configuration */
#if (USBD_SELF_POWERED == 1U)
0xC0, /* bmAttributes: Self Powered according to user configuration */
#else
0x80, /* bmAttributes: Bus Powered according to user configuration */
#endif
USBD_MAX_POWER, /* MaxPower in mA */
/*Interface Descriptor */
0x09, /* bLength: Interface Descriptor size */
USB_DESC_TYPE_INTERFACE, /* bDescriptorType: Interface */
0x00, /* bInterfaceNumber: Number of Interface */
0x00, /* bAlternateSetting: Alternate setting */
0x02, /* bNumEndpoints: 2 endpoints used */
0x07, /* bInterfaceClass: Communication Interface Class */
0x01, /* bInterfaceSubClass: Abstract Control Model */
USB_PRNT_BIDIRECTIONAL, /* bDeviceProtocol */
0x00, /* iInterface */
/*Endpoint IN Descriptor*/
0x07, /* bLength: Endpoint Descriptor size */
USB_DESC_TYPE_ENDPOINT, /* bDescriptorType: Endpoint */
PRNT_IN_EP, /* bEndpointAddress */
0x02, /* bmAttributes: Bulk */
LOBYTE(PRNT_DATA_FS_IN_PACKET_SIZE), /* wMaxPacketSize */
HIBYTE(PRNT_DATA_FS_IN_PACKET_SIZE),
0x00, /* bInterval */
/*Endpoint OUT Descriptor*/
0x07, /* bLength: Endpoint Descriptor size */
USB_DESC_TYPE_ENDPOINT, /* bDescriptorType: Endpoint */
PRNT_OUT_EP, /* bEndpointAddress */
0x02, /* bmAttributes: Bulk */
LOBYTE(PRNT_DATA_FS_OUT_PACKET_SIZE),/* wMaxPacketSize */
HIBYTE(PRNT_DATA_FS_OUT_PACKET_SIZE),
0x00 /* bInterval */
};
__ALIGN_BEGIN static uint8_t USBD_PRNT_OtherSpeedCfgDesc[] __ALIGN_END =
{
/*Configuration Descriptor*/
0x09, /* bLength: Configuration Descriptor size */
USB_DESC_TYPE_CONFIGURATION, /* bDescriptorType: Configuration */
USB_PRNT_CONFIG_DESC_SIZ, /* wTotalLength:no of returned bytes */
0x00,
0x01, /* bNumInterfaces: 1 interface */
0x01, /* bConfigurationValue: Configuration value */
0x00, /* iConfiguration: Index of string descriptor describing the configuration */
#if (USBD_SELF_POWERED == 1U)
0xC0, /* bmAttributes: Self Powered according to user configuration */
#else
0x80, /* bmAttributes: Bus Powered according to user configuration */
#endif
USBD_MAX_POWER, /* MaxPower in mA */
/*Interface Descriptor */
0x09, /* bLength: Interface Descriptor size */
USB_DESC_TYPE_INTERFACE, /* bDescriptorType: Interface */
0x00, /* bInterfaceNumber: Number of Interface */
0x00, /* bAlternateSetting: Alternate setting */
0x02, /* bNumEndpoints: 2 endpoints used */
0x07, /* bInterfaceClass: Communication Interface Class */
0x01, /* bInterfaceSubClass: Abstract Control Model */
USB_PRNT_BIDIRECTIONAL, /* bDeviceProtocol */
0x00, /* iInterface */
/*Endpoint IN Descriptor*/
0x07, /* bLength: Endpoint Descriptor size */
USB_DESC_TYPE_ENDPOINT, /* bDescriptorType: Endpoint */
PRNT_IN_EP, /* bEndpointAddress */
0x02, /* bmAttributes: Bulk */
LOBYTE(PRNT_DATA_FS_IN_PACKET_SIZE), /* wMaxPacketSize */
HIBYTE(PRNT_DATA_FS_IN_PACKET_SIZE),
0x00, /* bInterval */
/*Endpoint OUT Descriptor*/
0x07, /* bLength: Endpoint Descriptor size */
USB_DESC_TYPE_ENDPOINT, /* bDescriptorType: Endpoint */
PRNT_OUT_EP, /* bEndpointAddress */
0x02, /* bmAttributes: Bulk */
LOBYTE(PRNT_DATA_FS_OUT_PACKET_SIZE),/* wMaxPacketSize */
HIBYTE(PRNT_DATA_FS_OUT_PACKET_SIZE),
0x00 /* bInterval */
};
/**
* @}
*/
/** @defgroup USBD_PRNT_Private_Functions
* @{
*/
/**
* @brief USBD_PRNT_Init
* Initialize the PRNT interface
* @param pdev: device instance
* @param cfgidx: Configuration index
* @retval status
*/
static uint8_t USBD_PRNT_Init(USBD_HandleTypeDef *pdev, uint8_t cfgidx)
{
UNUSED(cfgidx);
USBD_PRNT_HandleTypeDef *hPRNT;
uint16_t mps;
hPRNT = (USBD_PRNT_HandleTypeDef *)USBD_malloc(sizeof(USBD_PRNT_HandleTypeDef));
if (hPRNT == NULL)
{
pdev->pClassData = NULL;
return (uint8_t)USBD_EMEM;
}
/* Setup the pClassData pointer */
pdev->pClassData = (void *)hPRNT;
/* Setup the max packet size according to selected speed */
if (pdev->dev_speed == USBD_SPEED_HIGH)
{
mps = PRNT_DATA_HS_IN_PACKET_SIZE;
}
else
{
mps = PRNT_DATA_FS_IN_PACKET_SIZE;
}
/* Open EP IN */
(void)USBD_LL_OpenEP(pdev, PRNT_IN_EP, USBD_EP_TYPE_BULK, mps);
/* Set endpoint as used */
pdev->ep_in[PRNT_IN_EP & 0xFU].is_used = 1U;
/* Open EP OUT */
(void)USBD_LL_OpenEP(pdev, PRNT_OUT_EP, USBD_EP_TYPE_BULK, mps);
/* Set endpoint as used */
pdev->ep_out[PRNT_OUT_EP & 0xFU].is_used = 1U;
/* Init physical Interface components */
((USBD_PRNT_ItfTypeDef *)pdev->pUserData)->Init();
/* Prepare Out endpoint to receive next packet */
(void)USBD_LL_PrepareReceive(pdev, PRNT_OUT_EP, hPRNT->RxBuffer, mps);
/* End of initialization phase */
return (uint8_t)USBD_OK;
}
/**
* @brief USBD_PRNT_DeInit
* DeInitialize the PRNT layer
* @param pdev: device instance
* @param cfgidx: Configuration index
* @retval status
*/
static uint8_t USBD_PRNT_DeInit(USBD_HandleTypeDef *pdev, uint8_t cfgidx)
{
UNUSED(cfgidx);
/* Close EP IN */
(void)USBD_LL_CloseEP(pdev, PRNT_IN_EP);
pdev->ep_in[PRNT_IN_EP & 0xFU].is_used = 0U;
/* Close EP OUT */
(void)USBD_LL_CloseEP(pdev, PRNT_OUT_EP);
pdev->ep_out[PRNT_OUT_EP & 0xFU].is_used = 0U;
/* DeInit physical Interface components */
if (pdev->pClassData != NULL)
{
((USBD_PRNT_ItfTypeDef *)pdev->pUserData)->DeInit();
(void)USBD_free(pdev->pClassData);
pdev->pClassData = NULL;
}
return 0U;
}
/**
* @brief USBD_PRNT_Setup
* Handle the PRNT specific requests
* @param pdev: instance
* @param req: usb requests
* @retval status
*/
static uint8_t USBD_PRNT_Setup(USBD_HandleTypeDef *pdev, USBD_SetupReqTypedef *req)
{
USBD_PRNT_HandleTypeDef *hPRNT = (USBD_PRNT_HandleTypeDef *)pdev->pClassData;
USBD_PRNT_ItfTypeDef *hPRNTitf = (USBD_PRNT_ItfTypeDef *)pdev->pUserData;
USBD_StatusTypeDef ret = USBD_OK;
uint16_t status_info = 0U;
uint16_t data_length;
switch (req->bmRequest & USB_REQ_TYPE_MASK)
{
case USB_REQ_TYPE_CLASS :
if (req->wLength != 0U)
{
data_length = MIN(req->wLength, PRNT_DATA_HS_MAX_PACKET_SIZE);
if ((req->bmRequest & 0x80U) != 0U)
{
/* Call the User class interface function to process the command */
hPRNTitf->Control_req(req->bRequest, (uint8_t *)hPRNT->data, &data_length);
/* Return the answer to host */
(void) USBD_CtlSendData(pdev, (uint8_t *)hPRNT->data, data_length);
}
else
{
/* Prepare for control data reception */
(void) USBD_CtlPrepareRx(pdev, (uint8_t *)hPRNT->data, data_length);
}
}
else
{
data_length = 0U;
hPRNTitf->Control_req(req->bRequest, (uint8_t *)req, &data_length);
}
break;
case USB_REQ_TYPE_STANDARD:
switch (req->bRequest)
{
case USB_REQ_GET_STATUS:
if (pdev->dev_state == USBD_STATE_CONFIGURED)
{
(void)USBD_CtlSendData(pdev, (uint8_t *)&status_info, 2U);
}
else
{
USBD_CtlError(pdev, req);
ret = USBD_FAIL;
}
break;
case USB_REQ_GET_INTERFACE:
if (pdev->dev_state == USBD_STATE_CONFIGURED)
{
(void)USBD_CtlSendData(pdev, (uint8_t *)&usbd_PRNT_altset, 1U);
}
else
{
USBD_CtlError(pdev, req);
ret = USBD_FAIL;
}
break;
case USB_REQ_SET_INTERFACE:
if (pdev->dev_state != USBD_STATE_CONFIGURED)
{
USBD_CtlError(pdev, req);
ret = USBD_FAIL;
}
break;
case USB_REQ_CLEAR_FEATURE:
break;
default:
USBD_CtlError(pdev, req);
ret = USBD_FAIL;
break;
}
break;
default:
USBD_CtlError(pdev, req);
ret = USBD_FAIL;
break;
}
return (uint8_t)ret;
}
/**
* @brief USBD_PRNT_DataIn
* Data sent on non-control IN endpoint
* @param pdev: device instance
* @param epnum: endpoint number
* @retval status
*/
static uint8_t USBD_PRNT_DataIn(USBD_HandleTypeDef *pdev, uint8_t epnum)
{
USBD_PRNT_HandleTypeDef *hPRNT = (USBD_PRNT_HandleTypeDef *)pdev->pClassData;
PCD_HandleTypeDef *hpcd = pdev->pData;
if (hPRNT == NULL)
{
return (uint8_t)USBD_FAIL;
}
if ((pdev->ep_in[epnum].total_length > 0U) &&
((pdev->ep_in[epnum].total_length % hpcd->IN_ep[epnum].maxpacket) == 0U))
{
/* Update the packet total length */
pdev->ep_in[epnum].total_length = 0U;
/* Send ZLP */
(void) USBD_LL_Transmit(pdev, epnum, NULL, 0U);
}
else
{
hPRNT->TxState = 0U;
}
return (uint8_t)USBD_OK;
}
/**
* @brief USBD_PRNT_DataOut
* Data received on non-control Out endpoint
* @param pdev: device instance
* @param epnum: endpoint number
* @retval status
*/
static uint8_t USBD_PRNT_DataOut(USBD_HandleTypeDef *pdev, uint8_t epnum)
{
USBD_PRNT_HandleTypeDef *hPRNT = (USBD_PRNT_HandleTypeDef *)pdev->pClassData;
if (hPRNT == NULL)
{
return (uint8_t)USBD_FAIL;
}
/* Get the received data length */
hPRNT->RxLength = USBD_LL_GetRxDataSize(pdev, epnum);
/* USB data will be immediately processed, this allow next USB traffic being
NAKed till the end of the application Xfer */
((USBD_PRNT_ItfTypeDef *)pdev->pUserData)->Receive(hPRNT->RxBuffer, &hPRNT->RxLength);
return (uint8_t)USBD_OK;
}
/**
* @brief USBD_PRNT_GetFSCfgDesc
* Return configuration descriptor
* @param length : pointer data length
* @retval pointer to descriptor buffer
*/
static uint8_t *USBD_PRNT_GetFSCfgDesc(uint16_t *length)
{
*length = (uint16_t) sizeof(USBD_PRNT_CfgFSDesc);
return USBD_PRNT_CfgFSDesc;
}
/**
* @brief USBD_PRNT_GetHSCfgDesc
* Return configuration descriptor
* @param length : pointer data length
* @retval pointer to descriptor buffer
*/
static uint8_t *USBD_PRNT_GetHSCfgDesc(uint16_t *length)
{
*length = (uint16_t) sizeof(USBD_PRNT_CfgHSDesc);
return USBD_PRNT_CfgHSDesc;
}
/**
* @brief USBD_PRNT_GetOtherSpeedCfgDesc
* Return configuration descriptor
* @param length : pointer data length
* @retval pointer to descriptor buffer
*/
static uint8_t *USBD_PRNT_GetOtherSpeedCfgDesc(uint16_t *length)
{
*length = (uint16_t) sizeof(USBD_PRNT_OtherSpeedCfgDesc);
return USBD_PRNT_OtherSpeedCfgDesc;
}
/**
* @brief USBD_PRNT_GetDeviceQualifierDescriptor
* return Device Qualifier descriptor
* @param length : pointer data length
* @retval pointer to descriptor buffer
*/
uint8_t *USBD_PRNT_GetDeviceQualifierDescriptor(uint16_t *length)
{
*length = (uint16_t)sizeof(USBD_PRNT_DeviceQualifierDesc);
return USBD_PRNT_DeviceQualifierDesc;
}
/**
* @brief USBD_PRNT_RegisterInterface
* @param pdev: device instance
* @param fops: Interface callbacks
* @retval status
*/
uint8_t USBD_PRNT_RegisterInterface(USBD_HandleTypeDef *pdev, USBD_PRNT_ItfTypeDef *fops)
{
/* Check if the fops pointer is valid */
if (fops == NULL)
{
return (uint8_t)USBD_FAIL;
}
/* Setup the fops pointer */
pdev->pUserData = fops;
return (uint8_t)USBD_OK;
}
/**
* @brief USBD_PRNT_SetRxBuffer
* @param pdev: device instance
* @param pbuff: Rx Buffer
* @retval status
*/
uint8_t USBD_PRNT_SetRxBuffer(USBD_HandleTypeDef *pdev, uint8_t *pbuff)
{
USBD_PRNT_HandleTypeDef *hPRNT = (USBD_PRNT_HandleTypeDef *) pdev->pClassData;
hPRNT->RxBuffer = pbuff;
return (uint8_t)USBD_OK;
}
/**
* @brief USBD_PRNT_ReceivePacket
* prepare OUT Endpoint for reception
* @param pdev: device instance
* @retval status
*/
uint8_t USBD_PRNT_ReceivePacket(USBD_HandleTypeDef *pdev)
{
USBD_PRNT_HandleTypeDef *hPRNT = (USBD_PRNT_HandleTypeDef *)pdev->pClassData;
if (hPRNT == NULL)
{
return (uint8_t)USBD_FAIL;
}
if (pdev->dev_speed == USBD_SPEED_HIGH)
{
/* Prepare Out endpoint to receive next packet */
(void)USBD_LL_PrepareReceive(pdev, PRNT_OUT_EP, hPRNT->RxBuffer,
PRNT_DATA_HS_OUT_PACKET_SIZE);
}
else
{
/* Prepare Out endpoint to receive next packet */
(void)USBD_LL_PrepareReceive(pdev, PRNT_OUT_EP, hPRNT->RxBuffer,
PRNT_DATA_FS_OUT_PACKET_SIZE);
}
return (uint8_t)USBD_OK;
}
/**
* @}
*/
/**
* @}
*/
/**
* @}
*/
/************************ (C) COPYRIGHT STMicroelectronics *****END OF FILE****/

View File

@@ -0,0 +1,218 @@
/**
******************************************************************************
* @file usbd_printer_if_template.c
* @author MCD Application Team
* @brief Generic media access Layer.
******************************************************************************
* @attention
*
* <h2><center>&copy; Copyright (c) 2021 STMicroelectronics.
* All rights reserved.</center></h2>
*
* This software component is licensed by ST under Ultimate Liberty license
* SLA0044, the "License"; You may not use this file except in compliance with
* the License. You may obtain a copy of the License at:
* http://www.st.com/SLA0044
*
******************************************************************************
*/
/* Includes ------------------------------------------------------------------*/
#include "usbd_printer_if_template.h"
/** @addtogroup STM32_USB_DEVICE_LIBRARY
* @{
*/
/** @defgroup USBD_PRNT
* @brief usbd core module
* @{
*/
/** @defgroup USBD_PRNT_Private_TypesDefinitions
* @{
*/
/**
* @}
*/
/** @defgroup USBD_PRNT_Private_Defines
* @{
*/
/**
* @}
*/
/** @defgroup USBD_PRNT_Private_Macros
* @{
*/
/**
* @}
*/
/** @defgroup USBD_PRNT_Private_FunctionPrototypes
* @{
*/
static int8_t TEMPLATE_Init(void);
static int8_t TEMPLATE_DeInit(void);
static int8_t TEMPLATE_Control_req(uint8_t req, uint8_t *pbuf, uint16_t *length);
static int8_t TEMPLATE_Receive(uint8_t *pbuf, uint32_t *Len);
/*printer Private function prototypes*/
void TEMPLATE_PRNT_PageEndManager(uint8_t *Buf, uint32_t Len);
USBD_PRNT_ItfTypeDef USBD_PRNT_Template_fops =
{
TEMPLATE_Init,
TEMPLATE_DeInit,
TEMPLATE_Control_req
TEMPLATE_Receive
};
static uint8_t PRNT_DEVICE_ID[DEVICE_ID_LEN] =
{
0x00, 0x6D,
'M', 'A', 'N', 'U', 'F', 'A', 'C', 'T', 'U', 'R', 'E', 'R', ':',
'S', 'T', 'M', 'i', 'c', 'r', 'o', 'e', 'l', 'e', 'c', 't', 'r', 'o', 'n', 'i', 'c', 's', ';',
'C', 'O', 'M', 'M', 'A', 'N', 'D', ' ', 'S', 'E', 'T', ':',
'P', 'D', 'L', ',', 'P', 'C', 'P', ';',
'M', 'O', 'D', 'E', 'L', ':',
'U', 'S', 'B', 'P', 'r', 'i', 'n', 't', 'e', 'r', ';',
'C', 'O', 'M', 'M', 'E', 'N', 'T', ':',
'G', 'o', 'o', 'd', ' ', '!', ';',
'A', 'C', 'T', 'I', 'V', 'E', ' ', 'C', 'O', 'M', 'M', 'A', 'N', 'D', ' ', 'S', 'E', 'T', ':',
'P', 'C', 'P', ';'
};
/* Private functions ---------------------------------------------------------*/
/**
* @brief TEMPLATE_Init
* Initializes the PRNT media low layer
* @param None
* @retval Result of the operation: USBD_OK if all operations are OK else USBD_FAIL
*/
static int8_t TEMPLATE_Init(void)
{
/*
Add your initialization code here
*/
return (0);
}
/**
* @brief TEMPLATE_DeInit
* DeInitializes the PRNT media low layer
* @param None
* @retval Result of the operation: USBD_OK if all operations are OK else USBD_FAIL
*/
static int8_t TEMPLATE_DeInit(void)
{
/*
Add your deinitialization code here
*/
return (0);
}
/**
* @brief TEMPLATE_Receive
* Data received over USB OUT endpoint are sent over PRNT interface
* through this function.
*
* @note
* This function will issue a NAK packet on any OUT packet received on
* USB endpoint untill exiting this function. If you exit this function
* before transfer is complete on PRNT interface (ie. using DMA controller)
* it will result in receiving more data while previous ones are still
* not sent.
*
* @param Buf: Buffer of data to be received
* @param Len: Number of data received (in bytes)
* @retval Result of the operation: USBD_OK if all operations are OK else USBD_FAIL
*/
static int8_t TEMPLATE_Receive(uint8_t *Buf, uint32_t *Len)
{
UNUSED(Buf);
UNUSED(Len);
return (0);
}
/**
* @brief TEMPLATE_PRNT_Itf_Control_req
* Manage the PRNT class requests
* @param req: Command code
* @param pbuf: Buffer containing command data (request parameters)
* @param length: Number of data to be sent (in bytes)
* @retval Result of the operation: USBD_OK if all operations are OK else USBD_FAIL
*/
static int8_t TEMPLATE_PRNT_Itf_Control_req(uint8_t req, uint8_t *pbuf, uint16_t *length)
{
uint32_t i = 0;
/* Check on the setup request value */
switch (req)
{
/* Get Printer Device ID request */
case PRNT_GET_DEVICE_ID:
/* Not using for loop here due to MISRA-C2012-Rule-16.1 */
while (i < sizeof(PRNT_DEVICE_ID))
{
pbuf[i] = PRNT_DEVICE_ID[i];
i++;
}
*length = i;
break;
/* Get Printer current status */
case PRNT_GET_PORT_STATUS:
pbuf[0] = PRNT_STATUS_PAPER_EMPTY |
PRNT_STATUS_SELECTED |
PRNT_STATUS_NO_ERROR;
*length = 1U;
break;
/* Printer SOFT RESET request: cleanup pending tasks */
case PRNT_SOFT_RESET:
(void)f_close(&hSD.MyFile);
break;
default:
/* Unkown commands are not managed */
break;
}
/**
* @brief TEMPLATE_PRNT_PageEndManager, defined by user
* Call this function frequently to check if data is received.
* @param Buf: Buffer of data to be received
* @param Len: Number of data received (in bytes)
*/
void TEMPLATE_PRNT_PageEndManager(uint8_t *Buf, uint32_t Len)
{
UNUSED(Buf);
UNUSED(Len);
}
/**
* @}
*/
/**
* @}
*/
/**
* @}
*/
/************************ (C) COPYRIGHT STMicroelectronics *****END OF FILE****/

View File

@@ -128,7 +128,7 @@ USBD_ClassTypeDef USBD_TEMPLATE_ClassDriver =
/* USB TEMPLATE device Configuration Descriptor */ /* USB TEMPLATE device Configuration Descriptor */
__ALIGN_BEGIN static uint8_t USBD_TEMPLATE_CfgDesc[USB_TEMPLATE_CONFIG_DESC_SIZ] __ALIGN_END = __ALIGN_BEGIN static uint8_t USBD_TEMPLATE_CfgDesc[USB_TEMPLATE_CONFIG_DESC_SIZ] __ALIGN_END =
{ {
0x09, /* bLength: Configuation Descriptor size */ 0x09, /* bLength: Configuration Descriptor size */
USB_DESC_TYPE_OTHER_SPEED_CONFIGURATION, /* bDescriptorType: Configuration */ USB_DESC_TYPE_OTHER_SPEED_CONFIGURATION, /* bDescriptorType: Configuration */
USB_TEMPLATE_CONFIG_DESC_SIZ, USB_TEMPLATE_CONFIG_DESC_SIZ,
/* wTotalLength: Bytes returned */ /* wTotalLength: Bytes returned */
@@ -210,36 +210,35 @@ static uint8_t USBD_TEMPLATE_Setup(USBD_HandleTypeDef *pdev,
switch (req->bmRequest & USB_REQ_TYPE_MASK) switch (req->bmRequest & USB_REQ_TYPE_MASK)
{ {
case USB_REQ_TYPE_CLASS : case USB_REQ_TYPE_CLASS :
switch (req->bRequest) switch (req->bRequest)
{ {
default:
USBD_CtlError(pdev, req);
ret = USBD_FAIL;
break;
}
break;
case USB_REQ_TYPE_STANDARD:
switch (req->bRequest)
{
default:
USBD_CtlError(pdev, req);
ret = USBD_FAIL;
break;
}
break;
default: default:
USBD_CtlError(pdev, req); USBD_CtlError(pdev, req);
ret = USBD_FAIL; ret = USBD_FAIL;
break; break;
}
break;
case USB_REQ_TYPE_STANDARD:
switch (req->bRequest)
{
default:
USBD_CtlError(pdev, req);
ret = USBD_FAIL;
break;
}
break;
default:
USBD_CtlError(pdev, req);
ret = USBD_FAIL;
break;
} }
return (uint8_t)ret; return (uint8_t)ret;
} }
/** /**
* @brief USBD_TEMPLATE_GetCfgDesc * @brief USBD_TEMPLATE_GetCfgDesc
* return configuration descriptor * return configuration descriptor
@@ -253,18 +252,17 @@ static uint8_t *USBD_TEMPLATE_GetCfgDesc(uint16_t *length)
} }
/** /**
* @brief DeviceQualifierDescriptor * @brief DeviceQualifierDescriptor
* return Device Qualifier descriptor * return Device Qualifier descriptor
* @param length : pointer data length * @param length : pointer data length
* @retval pointer to descriptor buffer * @retval pointer to descriptor buffer
*/ */
uint8_t *USBD_TEMPLATE_DeviceQualifierDescriptor(uint16_t *length) uint8_t *USBD_TEMPLATE_DeviceQualifierDescriptor(uint16_t *length)
{ {
*length = (uint16_t)sizeof(USBD_TEMPLATE_DeviceQualifierDesc); *length = (uint16_t)sizeof(USBD_TEMPLATE_DeviceQualifierDesc);
return USBD_TEMPLATE_DeviceQualifierDesc; return USBD_TEMPLATE_DeviceQualifierDesc;
} }
/** /**
* @brief USBD_TEMPLATE_DataIn * @brief USBD_TEMPLATE_DataIn
* handle data IN Stage * handle data IN Stage
@@ -289,6 +287,7 @@ static uint8_t USBD_TEMPLATE_EP0_RxReady(USBD_HandleTypeDef *pdev)
return (uint8_t)USBD_OK; return (uint8_t)USBD_OK;
} }
/** /**
* @brief USBD_TEMPLATE_EP0_TxReady * @brief USBD_TEMPLATE_EP0_TxReady
* handle EP0 TRx Ready event * handle EP0 TRx Ready event
@@ -300,6 +299,7 @@ static uint8_t USBD_TEMPLATE_EP0_TxReady(USBD_HandleTypeDef *pdev)
return (uint8_t)USBD_OK; return (uint8_t)USBD_OK;
} }
/** /**
* @brief USBD_TEMPLATE_SOF * @brief USBD_TEMPLATE_SOF
* handle SOF event * handle SOF event
@@ -311,6 +311,7 @@ static uint8_t USBD_TEMPLATE_SOF(USBD_HandleTypeDef *pdev)
return (uint8_t)USBD_OK; return (uint8_t)USBD_OK;
} }
/** /**
* @brief USBD_TEMPLATE_IsoINIncomplete * @brief USBD_TEMPLATE_IsoINIncomplete
* handle data ISO IN Incomplete event * handle data ISO IN Incomplete event
@@ -323,6 +324,7 @@ static uint8_t USBD_TEMPLATE_IsoINIncomplete(USBD_HandleTypeDef *pdev, uint8_t e
return (uint8_t)USBD_OK; return (uint8_t)USBD_OK;
} }
/** /**
* @brief USBD_TEMPLATE_IsoOutIncomplete * @brief USBD_TEMPLATE_IsoOutIncomplete
* handle data ISO OUT Incomplete event * handle data ISO OUT Incomplete event
@@ -349,11 +351,11 @@ static uint8_t USBD_TEMPLATE_DataOut(USBD_HandleTypeDef *pdev, uint8_t epnum)
} }
/** /**
* @brief DeviceQualifierDescriptor * @brief DeviceQualifierDescriptor
* return Device Qualifier descriptor * return Device Qualifier descriptor
* @param length : pointer data length * @param length : pointer data length
* @retval pointer to descriptor buffer * @retval pointer to descriptor buffer
*/ */
uint8_t *USBD_TEMPLATE_GetDeviceQualifierDesc(uint16_t *length) uint8_t *USBD_TEMPLATE_GetDeviceQualifierDesc(uint16_t *length)
{ {
*length = (uint16_t)sizeof(USBD_TEMPLATE_DeviceQualifierDesc); *length = (uint16_t)sizeof(USBD_TEMPLATE_DeviceQualifierDesc);

View File

@@ -0,0 +1,460 @@
/**
******************************************************************************
* @file usbd_video.h
* @author MCD Application Team
* @brief header file for the usbd_video.c file.
******************************************************************************
* @attention
*
* <h2><center>&copy; Copyright (c) 2020 STMicroelectronics.
* All rights reserved.</center></h2>
*
* This software component is licensed by ST under Ultimate Liberty license
* SLA0044, the "License"; You may not use this file except in compliance with
* the License. You may obtain a copy of the License at:
* www.st.com/SLA0044
*
******************************************************************************
*/
/* Define to prevent recursive inclusion -------------------------------------*/
#ifndef __USBD_VIDEO_H
#define __USBD_VIDEO_H
#ifdef __cplusplus
extern "C" {
#endif
/* Includes ------------------------------------------------------------------*/
#include "usbd_ioreq.h"
/** @addtogroup STM32_USB_DEVICE_LIBRARY
* @{
*/
/** @defgroup USBD_VIDEO
* @brief This file is the Header file for usbd_video.c
* @{
*/
/** @defgroup usbd_VIDEO_Exported_Defines
* @{
*/
/* USB Video device class specification version 1.10 */
#ifdef UVC_1_0
#define UVC_VERSION 0x0100U /* UVC 1.0 */
#else
#define UVC_VERSION 0x0110U /* UVC 1.1 */
#endif
/* bEndpointAddress in Endpoint Descriptor */
#ifndef UVC_IN_EP
#define UVC_IN_EP 0x81U
#endif /* VIDEO_IN_EP */
/* These defines shall be updated in the usbd_conf.h file */
#ifndef UVC_WIDTH
#define UVC_WIDTH 400U
#endif /* UVC_WIDTH */
#ifndef UVC_HEIGHT
#define UVC_HEIGHT 240U
#endif /* UVC_HEIGHT */
#ifndef UVC_CAM_FPS_FS
#define UVC_CAM_FPS_FS 10U
#endif /* UVC_CAM_FPS_FS */
#ifndef UVC_CAM_FPS_HS
#define UVC_CAM_FPS_HS 5U
#endif /* UVC_CAM_FPS_HS */
#ifndef UVC_PACKET_SIZE
#define UVC_PACKET_SIZE 512U
#endif /* UVC_PACKET_SIZE */
#ifndef UVC_MAX_FRAME_SIZE
#define UVC_MAX_FRAME_SIZE (UVC_WIDTH * UVC_HEIGHT * 16U / 2U)
#endif /* UVC_MAX_FRAME_SIZE */
#ifndef UVC_COLOR_PRIMARIE
#define UVC_COLOR_PRIMARIE 0x01U
#endif /* UVC_COLOR_PRIMARIE */
#ifndef UVC_TFR_CHARACTERISTICS
#define UVC_TFR_CHARACTERISTICS 0x01U
#endif /* UVC_TFR_CHARACTERISTICS */
#ifndef UVC_MATRIX_COEFFICIENTS
#define UVC_MATRIX_COEFFICIENTS 0x04U
#endif /* UVC_MATRIX_COEFFICIENTS */
#ifndef UVC_BITS_PER_PIXEL
#define UVC_BITS_PER_PIXEL 12U
#endif /* UVC_BITS_PER_PIXEL */
#define UVC_GUID_YUY2 0x32595559U
#define UVC_GUID_NV12 0x3231564EU
#ifndef UVC_UNCOMPRESSED_GUID
#define UVC_UNCOMPRESSED_GUID UVC_GUID_NV12
#endif /* UVC_UNCOMPRESSED_GUID */
#define UVC_INTERVAL(n) (10000000U/(n))
#define UVC_MIN_BIT_RATE(n) (UVC_WIDTH * UVC_HEIGHT * 16U * (n)) /* 16 bit */
#define UVC_MAX_BIT_RATE(n) (UVC_WIDTH * UVC_HEIGHT * 16U * (n)) /* 16 bit */
#define UVC_PACKETS_IN_FRAME(n) (UVC_MAX_FRAME_SIZE / (n))
#ifndef UVC_ISO_FS_MPS
#define UVC_ISO_FS_MPS 256U
#endif
#ifndef UVC_ISO_HS_MPS
#define UVC_ISO_HS_MPS 512U
#endif
#ifndef UVC_HEADER_PACKET_CNT
#define UVC_HEADER_PACKET_CNT 0x01U
#endif
#define UVC_REQ_READ_MASK 0x80U
#define UVC_VC_IF_NUM 0x00U
#define UVC_VS_IF_NUM 0x01U
#define UVC_TOTAL_IF_NUM 0x02U
#ifdef USBD_UVC_FORMAT_UNCOMPRESSED
#define UVC_CONFIG_DESC_SIZ (0x88U + 0x16U)
#else
#define UVC_CONFIG_DESC_SIZ 0x88U
#endif
#define UVC_TOTAL_BUF_SIZE 0x04U
#define UVC_VC_EP_DESC_SIZE 0x05U
#define UVC_STREAMING_EP_DESC_SIZE 0x07U
#define UVC_EP_DESC_TYPE 0x25U
/* Video Interface Class Codes*/
#define UVC_CC_VIDEO 0x0EU
#define UVC_PLAY_STATUS_STOP 0x00U
#define UVC_PLAY_STATUS_READY 0x01U
#define UVC_PLAY_STATUS_STREAMING 0x02U
#ifndef WBVAL
#define WBVAL(x) ((x) & 0xFFU),(((x) >> 8) & 0xFFU)
#endif
#ifndef DBVAL
#define DBVAL(x) ((x)& 0xFFU),(((x) >> 8) & 0xFFU),(((x)>> 16) & 0xFFU),(((x) >> 24) & 0xFFU)
#endif
/* Video Interface Protocol Codes */
#define PC_PROTOCOL_UNDEFINED 0x00U
#define VIDEO_VC_IF_HEADER_DESC_SIZE 0x0DU
#define VIDEO_IN_TERMINAL_DESC_SIZE 0x08U
#define VIDEO_OUT_TERMINAL_DESC_SIZE 0x09U
#define VIDEO_VS_IF_IN_HEADER_DESC_SIZE 0x0EU
#define VS_FORMAT_UNCOMPRESSED_DESC_SIZE 0x1BU
#define VS_FORMAT_MJPEG_DESC_SIZE 0x0BU
#define VS_FRAME_DESC_SIZE 0x1EU
#define VS_COLOR_MATCHING_DESC_SIZE 0x06U
#ifdef USBD_UVC_FORMAT_UNCOMPRESSED
#define VS_FORMAT_DESC_SIZE VS_FORMAT_UNCOMPRESSED_DESC_SIZE
#define VS_FORMAT_SUBTYPE VS_FORMAT_UNCOMPRESSED
#define VS_FRAME_SUBTYPE VS_FRAME_UNCOMPRESSED
#define VC_HEADER_SIZE (VIDEO_VS_IF_IN_HEADER_DESC_SIZE + \
VS_FORMAT_UNCOMPRESSED_DESC_SIZE + \
VS_FRAME_DESC_SIZE + \
VS_COLOR_MATCHING_DESC_SIZE)
#else
#define VS_FORMAT_DESC_SIZE VS_FORMAT_MJPEG_DESC_SIZE
#define VS_FORMAT_SUBTYPE VS_FORMAT_MJPEG
#define VS_FRAME_SUBTYPE VS_FRAME_MJPEG
#define VC_HEADER_SIZE (VIDEO_VS_IF_IN_HEADER_DESC_SIZE + \
VS_FORMAT_DESC_SIZE + \
VS_FRAME_DESC_SIZE)
#endif
/*
* Video Class specification release 1.1
* Appendix A. Video Device Class Codes defines
*/
/* Video Interface Subclass values */
#define SC_UNDEFINED 0x00U
#define SC_VIDEOCONTROL 0x01U
#define SC_VIDEOSTREAMING 0x02U
#define SC_VIDEO_INTERFACE_COLLECTION 0x03U
/* Video Class-Specific Descriptor Types */
#define CS_UNDEFINED 0x20U
#define CS_DEVICE 0x21U
#define CS_CONFIGURATION 0x22U
#define CS_STRING 0x23U
#define CS_INTERFACE 0x24U
#define CS_ENDPOINT 0x25U
/* Video Class-Specific VideoControl Interface Descriptor Subtypes */
#define VC_DESCRIPTOR_UNDEFINED 0x00U
#define VC_HEADER 0x01U
#define VC_INPUT_TERMINAL 0x02U
#define VC_OUTPUT_TERMINAL 0x03U
#define VC_SELECTOR_UNIT 0x04U
#define VC_PROCESSING_UNIT 0x05U
#define VC_EXTENSION_UNIT 0x06U
/* Video Class-Specific VideoStreaming Interface Descriptor Subtypes */
#define VS_UNDEFINED 0x00U
#define VS_INPUT_HEADER 0x01U
#define VS_OUTPUT_HEADER 0x02U
#define VS_STILL_IMAGE_FRAME 0x03U
#define VS_FORMAT_UNCOMPRESSED 0x04U
#define VS_FRAME_UNCOMPRESSED 0x05U
#define VS_FORMAT_MJPEG 0x06U
#define VS_FRAME_MJPEG 0x07U
#define VS_FORMAT_MPEG2TS 0x0AU
#define VS_FORMAT_DV 0x0CU
#define VS_COLORFORMAT 0x0DU
#define VS_FORMAT_FRAME_BASED 0x10U
#define VS_FRAME_FRAME_BASED 0x11U
#define VS_FORMAT_STREAM_BASED 0x12U
/* Video Class-Specific Request values */
#define UVC_RQ_UNDEFINED 0x00U
#define UVC_SET_CUR 0x01U
#define UVC_GET_CUR 0x81U
#define UVC_GET_MIN 0x82U
#define UVC_GET_MAX 0x83U
#define UVC_GET_RES 0x84U
#define UVC_GET_LEN 0x85U
#define UVC_GET_INFO 0x86U
#define UVC_GET_DEF 0x87U
/* VideoControl Interface Control Selectors */
#define VC_CONTROL_UNDEFINED 0x00U
#define VC_VIDEO_POWER_MODE_CONTROL 0x01U
#define VC_REQUEST_ERROR_CODE_CONTROL 0x02U
/* Request Error Code Control */
#define UVC_NO_ERROR_ERR 0x00U
#define UVC_NOT_READY_ERR 0x01U
#define UVC_WRONG_STATE_ERR 0x02U
#define UVC_POWER_ERR 0x03U
#define UVC_OUT_OF_RANGE_ERR 0x04U
#define UVC_INVALID_UNIT_ERR 0x05U
#define UVC_INVALID_CONTROL_ERR 0x06U
#define UVC_INVALID_REQUEST_ERR 0x07U
#define UVC_UNKNOWN_ERR 0xFFU
/*Terminal Control Selectors*/
#define TE_CONTROL_UNDEFINED 0x00U
/* Selector Unit Control Selectors */
#define SU_CONTROL_UNDEFINED 0x00U
#define SU_INPUT_SELECT_CONTROL 0x01U
/* Camera Terminal Control Selectors */
#define CT_CONTROL_UNDEFINED 0x00U
#define CT_SCANNING_MODE_CONTROL 0x01U
#define CT_AE_MODE_CONTROL 0x02U
#define CT_AE_PRIORITY_CONTROL 0x03U
#define CT_EXPOSURE_TIME_ABSOLUTE_CONTROL 0x04U
#define CT_EXPOSURE_TIME_RELATIVE_CONTROL 0x05U
#define CT_FOCUS_ABSOLUTE_CONTROL 0x06U
#define CT_FOCUS_RELATIVE_CONTROL 0x07U
#define CT_FOCUS_AUTO_CONTROL 0x08U
#define CT_IRIS_ABSOLUTE_CONTROL 0x09U
#define CT_IRIS_RELATIVE_CONTROL 0x0AU
#define CT_ZOOM_ABSOLUTE_CONTROL 0x0BU
#define CT_ZOOM_RELATIVE_CONTROL 0x0CU
#define CT_PANTILT_ABSOLUTE_CONTROL 0x0DU
#define CT_PANTILT_RELATIVE_CONTROL 0x0EU
#define CT_ROLL_ABSOLUTE_CONTROL 0x0FU
#define CT_ROLL_RELATIVE_CONTROL 0x10U
#define CT_PRIVACY_CONTROL 0x11U
/* Processing Unit Control Selectors */
#define PU_CONTROL_UNDEFINED 0x00U
#define PU_BACKLIGHT_COMPENSATION_CONTROL 0x01U
#define PU_BRIGHTNESS_CONTROL 0x02U
#define PU_CONTRAST_CONTROL 0x03U
#define PU_GAIN_CONTROL 0x04U
#define PU_POWER_LINE_FREQUENCY_CONTROL 0x05U
#define PU_HUE_CONTROL 0x06U
#define PU_SATURATION_CONTROL 0x07U
#define PU_SHARPNESS_CONTROL 0x08U
#define PU_GAMMA_CONTROL 0x09U
#define PU_WHITE_BALANCE_TEMPERATURE_CONTROL 0x0AU
#define PU_WHITE_BALANCE_TEMPERATURE_AUTO_CONTROL 0x0BU
#define PU_WHITE_BALANCE_COMPONENT_CONTROL 0x0CU
#define PU_WHITE_BALANCE_COMPONENT_AUTO_CONTROL 0x0DU
#define PU_DIGITAL_MULTIPLIER_CONTROL 0x0EU
#define PU_DIGITAL_MULTIPLIER_LIMIT_CONTROL 0x0FU
#define PU_HUE_AUTO_CONTROL 0x10U
#define PU_ANALOG_VIDEO_STANDARD_CONTROL 0x11U
#define PU_ANALOG_LOCK_STATUS_CONTROL 0x12U
/*Extension Unit Control Selectors */
#define XU_CONTROL_UNDEFINED 0x00U
/* VideoStreaming Interface Control Selectors */
#define VS_CONTROL_UNDEFINED 0x00U
#define VS_PROBE_CONTROL 0x100U
#define VS_COMMIT_CONTROL 0x200U
#define VS_STILL_PROBE_CONTROL 0x03U
#define VS_STILL_COMMIT_CONTROL 0x04U
#define VS_STILL_IMAGE_TRIGGER_CONTROL 0x05U
#define VS_STREAM_ERROR_CODE_CONTROL 0x06U
#define VS_GENERATE_KEY_FRAME_CONTROL 0x07U
#define VS_UPDATE_FRAME_SEGMENT_CONTROL 0x08U
#define VS_SYNC_DELAY_CONTROL 0x09U
/* Control Capabilities */
#define UVC_SUPPORTS_GET 0x01U
#define UVC_SUPPORTS_SET 0x02U
#define UVC_STATE_DISABLED 0x04U
#define UVC_AUTOUPDATE_CONTROL 0x08U
#define UVC_ASYNCHRONOUS_CONTROL 0x10U
/* USB Terminal Types */
#define TT_VENDOR_SPECIFIC 0x0100U
#define TT_STREAMING 0x0101U
/* Input Terminal Types */
#define ITT_VENDOR_SPECIFIC 0x0200U
#define ITT_CAMERA 0x0201U
#define ITT_MEDIA_TRANSPORT_INPUT 0x0202U
/*Output Terminal Types */
#define OTT_VENDOR_SPECIFIC 0x0300U
#define OTT_DISPLAY 0x0301U
#define OTT_MEDIA_TRANSPORT_OUTPUT 0x0302U
/* External Terminal Types */
#define EXTERNAL_VENDOR_SPECIFIC 0x0400U
#define COMPOSITE_CONNECTOR 0x0401U
#define SVIDEO_CONNECTOR 0x0402U
#define COMPONENT_CONNECTOR 0x0403U
/* VIDEO Commands enumeration */
typedef enum
{
VIDEO_CMD_START = 1U,
VIDEO_CMD_PLAY,
VIDEO_CMD_STOP,
} VIDEO_CMD_TypeDef;
typedef enum
{
VIDEO_OFFSET_NONE = 0U,
VIDEO_OFFSET_HALF,
VIDEO_OFFSET_FULL,
VIDEO_OFFSET_UNKNOWN,
} VIDEO_OffsetTypeDef;
typedef struct _VIDEO_DescHeader
{
uint8_t bLength;
uint8_t bDescriptorType;
uint8_t bDescriptorSubType;
} USBD_VIDEO_DescHeader_t;
typedef struct
{
uint8_t bLength;
uint8_t bDescriptorType;
uint8_t bDescriptorSubType;
uint8_t bFrameIndex;
uint8_t bmCapabilities;
uint16_t wWidth;
uint16_t wHeight;
uint32_t dwMinBitRate;
uint32_t dwMaxBitRate;
uint32_t dwMaxVideoFrameBufSize;
uint32_t dwDefaultFrameInterval;
uint8_t bFrameIntervalType;
uint32_t dwMinFrameInterval;
uint32_t dwMaxFrameInterval;
uint32_t dwFrameIntervalStep;
} __PACKED USBD_VIDEO_VSFrameDescTypeDef;
typedef struct
{
uint8_t cmd;
uint8_t data[USB_MAX_EP0_SIZE];
uint8_t len;
uint8_t unit;
} USBD_VIDEO_ControlTypeDef;
typedef struct
{
uint32_t interface;
uint32_t uvc_state;
uint8_t buffer[UVC_TOTAL_BUF_SIZE];
VIDEO_OffsetTypeDef offset;
USBD_VIDEO_ControlTypeDef control;
} USBD_VIDEO_HandleTypeDef;
typedef struct
{
int8_t (* Init)(void);
int8_t (* DeInit)(void);
int8_t (* Control)(uint8_t, uint8_t *, uint16_t);
int8_t (* Data)(uint8_t **, uint16_t *, uint16_t *);
uint8_t *pStrDesc;
} USBD_VIDEO_ItfTypeDef;
/* UVC uses only 26 first bytes */
typedef struct
{
uint16_t bmHint;
uint8_t bFormatIndex;
uint8_t bFrameIndex;
uint32_t dwFrameInterval;
uint16_t wKeyFrameRate;
uint16_t wPFrameRate;
uint16_t wCompQuality;
uint16_t wCompWindowSize;
uint16_t wDelay;
uint32_t dwMaxVideoFrameSize;
uint32_t dwMaxPayloadTransferSize;
uint32_t dwClockFrequency;
uint8_t bmFramingInfo;
uint8_t bPreferedVersion;
uint8_t bMinVersion;
uint8_t bMaxVersion;
} __PACKED USBD_VideoControlTypeDef;
extern USBD_ClassTypeDef USBD_VIDEO;
#define USBD_VIDEO_CLASS &USBD_VIDEO
/**
* @}
*/
/** @defgroup USB_CORE_Exported_Functions
* @{
*/
uint8_t USBD_VIDEO_RegisterInterface(USBD_HandleTypeDef *pdev, USBD_VIDEO_ItfTypeDef *fops);
/**
* @}
*/
#ifdef __cplusplus
}
#endif
#endif /* _USBD_VIDEO_H_ */

View File

@@ -0,0 +1,142 @@
/**
******************************************************************************
* @file usbd_video_if_template.h
* @author MCD Application Team
* @brief Template Header file for the video Interface application layer functions
******************************************************************************
* @attention
*
* <h2><center>&copy; Copyright (c) 2020 STMicroelectronics.
* All rights reserved.</center></h2>
*
* This software component is licensed by ST under Ultimate Liberty license
* SLA0044, the "License"; You may not use this file except in compliance with
* the License. You may obtain a copy of the License at:
* www.st.com/SLA0044
*
******************************************************************************
*/
/* Define to prevent recursive inclusion -------------------------------------*/
#ifndef __USBD_VIDEO_IF_H__
#define __USBD_VIDEO_IF_H__
#ifdef __cplusplus
extern "C" {
#endif
/* Includes ------------------------------------------------------------------*/
#include "usbd_video.h"
/* USER CODE BEGIN INCLUDE */
/* USER CODE END INCLUDE */
/** @addtogroup STM32_USB_OTG_DEVICE_LIBRARY
* @brief For Usb device.
* @{
*/
/** @defgroup USBD_VIDEO_IF
* @brief Usb VIDEO interface device module.
* @{
*/
/** @defgroup USBD_VIDEO_IF_Exported_Defines
* @brief Defines.
* @{
*/
/* USER CODE BEGIN EXPORTED_DEFINES */
/* USER CODE END EXPORTED_DEFINES */
/**
* @}
*/
/** @defgroup USBD_VIDEO_IF_Exported_Types
* @brief Types.
* @{
*/
/* USER CODE BEGIN EXPORTED_TYPES */
/* USER CODE END EXPORTED_TYPES */
/**
* @}
*/
/** @defgroup USBD_VIDEO_IF_Exported_Macros
* @brief Aliases.
* @{
*/
/* USER CODE BEGIN EXPORTED_MACRO */
/* USER CODE END EXPORTED_MACRO */
/**
* @}
*/
/** @defgroup USBD_VIDEO_IF_Exported_Variables
* @brief Public variables.
* @{
*/
/** VIDEO_IF Interface callback. */
extern USBD_VIDEO_ItfTypeDef USBD_VIDEO_fops_FS;
/* USER CODE BEGIN EXPORTED_VARIABLES */
/* USER CODE END EXPORTED_VARIABLES */
/**
* @}
*/
/** @defgroup USBD_VIDEO_IF_Exported_FunctionsPrototype
* @brief Public functions declaration.
* @{
*/
/**
* @brief Manages the DMA full transfer complete event.
* @retval None
*/
void TransferComplete_CallBack_FS(void);
/**
* @brief Manages the DMA half transfer complete event.
* @retval None
*/
void HalfTransfer_CallBack_FS(void);
/* USER CODE BEGIN EXPORTED_FUNCTIONS */
/* USER CODE END EXPORTED_FUNCTIONS */
/**
* @}
*/
/**
* @}
*/
/**
* @}
*/
#ifdef __cplusplus
}
#endif
#endif /* USBD_VIDEO_IF_H_ */
/************************ (C) COPYRIGHT STMicroelectronics *****END OF FILE****/

1051
Class/VIDEO/Src/usbd_video.c Normal file

File diff suppressed because it is too large Load Diff

View File

@@ -0,0 +1,296 @@
/**
******************************************************************************
* @file usbd_video_if_template.c
* @author MCD Application Team
* @brief Template file for Video Interface application layer functions
******************************************************************************
* @attention
*
* <h2><center>&copy; Copyright (c) 2020 STMicroelectronics.
* All rights reserved.</center></h2>
*
* This software component is licensed by ST under Ultimate Liberty license
* SLA0044, the "License"; You may not use this file except in compliance with
* the License. You may obtain a copy of the License at:
* www.st.com/SLA0044
*
******************************************************************************
*/
/* Includes ------------------------------------------------------------------*/
#include "usbd_video_if.h"
/* Include you image binary file here
Binary image template shall provide:
- tImagesList: table containing pointers to all images
- tImagesSizes: table containing sizes of each image respectively
- img_count: global image counter variable
- IMG_NBR: Total image number
To generate such file, it is possible to use tools converting video to MJPEG then to JPEG images.
*/
/* #include "img_bin.h" */
/* USER CODE BEGIN INCLUDE */
/* USER CODE END INCLUDE */
/* Private typedef -----------------------------------------------------------*/
/* Private define ------------------------------------------------------------*/
/* Private macro -------------------------------------------------------------*/
/* USER CODE BEGIN PV */
/* Private variables ---------------------------------------------------------*/
/* USER CODE END PV */
/** @addtogroup STM32_USB_OTG_DEVICE_LIBRARY
* @brief Usb device library.
* @{
*/
/** @addtogroup USBD_VIDEO_IF
* @{
*/
/** @defgroup USBD_VIDEO_IF_Private_TypesDefinitions
* @brief Private types.
* @{
*/
/* USER CODE BEGIN PRIVATE_TYPES */
/* USER CODE END PRIVATE_TYPES */
/**
* @}
*/
/** @defgroup USBD_VIDEO_IF_Private_Defines
* @brief Private defines.
* @{
*/
/* USER CODE BEGIN PRIVATE_DEFINES */
/* USER CODE END PRIVATE_DEFINES */
/**
* @}
*/
/** @defgroup USBD_VIDEO_IF_Private_Macros
* @brief Private macros.
* @{
*/
/* USER CODE BEGIN PRIVATE_MACRO */
/* USER CODE END PRIVATE_MACRO */
/**
* @}
*/
/** @defgroup USBD_VIDEO_IF_Private_Variables
* @brief Private variables.
* @{
*/
/* USER CODE BEGIN PRIVATE_VARIABLES */
/* USER CODE END PRIVATE_VARIABLES */
/**
* @}
*/
/** @defgroup USBD_VIDEO_IF_Exported_Variables
* @brief Public variables.
* @{
*/
/* USER CODE BEGIN EXPORTED_VARIABLES */
/* USER CODE END EXPORTED_VARIABLES */
/**
* @}
*/
/** @defgroup USBD_VIDEO_IF_Private_FunctionPrototypes
* @brief Private functions declaration.
* @{
*/
static int8_t VIDEO_Itf_Init(void);
static int8_t VIDEO_Itf_DeInit(void);
static int8_t VIDEO_Itf_Control(uint8_t cmd, uint8_t *pbuf, uint16_t length);
static int8_t VIDEO_Itf_Data(uint8_t **pbuf, uint16_t *psize, uint16_t *pcktidx);
/* USER CODE BEGIN PRIVATE_FUNCTIONS_DECLARATION */
/* USER CODE END PRIVATE_FUNCTIONS_DECLARATION */
/**
* @}
*/
USBD_VIDEO_ItfTypeDef USBD_VIDEO_fops_FS =
{
VIDEO_Itf_Init,
VIDEO_Itf_DeInit,
VIDEO_Itf_Control,
VIDEO_Itf_Data,
};
/* Private functions ---------------------------------------------------------*/
/**
* @brief Initializes the VIDEO media low layer over USB FS IP
* @param VIDEOFreq: VIDEO frequency used to play the VIDEO stream.
* @param Volume: Initial volume level (from 0 (Mute) to 100 (Max))
* @param options: Reserved for future use
* @retval USBD_OK if all operations are OK else USBD_FAIL
*/
static int8_t VIDEO_Itf_Init(void)
{
/*
Add your initialization code here
*/
return (0);
}
/**
* @brief TEMPLATE_DeInit
* DeInitializes the UVC media low layer
* @param None
* @retval Result of the operation: USBD_OK if all operations are OK else USBD_FAIL
*/
static int8_t VIDEO_Itf_DeInit(void)
{
/*
Add your deinitialization code here
*/
return (0);
}
/**
* @brief TEMPLATE_Control
* Manage the UVC class requests
* @param Cmd: Command code
* @param Buf: Buffer containing command data (request parameters)
* @param Len: Number of data to be sent (in bytes)
* @retval Result of the operation: USBD_OK if all operations are OK else USBD_FAIL
*/
static int8_t VIDEO_Itf_Control(uint8_t cmd, uint8_t *pbuf, uint16_t length)
{
return (0);
}
/**
* @brief TEMPLATE_Data
* Manage the UVC data packets
* @param pbuf: pointer to the buffer data to be filled
* @param psize: pointer tot he current packet size to be filled
* @param pcktidx: pointer to the current packet index in the current image
* @retval Result of the operation: USBD_OK if all operations are OK else USBD_FAIL
*/
static int8_t VIDEO_Itf_Data(uint8_t **pbuf, uint16_t *psize, uint16_t *pcktidx)
{
/*
Implementation of this function is mandatory to provide the video data to the USB video class
This function shall parse the MJPEG images and provide each time the buffer packet relative to
current packet index and its size.
If the packet is the first packet in the current MJPEG image, then packet size shall be zero and
the pbuf is ignored and pcktidx shall be zero.
Below is typical implementation of this function based on a binary image template.
Binary image template shall provide:
- tImagesList: table containing pointers to all images
- tImagesSizes: table containing sizes of each image respectively
- img_count: global image counter variable
- IMG_NBR: Total image number
To generate such file, it is possible to use tools converting video to MJPEG then to JPEG images.
*/
const uint8_t *(*ImagePtr) = tImagesList;
uint32_t packet_count = (tImagesSizes[img_count]) / ((uint16_t)(UVC_PACKET_SIZE - (UVC_HEADER_PACKET_CNT * 2U)));
uint32_t packet_remainder = (tImagesSizes[img_count]) % ((uint16_t)(UVC_PACKET_SIZE - (UVC_HEADER_PACKET_CNT * 2U)));
static uint8_t packet_index = 0;
/* Check if end of current image has been reached */
if (packet_index < packet_count)
{
/* Set the current packet size */
*psize = (uint16_t)UVC_PACKET_SIZE;
/* Get the pointer to the next packet to be transmitted */
*pbuf = (uint8_t *)(*(ImagePtr + img_count) + packet_index * ((uint16_t)(UVC_PACKET_SIZE - (UVC_HEADER_PACKET_CNT * 2U))));
}
else if ((packet_index == packet_count))
{
if (packet_remainder != 0U)
{
/* Get the pointer to the next packet to be transmitted */
*pbuf = (uint8_t *)(*(ImagePtr + img_count) + packet_index * ((uint16_t)(UVC_PACKET_SIZE - (UVC_HEADER_PACKET_CNT * 2U))));
/* Set the current packet size */
*psize = packet_remainder + (UVC_HEADER_PACKET_CNT * 2U);
}
else
{
packet_index++;
/* New image to be started, send only the packet header */
*psize = 2;
}
}
else
{
/* New image to be started, send only the packet header */
*psize = 2;
}
/* Update the packet index */
*pcktidx = packet_index;
/* Increment the packet count and check if it reached the end of current image buffer */
if (packet_index++ >= (packet_count + 1))
{
/* Reset the packet count to zero */
packet_index = 0U;
/* Move to the next image in the images table */
img_count++;
HAL_Delay(USBD_VIDEO_IMAGE_LAPS);
/* Check if images count has been reached, then reset to zero (go back to first image in circular loop) */
if (img_count == IMG_NBR)
{
img_count = 0U;
}
}
return (0);
}
/* USER CODE BEGIN PRIVATE_FUNCTIONS_IMPLEMENTATION */
/* USER CODE END PRIVATE_FUNCTIONS_IMPLEMENTATION */
/**
* @}
*/
/**
* @}
*/
/************************ (C) COPYRIGHT STMicroelectronics *****END OF FILE****/

View File

@@ -44,50 +44,101 @@ extern "C" {
* @{ * @{
*/ */
#define USBD_MAX_NUM_INTERFACES 1U #define USBD_MAX_NUM_INTERFACES 1U
#define USBD_MAX_NUM_CONFIGURATION 1U #define USBD_MAX_NUM_CONFIGURATION 1U
#define USBD_MAX_STR_DESC_SIZ 0x100U #define USBD_MAX_STR_DESC_SIZ 0x100U
#define USBD_SELF_POWERED 1U #define USBD_SELF_POWERED 1U
#define USBD_DEBUG_LEVEL 2U #define USBD_DEBUG_LEVEL 2U
/* ECM, RNDIS, DFU Class Config */ /* ECM, RNDIS, DFU Class Config */
#define USBD_SUPPORT_USER_STRING_DESC 1U #define USBD_SUPPORT_USER_STRING_DESC 1U
/* BillBoard Class Config */ /* BillBoard Class Config */
#define USBD_CLASS_USER_STRING_DESC 1U #define USBD_CLASS_USER_STRING_DESC 1U
#define USBD_CLASS_BOS_ENABLED 1U #define USBD_CLASS_BOS_ENABLED 1U
#define USB_BB_MAX_NUM_ALT_MODE 0x2U #define USB_BB_MAX_NUM_ALT_MODE 0x2U
/* MSC Class Config */ /* MSC Class Config */
#define MSC_MEDIA_PACKET 8192U #define MSC_MEDIA_PACKET 8192U
/* CDC Class Config */ /* CDC Class Config */
#define USBD_CDC_INTERVAL 2000U #define USBD_CDC_INTERVAL 2000U
/* DFU Class Config */ /* DFU Class Config */
#define USBD_DFU_MAX_ITF_NUM 1U #define USBD_DFU_MAX_ITF_NUM 1U
#define USBD_DFU_XFERS_IZE 1024U #define USBD_DFU_XFERS_IZE 1024U
/* AUDIO Class Config */ /* AUDIO Class Config */
#define USBD_AUDIO_FREQ 22100U #define USBD_AUDIO_FREQ 22100U
/* CustomHID Class Config */
#define CUSTOM_HID_HS_BINTERVAL 0x05U
#define CUSTOM_HID_FS_BINTERVAL 0x05U
#define USBD_CUSTOMHID_OUTREPORT_BUF_SIZE 0x02U
#define USBD_CUSTOM_HID_REPORT_DESC_SIZE 163U
/* VIDEO Class Config */
#define UVC_1_1 /* #define UVC_1_0 */
/* To be used only with YUY2 and NV12 Video format, shouldn't be defined for MJPEG format */
#define USBD_UVC_FORMAT_UNCOMPRESSED
#ifdef USBD_UVC_FORMAT_UNCOMPRESSED
#define UVC_BITS_PER_PIXEL 12U
#define UVC_UNCOMPRESSED_GUID UVC_GUID_NV12 /* UVC_GUID_YUY2 */
/* refer to Table 3-18 Color Matching Descriptor video class v1.1 */
#define UVC_COLOR_PRIMARIE 0x01U
#define UVC_TFR_CHARACTERISTICS 0x01U
#define UVC_MATRIX_COEFFICIENTS 0x04U
#endif
/* Video Stream frame width and height */
#define UVC_WIDTH 176U
#define UVC_HEIGHT 144U
/* bEndpointAddress in Endpoint Descriptor */
#define UVC_IN_EP 0x81U
#define UVC_CAM_FPS_FS 10U
#define UVC_CAM_FPS_HS 5U
#define UVC_ISO_FS_MPS 512U
#define UVC_ISO_HS_MPS 512U
#define UVC_PACKET_SIZE UVC_ISO_FS_MPS
/* To be used with Device Only IP supporting double buffer mode */
/* #define UVC_HEADER_PACKET_CNT 0x02U */
/* #define UVC_PACKET_SIZE (UVC_ISO_FS_MPS * UVC_HEADER_PACKET_CNT) */
#define UVC_MAX_FRAME_SIZE (UVC_WIDTH * UVC_HEIGHT * 16U / 8U)
/** @defgroup USBD_Exported_Macros /** @defgroup USBD_Exported_Macros
* @{ * @{
*/ */
/* Memory management macros */ /* Memory management macros make sure to use static memory allocation */
#define USBD_malloc malloc /** Alias for memory allocation. */
#define USBD_free free #define USBD_malloc (void *)USBD_static_malloc
#define USBD_memset memset
#define USBD_memcpy memcpy /** Alias for memory release. */
#define USBD_Delay HAL_Delay #define USBD_free USBD_static_free
/** Alias for memory set. */
#define USBD_memset memset
/** Alias for memory copy. */
#define USBD_memcpy memcpy
/** Alias for delay. */
#define USBD_Delay HAL_Delay
/* DEBUG macros */ /* DEBUG macros */
#if (USBD_DEBUG_LEVEL > 0U) #if (USBD_DEBUG_LEVEL > 0U)
#define USBD_UsrLog(...) do { \ #define USBD_UsrLog(...) do { \
printf(__VA_ARGS__); \ printf(__VA_ARGS__); \
printf("\n"); \ printf("\n"); \
} while (0) } while (0)
#else #else
#define USBD_UsrLog(...) do {} while (0) #define USBD_UsrLog(...) do {} while (0)
#endif #endif
@@ -95,20 +146,20 @@ extern "C" {
#if (USBD_DEBUG_LEVEL > 1U) #if (USBD_DEBUG_LEVEL > 1U)
#define USBD_ErrLog(...) do { \ #define USBD_ErrLog(...) do { \
printf("ERROR: ") ; \ printf("ERROR: ") ; \
printf(__VA_ARGS__); \ printf(__VA_ARGS__); \
printf("\n"); \ printf("\n"); \
} while (0) } while (0)
#else #else
#define USBD_ErrLog(...) do {} while (0) #define USBD_ErrLog(...) do {} while (0)
#endif #endif
#if (USBD_DEBUG_LEVEL > 2U) #if (USBD_DEBUG_LEVEL > 2U)
#define USBD_DbgLog(...) do { \ #define USBD_DbgLog(...) do { \
printf("DEBUG : ") ; \ printf("DEBUG : ") ; \
printf(__VA_ARGS__); \ printf(__VA_ARGS__); \
printf("\n"); \ printf("\n"); \
} while (0) } while (0)
#else #else
#define USBD_DbgLog(...) do {} while (0) #define USBD_DbgLog(...) do {} while (0)
#endif #endif
@@ -149,6 +200,9 @@ extern "C" {
/** @defgroup USBD_CONF_Exported_FunctionsPrototype /** @defgroup USBD_CONF_Exported_FunctionsPrototype
* @{ * @{
*/ */
/* Exported functions -------------------------------------------------------*/
void *USBD_static_malloc(uint32_t size);
void USBD_static_free(void *p);
/** /**
* @} * @}
*/ */

View File

@@ -149,8 +149,8 @@ void USBD_LL_Delay(uint32_t Delay);
*/ */
/** /**
* @} * @}
*/ */
/************************ (C) COPYRIGHT STMicroelectronics *****END OF FILE****/ /************************ (C) COPYRIGHT STMicroelectronics *****END OF FILE****/

View File

@@ -96,8 +96,8 @@ void USBD_GetString(uint8_t *desc, uint8_t *unicode, uint16_t *len);
*/ */
/** /**
* @} * @}
*/ */
/************************ (C) COPYRIGHT STMicroelectronics *****END OF FILE****/ /************************ (C) COPYRIGHT STMicroelectronics *****END OF FILE****/

View File

@@ -61,6 +61,10 @@ extern "C" {
#define USBD_SELF_POWERED 1U #define USBD_SELF_POWERED 1U
#endif /*USBD_SELF_POWERED */ #endif /*USBD_SELF_POWERED */
#ifndef USBD_MAX_POWER
#define USBD_MAX_POWER 0x32U /* 100 mA */
#endif /* USBD_MAX_POWER */
#ifndef USBD_SUPPORT_USER_STRING_DESC #ifndef USBD_SUPPORT_USER_STRING_DESC
#define USBD_SUPPORT_USER_STRING_DESC 0U #define USBD_SUPPORT_USER_STRING_DESC 0U
#endif /* USBD_SUPPORT_USER_STRING_DESC */ #endif /* USBD_SUPPORT_USER_STRING_DESC */
@@ -114,6 +118,7 @@ extern "C" {
#define USB_DESC_TYPE_ENDPOINT 0x05U #define USB_DESC_TYPE_ENDPOINT 0x05U
#define USB_DESC_TYPE_DEVICE_QUALIFIER 0x06U #define USB_DESC_TYPE_DEVICE_QUALIFIER 0x06U
#define USB_DESC_TYPE_OTHER_SPEED_CONFIGURATION 0x07U #define USB_DESC_TYPE_OTHER_SPEED_CONFIGURATION 0x07U
#define USB_DESC_TYPE_IAD 0x0BU
#define USB_DESC_TYPE_BOS 0x0FU #define USB_DESC_TYPE_BOS 0x0FU
#define USB_CONFIG_REMOTE_WAKEUP 0x02U #define USB_CONFIG_REMOTE_WAKEUP 0x02U
@@ -125,6 +130,11 @@ extern "C" {
#define USB_DEVICE_CAPABITY_TYPE 0x10U #define USB_DEVICE_CAPABITY_TYPE 0x10U
#define USB_CONF_DESC_SIZE 0x09U
#define USB_IF_DESC_SIZE 0x09U
#define USB_EP_DESC_SIZE 0x07U
#define USB_IAD_DESC_SIZE 0x08U
#define USB_HS_MAX_PACKET_SIZE 512U #define USB_HS_MAX_PACKET_SIZE 512U
#define USB_FS_MAX_PACKET_SIZE 64U #define USB_FS_MAX_PACKET_SIZE 64U
#define USB_MAX_EP0_SIZE 64U #define USB_MAX_EP0_SIZE 64U
@@ -150,7 +160,6 @@ extern "C" {
#define USBD_EP_TYPE_BULK 0x02U #define USBD_EP_TYPE_BULK 0x02U
#define USBD_EP_TYPE_INTR 0x03U #define USBD_EP_TYPE_INTR 0x03U
/** /**
* @} * @}
*/ */
@@ -173,8 +182,7 @@ typedef struct
{ {
uint8_t bLength; uint8_t bLength;
uint8_t bDescriptorType; uint8_t bDescriptorType;
uint8_t wDescriptorLengthLow; uint16_t wTotalLength;
uint8_t wDescriptorLengthHigh;
uint8_t bNumInterfaces; uint8_t bNumInterfaces;
uint8_t bConfigurationValue; uint8_t bConfigurationValue;
uint8_t iConfiguration; uint8_t iConfiguration;
@@ -190,6 +198,15 @@ typedef struct
uint8_t bNumDeviceCaps; uint8_t bNumDeviceCaps;
} USBD_BosDescTypedef; } USBD_BosDescTypedef;
typedef struct
{
uint8_t bLength;
uint8_t bDescriptorType;
uint8_t bEndpointAddress;
uint8_t bmAttributes;
uint16_t wMaxPacketSize;
uint8_t bInterval;
} USBD_EpDescTypedef;
struct _USBD_HandleTypeDef; struct _USBD_HandleTypeDef;
@@ -274,10 +291,10 @@ typedef struct _USBD_HandleTypeDef
USBD_SpeedTypeDef dev_speed; USBD_SpeedTypeDef dev_speed;
USBD_EndpointTypeDef ep_in[16]; USBD_EndpointTypeDef ep_in[16];
USBD_EndpointTypeDef ep_out[16]; USBD_EndpointTypeDef ep_out[16];
uint32_t ep0_state; __IO uint32_t ep0_state;
uint32_t ep0_data_len; uint32_t ep0_data_len;
uint8_t dev_state; __IO uint8_t dev_state;
uint8_t dev_old_state; __IO uint8_t dev_old_state;
uint8_t dev_address; uint8_t dev_address;
uint8_t dev_connection_status; uint8_t dev_connection_status;
uint8_t dev_test_mode; uint8_t dev_test_mode;
@@ -317,11 +334,21 @@ __STATIC_INLINE uint16_t SWAPBYTE(uint8_t *addr)
return _SwapVal; return _SwapVal;
} }
#ifndef LOBYTE
#define LOBYTE(x) ((uint8_t)((x) & 0x00FFU)) #define LOBYTE(x) ((uint8_t)((x) & 0x00FFU))
#define HIBYTE(x) ((uint8_t)(((x) & 0xFF00U) >> 8U)) #endif
#define MIN(a, b) (((a) < (b)) ? (a) : (b))
#define MAX(a, b) (((a) > (b)) ? (a) : (b))
#ifndef HIBYTE
#define HIBYTE(x) ((uint8_t)(((x) & 0xFF00U) >> 8U))
#endif
#ifndef MIN
#define MIN(a, b) (((a) < (b)) ? (a) : (b))
#endif
#ifndef MAX
#define MAX(a, b) (((a) > (b)) ? (a) : (b))
#endif
#if defined ( __GNUC__ ) #if defined ( __GNUC__ )
#ifndef __weak #ifndef __weak
@@ -388,6 +415,6 @@ __STATIC_INLINE uint16_t SWAPBYTE(uint8_t *addr)
*/ */
/** /**
* @} * @}
*/ */
/************************ (C) COPYRIGHT STMicroelectronics *****END OF FILE****/ /************************ (C) COPYRIGHT STMicroelectronics *****END OF FILE****/

View File

@@ -109,6 +109,6 @@ uint32_t USBD_GetRxCount(USBD_HandleTypeDef *pdev, uint8_t ep_addr);
*/ */
/** /**
* @} * @}
*/ */
/************************ (C) COPYRIGHT STMicroelectronics *****END OF FILE****/ /************************ (C) COPYRIGHT STMicroelectronics *****END OF FILE****/

View File

@@ -21,6 +21,7 @@
/* Includes ------------------------------------------------------------------*/ /* Includes ------------------------------------------------------------------*/
#include "usbd_core.h" #include "usbd_core.h"
#include "usbd_hid.h" /* Include class header file */
/* Private typedef -----------------------------------------------------------*/ /* Private typedef -----------------------------------------------------------*/
/* Private define ------------------------------------------------------------*/ /* Private define ------------------------------------------------------------*/
/* Private macro -------------------------------------------------------------*/ /* Private macro -------------------------------------------------------------*/
@@ -168,14 +169,14 @@ uint8_t USBD_LL_IsStallEP(USBD_HandleTypeDef *pdev, uint8_t ep_addr)
/** /**
* @brief Assigns a USB address to the device. * @brief Assigns a USB address to the device.
* @param pdev: Device handle * @param pdev: Device handle
* @param ep_addr: Endpoint Number * @param dev_addr: Endpoint Number
* @retval USBD Status * @retval USBD Status
*/ */
USBD_StatusTypeDef USBD_LL_SetUSBAddress(USBD_HandleTypeDef *pdev, USBD_StatusTypeDef USBD_LL_SetUSBAddress(USBD_HandleTypeDef *pdev,
uint8_t dev_addr) uint8_t dev_addr)
{ {
UNUSED(pdev); UNUSED(pdev);
UNUSED(ep_addr); UNUSED(dev_addr);
return USBD_OK; return USBD_OK;
} }
@@ -223,7 +224,7 @@ USBD_StatusTypeDef USBD_LL_PrepareReceive(USBD_HandleTypeDef *pdev,
* @brief Returns the last transferred packet size. * @brief Returns the last transferred packet size.
* @param pdev: Device handle * @param pdev: Device handle
* @param ep_addr: Endpoint Number * @param ep_addr: Endpoint Number
* @retval Recived Data Size * @retval Received Data Size
*/ */
uint32_t USBD_LL_GetRxDataSize(USBD_HandleTypeDef *pdev, uint8_t ep_addr) uint32_t USBD_LL_GetRxDataSize(USBD_HandleTypeDef *pdev, uint8_t ep_addr)
{ {
@@ -233,6 +234,27 @@ uint32_t USBD_LL_GetRxDataSize(USBD_HandleTypeDef *pdev, uint8_t ep_addr)
return 0U; return 0U;
} }
/**
* @brief Static single allocation.
* @param size: Size of allocated memory
* @retval None
*/
void *USBD_static_malloc(uint32_t size)
{
static uint32_t mem[(sizeof(USBD_HID_HandleTypeDef) / 4) + 1]; /* On 32-bit boundary */
return mem;
}
/**
* @brief Dummy memory free
* @param p: Pointer to allocated memory address
* @retval None
*/
void USBD_static_free(void *p)
{
}
/** /**
* @brief Delays routine for the USB Device Library. * @brief Delays routine for the USB Device Library.
* @param Delay: Delay in ms * @param Delay: Delay in ms

View File

@@ -21,71 +21,71 @@
#include "usbd_core.h" #include "usbd_core.h"
/** @addtogroup STM32_USBD_DEVICE_LIBRARY /** @addtogroup STM32_USBD_DEVICE_LIBRARY
* @{ * @{
*/ */
/** @defgroup USBD_CORE /** @defgroup USBD_CORE
* @brief usbd core module * @brief usbd core module
* @{ * @{
*/ */
/** @defgroup USBD_CORE_Private_TypesDefinitions /** @defgroup USBD_CORE_Private_TypesDefinitions
* @{ * @{
*/ */
/** /**
* @} * @}
*/ */
/** @defgroup USBD_CORE_Private_Defines /** @defgroup USBD_CORE_Private_Defines
* @{ * @{
*/ */
/** /**
* @} * @}
*/ */
/** @defgroup USBD_CORE_Private_Macros /** @defgroup USBD_CORE_Private_Macros
* @{ * @{
*/ */
/** /**
* @} * @}
*/ */
/** @defgroup USBD_CORE_Private_FunctionPrototypes /** @defgroup USBD_CORE_Private_FunctionPrototypes
* @{ * @{
*/ */
/** /**
* @} * @}
*/ */
/** @defgroup USBD_CORE_Private_Variables /** @defgroup USBD_CORE_Private_Variables
* @{ * @{
*/ */
/** /**
* @} * @}
*/ */
/** @defgroup USBD_CORE_Private_Functions /** @defgroup USBD_CORE_Private_Functions
* @{ * @{
*/ */
/** /**
* @brief USBD_Init * @brief USBD_Init
* Initializes the device stack and load the class driver * Initializes the device stack and load the class driver
* @param pdev: device instance * @param pdev: device instance
* @param pdesc: Descriptor structure address * @param pdesc: Descriptor structure address
* @param id: Low level core index * @param id: Low level core index
* @retval None * @retval None
*/ */
USBD_StatusTypeDef USBD_Init(USBD_HandleTypeDef *pdev, USBD_StatusTypeDef USBD_Init(USBD_HandleTypeDef *pdev,
USBD_DescriptorsTypeDef *pdesc, uint8_t id) USBD_DescriptorsTypeDef *pdesc, uint8_t id)
{ {
@@ -100,16 +100,10 @@ USBD_StatusTypeDef USBD_Init(USBD_HandleTypeDef *pdev,
return USBD_FAIL; return USBD_FAIL;
} }
/* Unlink previous class */ /* Unlink previous class resources */
if (pdev->pClass != NULL) pdev->pClass = NULL;
{ pdev->pUserData = NULL;
pdev->pClass = NULL; pdev->pConfDesc = NULL;
}
if (pdev->pConfDesc != NULL)
{
pdev->pConfDesc = NULL;
}
/* Assign USBD Descriptors */ /* Assign USBD Descriptors */
if (pdesc != NULL) if (pdesc != NULL)
@@ -128,15 +122,18 @@ USBD_StatusTypeDef USBD_Init(USBD_HandleTypeDef *pdev,
} }
/** /**
* @brief USBD_DeInit * @brief USBD_DeInit
* Re-Initialize th device library * Re-Initialize the device library
* @param pdev: device instance * @param pdev: device instance
* @retval status: status * @retval status: status
*/ */
USBD_StatusTypeDef USBD_DeInit(USBD_HandleTypeDef *pdev) USBD_StatusTypeDef USBD_DeInit(USBD_HandleTypeDef *pdev)
{ {
USBD_StatusTypeDef ret; USBD_StatusTypeDef ret;
/* Disconnect the USB Device */
(void)USBD_LL_Stop(pdev);
/* Set Default State */ /* Set Default State */
pdev->dev_state = USBD_STATE_DEFAULT; pdev->dev_state = USBD_STATE_DEFAULT;
@@ -144,22 +141,15 @@ USBD_StatusTypeDef USBD_DeInit(USBD_HandleTypeDef *pdev)
if (pdev->pClass != NULL) if (pdev->pClass != NULL)
{ {
pdev->pClass->DeInit(pdev, (uint8_t)pdev->dev_config); pdev->pClass->DeInit(pdev, (uint8_t)pdev->dev_config);
pdev->pClass = NULL;
pdev->pUserData = NULL;
} }
if (pdev->pConfDesc != NULL) /* Free Device descriptors resources */
{ pdev->pDesc = NULL;
pdev->pConfDesc = NULL; pdev->pConfDesc = NULL;
}
/* Stop the low level driver */ /* DeInitialize low level driver */
ret = USBD_LL_Stop(pdev);
if (ret != USBD_OK)
{
return ret;
}
/* Initialize low level driver */
ret = USBD_LL_DeInit(pdev); ret = USBD_LL_DeInit(pdev);
return ret; return ret;
@@ -188,13 +178,18 @@ USBD_StatusTypeDef USBD_RegisterClass(USBD_HandleTypeDef *pdev, USBD_ClassTypeDe
pdev->pClass = pclass; pdev->pClass = pclass;
/* Get Device Configuration Descriptor */ /* Get Device Configuration Descriptor */
#ifdef USE_USB_FS #ifdef USE_USB_HS
pdev->pConfDesc = (void *)pdev->pClass->GetFSConfigDescriptor(&len); if (pdev->pClass->GetHSConfigDescriptor != NULL)
#else /* USE_USB_HS */ {
pdev->pConfDesc = (void *)pdev->pClass->GetHSConfigDescriptor(&len); pdev->pConfDesc = (void *)pdev->pClass->GetHSConfigDescriptor(&len);
}
#else /* Default USE_USB_FS */
if (pdev->pClass->GetFSConfigDescriptor != NULL)
{
pdev->pConfDesc = (void *)pdev->pClass->GetFSConfigDescriptor(&len);
}
#endif /* USE_USB_FS */ #endif /* USE_USB_FS */
return USBD_OK; return USBD_OK;
} }
@@ -218,31 +213,24 @@ USBD_StatusTypeDef USBD_Start(USBD_HandleTypeDef *pdev)
*/ */
USBD_StatusTypeDef USBD_Stop(USBD_HandleTypeDef *pdev) USBD_StatusTypeDef USBD_Stop(USBD_HandleTypeDef *pdev)
{ {
USBD_StatusTypeDef ret; /* Disconnect USB Device */
(void)USBD_LL_Stop(pdev);
/* Free Class Resources */ /* Free Class Resources */
if (pdev->pClass != NULL) if (pdev->pClass != NULL)
{ {
pdev->pClass->DeInit(pdev, (uint8_t)pdev->dev_config); (void)pdev->pClass->DeInit(pdev, (uint8_t)pdev->dev_config);
} }
if (pdev->pConfDesc != NULL) return USBD_OK;
{
pdev->pConfDesc = NULL;
}
/* Stop the low level driver */
ret = USBD_LL_Stop(pdev);
return ret;
} }
/** /**
* @brief USBD_RunTestMode * @brief USBD_RunTestMode
* Launch test mode process * Launch test mode process
* @param pdev: device instance * @param pdev: device instance
* @retval status * @retval status
*/ */
USBD_StatusTypeDef USBD_RunTestMode(USBD_HandleTypeDef *pdev) USBD_StatusTypeDef USBD_RunTestMode(USBD_HandleTypeDef *pdev)
{ {
/* Prevent unused argument compilation warning */ /* Prevent unused argument compilation warning */
@@ -252,12 +240,12 @@ USBD_StatusTypeDef USBD_RunTestMode(USBD_HandleTypeDef *pdev)
} }
/** /**
* @brief USBD_SetClassConfig * @brief USBD_SetClassConfig
* Configure device and start the interface * Configure device and start the interface
* @param pdev: device instance * @param pdev: device instance
* @param cfgidx: configuration index * @param cfgidx: configuration index
* @retval status * @retval status
*/ */
USBD_StatusTypeDef USBD_SetClassConfig(USBD_HandleTypeDef *pdev, uint8_t cfgidx) USBD_StatusTypeDef USBD_SetClassConfig(USBD_HandleTypeDef *pdev, uint8_t cfgidx)
{ {
@@ -273,12 +261,12 @@ USBD_StatusTypeDef USBD_SetClassConfig(USBD_HandleTypeDef *pdev, uint8_t cfgidx)
} }
/** /**
* @brief USBD_ClrClassConfig * @brief USBD_ClrClassConfig
* Clear current configuration * Clear current configuration
* @param pdev: device instance * @param pdev: device instance
* @param cfgidx: configuration index * @param cfgidx: configuration index
* @retval status: USBD_StatusTypeDef * @retval status: USBD_StatusTypeDef
*/ */
USBD_StatusTypeDef USBD_ClrClassConfig(USBD_HandleTypeDef *pdev, uint8_t cfgidx) USBD_StatusTypeDef USBD_ClrClassConfig(USBD_HandleTypeDef *pdev, uint8_t cfgidx)
{ {
/* Clear configuration and De-initialize the Class process */ /* Clear configuration and De-initialize the Class process */
@@ -292,11 +280,11 @@ USBD_StatusTypeDef USBD_ClrClassConfig(USBD_HandleTypeDef *pdev, uint8_t cfgidx)
/** /**
* @brief USBD_SetupStage * @brief USBD_LL_SetupStage
* Handle the setup stage * Handle the setup stage
* @param pdev: device instance * @param pdev: device instance
* @retval status * @retval status
*/ */
USBD_StatusTypeDef USBD_LL_SetupStage(USBD_HandleTypeDef *pdev, uint8_t *psetup) USBD_StatusTypeDef USBD_LL_SetupStage(USBD_HandleTypeDef *pdev, uint8_t *psetup)
{ {
USBD_StatusTypeDef ret; USBD_StatusTypeDef ret;
@@ -330,12 +318,13 @@ USBD_StatusTypeDef USBD_LL_SetupStage(USBD_HandleTypeDef *pdev, uint8_t *psetup)
} }
/** /**
* @brief USBD_DataOutStage * @brief USBD_LL_DataOutStage
* Handle data OUT stage * Handle data OUT stage
* @param pdev: device instance * @param pdev: device instance
* @param epnum: endpoint index * @param epnum: endpoint index
* @retval status * @param pdata: data pointer
*/ * @retval status
*/
USBD_StatusTypeDef USBD_LL_DataOutStage(USBD_HandleTypeDef *pdev, USBD_StatusTypeDef USBD_LL_DataOutStage(USBD_HandleTypeDef *pdev,
uint8_t epnum, uint8_t *pdata) uint8_t epnum, uint8_t *pdata)
{ {
@@ -356,11 +345,14 @@ USBD_StatusTypeDef USBD_LL_DataOutStage(USBD_HandleTypeDef *pdev,
} }
else else
{ {
if ((pdev->pClass->EP0_RxReady != NULL) && if (pdev->dev_state == USBD_STATE_CONFIGURED)
(pdev->dev_state == USBD_STATE_CONFIGURED))
{ {
pdev->pClass->EP0_RxReady(pdev); if (pdev->pClass->EP0_RxReady != NULL)
{
pdev->pClass->EP0_RxReady(pdev);
}
} }
(void)USBD_CtlSendStatus(pdev); (void)USBD_CtlSendStatus(pdev);
} }
} }
@@ -370,40 +362,40 @@ USBD_StatusTypeDef USBD_LL_DataOutStage(USBD_HandleTypeDef *pdev,
if (pdev->ep0_state == USBD_EP0_STATUS_OUT) if (pdev->ep0_state == USBD_EP0_STATUS_OUT)
{ {
/* /*
* STATUS PHASE completed, update ep0_state to idle * STATUS PHASE completed, update ep0_state to idle
*/ */
pdev->ep0_state = USBD_EP0_IDLE; pdev->ep0_state = USBD_EP0_IDLE;
(void)USBD_LL_StallEP(pdev, 0U); (void)USBD_LL_StallEP(pdev, 0U);
} }
#endif #endif
} }
} }
else if ((pdev->pClass->DataOut != NULL) &&
(pdev->dev_state == USBD_STATE_CONFIGURED))
{
ret = (USBD_StatusTypeDef)pdev->pClass->DataOut(pdev, epnum);
if (ret != USBD_OK)
{
return ret;
}
}
else else
{ {
/* should never be in this condition */ if (pdev->dev_state == USBD_STATE_CONFIGURED)
return USBD_FAIL; {
if (pdev->pClass->DataOut != NULL)
{
ret = (USBD_StatusTypeDef)pdev->pClass->DataOut(pdev, epnum);
if (ret != USBD_OK)
{
return ret;
}
}
}
} }
return USBD_OK; return USBD_OK;
} }
/** /**
* @brief USBD_DataInStage * @brief USBD_LL_DataInStage
* Handle data in stage * Handle data in stage
* @param pdev: device instance * @param pdev: device instance
* @param epnum: endpoint index * @param epnum: endpoint index
* @retval status * @retval status
*/ */
USBD_StatusTypeDef USBD_LL_DataInStage(USBD_HandleTypeDef *pdev, USBD_StatusTypeDef USBD_LL_DataInStage(USBD_HandleTypeDef *pdev,
uint8_t epnum, uint8_t *pdata) uint8_t epnum, uint8_t *pdata)
{ {
@@ -423,7 +415,7 @@ USBD_StatusTypeDef USBD_LL_DataInStage(USBD_HandleTypeDef *pdev,
(void)USBD_CtlContinueSendData(pdev, pdata, pep->rem_length); (void)USBD_CtlContinueSendData(pdev, pdata, pep->rem_length);
/* Prepare endpoint for premature end of transfer */ /* Prepare endpoint for premature end of transfer */
(void)USBD_LL_PrepareReceive(pdev, 0U, NULL, 0U); (void)USBD_LL_PrepareReceive(pdev, 0U, NULL, 0U);
} }
else else
{ {
@@ -440,10 +432,12 @@ USBD_StatusTypeDef USBD_LL_DataInStage(USBD_HandleTypeDef *pdev,
} }
else else
{ {
if ((pdev->pClass->EP0_TxSent != NULL) && if (pdev->dev_state == USBD_STATE_CONFIGURED)
(pdev->dev_state == USBD_STATE_CONFIGURED))
{ {
pdev->pClass->EP0_TxSent(pdev); if (pdev->pClass->EP0_TxSent != NULL)
{
pdev->pClass->EP0_TxSent(pdev);
}
} }
(void)USBD_LL_StallEP(pdev, 0x80U); (void)USBD_LL_StallEP(pdev, 0x80U);
(void)USBD_CtlReceiveStatus(pdev); (void)USBD_CtlReceiveStatus(pdev);
@@ -467,31 +461,31 @@ USBD_StatusTypeDef USBD_LL_DataInStage(USBD_HandleTypeDef *pdev,
pdev->dev_test_mode = 0U; pdev->dev_test_mode = 0U;
} }
} }
else if ((pdev->pClass->DataIn != NULL) &&
(pdev->dev_state == USBD_STATE_CONFIGURED))
{
ret = (USBD_StatusTypeDef)pdev->pClass->DataIn(pdev, epnum);
if (ret != USBD_OK)
{
return ret;
}
}
else else
{ {
/* should never be in this condition */ if (pdev->dev_state == USBD_STATE_CONFIGURED)
return USBD_FAIL; {
if (pdev->pClass->DataIn != NULL)
{
ret = (USBD_StatusTypeDef)pdev->pClass->DataIn(pdev, epnum);
if (ret != USBD_OK)
{
return ret;
}
}
}
} }
return USBD_OK; return USBD_OK;
} }
/** /**
* @brief USBD_LL_Reset * @brief USBD_LL_Reset
* Handle Reset event * Handle Reset event
* @param pdev: device instance * @param pdev: device instance
* @retval status * @retval status
*/ */
USBD_StatusTypeDef USBD_LL_Reset(USBD_HandleTypeDef *pdev) USBD_StatusTypeDef USBD_LL_Reset(USBD_HandleTypeDef *pdev)
{ {
@@ -501,12 +495,20 @@ USBD_StatusTypeDef USBD_LL_Reset(USBD_HandleTypeDef *pdev)
pdev->dev_config = 0U; pdev->dev_config = 0U;
pdev->dev_remote_wakeup = 0U; pdev->dev_remote_wakeup = 0U;
if (pdev->pClassData != NULL) if (pdev->pClass == NULL)
{ {
pdev->pClass->DeInit(pdev, (uint8_t)pdev->dev_config); return USBD_FAIL;
} }
/* Open EP0 OUT */ if (pdev->pClassData != NULL)
{
if (pdev->pClass->DeInit != NULL)
{
(void)pdev->pClass->DeInit(pdev, (uint8_t)pdev->dev_config);
}
}
/* Open EP0 OUT */
(void)USBD_LL_OpenEP(pdev, 0x00U, USBD_EP_TYPE_CTRL, USB_MAX_EP0_SIZE); (void)USBD_LL_OpenEP(pdev, 0x00U, USBD_EP_TYPE_CTRL, USB_MAX_EP0_SIZE);
pdev->ep_out[0x00U & 0xFU].is_used = 1U; pdev->ep_out[0x00U & 0xFU].is_used = 1U;
@@ -522,11 +524,11 @@ USBD_StatusTypeDef USBD_LL_Reset(USBD_HandleTypeDef *pdev)
} }
/** /**
* @brief USBD_LL_Reset * @brief USBD_LL_SetSpeed
* Handle Reset event * Handle Reset event
* @param pdev: device instance * @param pdev: device instance
* @retval status * @retval status
*/ */
USBD_StatusTypeDef USBD_LL_SetSpeed(USBD_HandleTypeDef *pdev, USBD_StatusTypeDef USBD_LL_SetSpeed(USBD_HandleTypeDef *pdev,
USBD_SpeedTypeDef speed) USBD_SpeedTypeDef speed)
{ {
@@ -536,11 +538,11 @@ USBD_StatusTypeDef USBD_LL_SetSpeed(USBD_HandleTypeDef *pdev,
} }
/** /**
* @brief USBD_Suspend * @brief USBD_LL_Suspend
* Handle Suspend event * Handle Suspend event
* @param pdev: device instance * @param pdev: device instance
* @retval status * @retval status
*/ */
USBD_StatusTypeDef USBD_LL_Suspend(USBD_HandleTypeDef *pdev) USBD_StatusTypeDef USBD_LL_Suspend(USBD_HandleTypeDef *pdev)
{ {
@@ -551,11 +553,11 @@ USBD_StatusTypeDef USBD_LL_Suspend(USBD_HandleTypeDef *pdev)
} }
/** /**
* @brief USBD_Resume * @brief USBD_LL_Resume
* Handle Resume event * Handle Resume event
* @param pdev: device instance * @param pdev: device instance
* @retval status * @retval status
*/ */
USBD_StatusTypeDef USBD_LL_Resume(USBD_HandleTypeDef *pdev) USBD_StatusTypeDef USBD_LL_Resume(USBD_HandleTypeDef *pdev)
{ {
@@ -568,19 +570,24 @@ USBD_StatusTypeDef USBD_LL_Resume(USBD_HandleTypeDef *pdev)
} }
/** /**
* @brief USBD_SOF * @brief USBD_LL_SOF
* Handle SOF event * Handle SOF event
* @param pdev: device instance * @param pdev: device instance
* @retval status * @retval status
*/ */
USBD_StatusTypeDef USBD_LL_SOF(USBD_HandleTypeDef *pdev) USBD_StatusTypeDef USBD_LL_SOF(USBD_HandleTypeDef *pdev)
{ {
if (pdev->pClass == NULL)
{
return USBD_FAIL;
}
if (pdev->dev_state == USBD_STATE_CONFIGURED) if (pdev->dev_state == USBD_STATE_CONFIGURED)
{ {
if (pdev->pClass->SOF != NULL) if (pdev->pClass->SOF != NULL)
{ {
pdev->pClass->SOF(pdev); (void)pdev->pClass->SOF(pdev);
} }
} }
@@ -588,43 +595,61 @@ USBD_StatusTypeDef USBD_LL_SOF(USBD_HandleTypeDef *pdev)
} }
/** /**
* @brief USBD_IsoINIncomplete * @brief USBD_LL_IsoINIncomplete
* Handle iso in incomplete event * Handle iso in incomplete event
* @param pdev: device instance * @param pdev: device instance
* @retval status * @retval status
*/ */
USBD_StatusTypeDef USBD_LL_IsoINIncomplete(USBD_HandleTypeDef *pdev, USBD_StatusTypeDef USBD_LL_IsoINIncomplete(USBD_HandleTypeDef *pdev,
uint8_t epnum) uint8_t epnum)
{ {
/* Prevent unused arguments compilation warning */ if (pdev->pClass == NULL)
UNUSED(pdev); {
UNUSED(epnum); return USBD_FAIL;
}
if (pdev->dev_state == USBD_STATE_CONFIGURED)
{
if (pdev->pClass->IsoINIncomplete != NULL)
{
(void)pdev->pClass->IsoINIncomplete(pdev, epnum);
}
}
return USBD_OK; return USBD_OK;
} }
/** /**
* @brief USBD_IsoOUTIncomplete * @brief USBD_LL_IsoOUTIncomplete
* Handle iso out incomplete event * Handle iso out incomplete event
* @param pdev: device instance * @param pdev: device instance
* @retval status * @retval status
*/ */
USBD_StatusTypeDef USBD_LL_IsoOUTIncomplete(USBD_HandleTypeDef *pdev, USBD_StatusTypeDef USBD_LL_IsoOUTIncomplete(USBD_HandleTypeDef *pdev,
uint8_t epnum) uint8_t epnum)
{ {
/* Prevent unused arguments compilation warning */ if (pdev->pClass == NULL)
UNUSED(pdev); {
UNUSED(epnum); return USBD_FAIL;
}
if (pdev->dev_state == USBD_STATE_CONFIGURED)
{
if (pdev->pClass->IsoOUTIncomplete != NULL)
{
(void)pdev->pClass->IsoOUTIncomplete(pdev, epnum);
}
}
return USBD_OK; return USBD_OK;
} }
/** /**
* @brief USBD_DevConnected * @brief USBD_LL_DevConnected
* Handle device connection event * Handle device connection event
* @param pdev: device instance * @param pdev: device instance
* @retval status * @retval status
*/ */
USBD_StatusTypeDef USBD_LL_DevConnected(USBD_HandleTypeDef *pdev) USBD_StatusTypeDef USBD_LL_DevConnected(USBD_HandleTypeDef *pdev)
{ {
/* Prevent unused argument compilation warning */ /* Prevent unused argument compilation warning */
@@ -634,11 +659,11 @@ USBD_StatusTypeDef USBD_LL_DevConnected(USBD_HandleTypeDef *pdev)
} }
/** /**
* @brief USBD_DevDisconnected * @brief USBD_LL_DevDisconnected
* Handle device disconnection event * Handle device disconnection event
* @param pdev: device instance * @param pdev: device instance
* @retval status * @retval status
*/ */
USBD_StatusTypeDef USBD_LL_DevDisconnected(USBD_HandleTypeDef *pdev) USBD_StatusTypeDef USBD_LL_DevDisconnected(USBD_HandleTypeDef *pdev)
{ {
/* Free Class Resources */ /* Free Class Resources */
@@ -646,24 +671,24 @@ USBD_StatusTypeDef USBD_LL_DevDisconnected(USBD_HandleTypeDef *pdev)
if (pdev->pClass != NULL) if (pdev->pClass != NULL)
{ {
pdev->pClass->DeInit(pdev, (uint8_t)pdev->dev_config); (void)pdev->pClass->DeInit(pdev, (uint8_t)pdev->dev_config);
} }
return USBD_OK; return USBD_OK;
} }
/** /**
* @} * @}
*/ */
/** /**
* @} * @}
*/ */
/** /**
* @} * @}
*/ */
/************************ (C) COPYRIGHT STMicroelectronics *****END OF FILE****/ /************************ (C) COPYRIGHT STMicroelectronics *****END OF FILE****/

File diff suppressed because it is too large Load Diff

View File

@@ -52,7 +52,7 @@ uint8_t *USBD_Class_UserStrDescriptor(USBD_SpeedTypeDef speed, uint8_t idx, uint
#endif /* USB_CLASS_USER_STRING_DESC */ #endif /* USB_CLASS_USER_STRING_DESC */
#if ((USBD_LPM_ENABLED == 1) || (USBD_CLASS_BOS_ENABLED == 1)) #if ((USBD_LPM_ENABLED == 1) || (USBD_CLASS_BOS_ENABLED == 1))
uint8_t *USBD_USR_BOSDescriptor(USBD_SpeedTypeDef speed , uint16_t *length); uint8_t *USBD_USR_BOSDescriptor(USBD_SpeedTypeDef speed, uint16_t *length);
#endif #endif
/* Private variables ---------------------------------------------------------*/ /* Private variables ---------------------------------------------------------*/
@@ -109,7 +109,7 @@ __ALIGN_BEGIN uint8_t USBD_DeviceDesc[USB_LEN_DEV_DESC] __ALIGN_END =
/* USB Device LPM BOS descriptor */ /* USB Device LPM BOS descriptor */
#if (USBD_LPM_ENABLED == 1) #if (USBD_LPM_ENABLED == 1)
#if defined ( __ICCARM__ ) /*!< IAR Compiler */ #if defined ( __ICCARM__ ) /*!< IAR Compiler */
#pragma data_alignment=4 #pragma data_alignment=4
#endif #endif
__ALIGN_BEGIN uint8_t USBD_BOSDesc[USB_SIZ_BOS_DESC] __ALIGN_END = __ALIGN_BEGIN uint8_t USBD_BOSDesc[USB_SIZ_BOS_DESC] __ALIGN_END =
{ {
@@ -132,87 +132,87 @@ __ALIGN_BEGIN uint8_t USBD_BOSDesc[USB_SIZ_BOS_DESC] __ALIGN_END =
/* USB Device Billboard BOS descriptor Template */ /* USB Device Billboard BOS descriptor Template */
#if (USBD_CLASS_BOS_ENABLED == 1) #if (USBD_CLASS_BOS_ENABLED == 1)
#if defined ( __ICCARM__ ) /*!< IAR Compiler */ #if defined ( __ICCARM__ ) /*!< IAR Compiler */
#pragma data_alignment=4 #pragma data_alignment=4
#endif #endif
__ALIGN_BEGIN uint8_t USBD_BOSDesc[USB_SIZ_BOS_DESC] __ALIGN_END = __ALIGN_BEGIN uint8_t USBD_BOSDesc[USB_SIZ_BOS_DESC] __ALIGN_END =
{ {
0x05, /* bLength */ 0x05, /* bLength */
USB_DESC_TYPE_BOS, /* Device Descriptor Type */ USB_DESC_TYPE_BOS, /* Device Descriptor Type */
USB_SIZ_BOS_DESC, /* Total length of BOS descriptor and all of its sub descs */ USB_SIZ_BOS_DESC, /* Total length of BOS descriptor and all of its sub descs */
0x00, 0x00,
0x04, /* The number of separate device capability descriptors in the BOS */ 0x04, /* The number of separate device capability descriptors in the BOS */
/* ----------- Device Capability Descriptor: CONTAINER_ID ---------- */ /* ----------- Device Capability Descriptor: CONTAINER_ID ---------- */
0x14, /* bLength */ 0x14, /* bLength */
0x10, /* bDescriptorType: DEVICE CAPABILITY Type */ 0x10, /* bDescriptorType: DEVICE CAPABILITY Type */
0x04, /* bDevCapabilityType: CONTAINER_ID */ 0x04, /* bDevCapabilityType: CONTAINER_ID */
0x00, /* bReserved */ 0x00, /* bReserved */
0xa7, 0xd6, 0x1b, 0xfa, /* ContainerID: This is a Unique 128-bit number GUID */ 0xa7, 0xd6, 0x1b, 0xfa, /* ContainerID: This is a Unique 128-bit number GUID */
0x91, 0xa6, 0xa8, 0x4e, 0x91, 0xa6, 0xa8, 0x4e,
0xa8, 0x21, 0x9f, 0x2b, 0xa8, 0x21, 0x9f, 0x2b,
0xaf, 0xf7, 0x94, 0xd4, 0xaf, 0xf7, 0x94, 0xd4,
/* ----------- Device Capability Descriptor: BillBoard ---------- */ /* ----------- Device Capability Descriptor: BillBoard ---------- */
0x34, /* bLength */ 0x34, /* bLength */
0x10, /* bDescriptorType: DEVICE CAPABILITY Type */ 0x10, /* bDescriptorType: DEVICE CAPABILITY Type */
0x0D, /* bDevCapabilityType: BILLBOARD_CAPABILITY */ 0x0D, /* bDevCapabilityType: BILLBOARD_CAPABILITY */
USBD_BB_URL_STRING_INDEX, /* iAddtionalInfoURL: Index of string descriptor providing a URL where the user can go to get more USBD_BB_URL_STRING_INDEX, /* iAddtionalInfoURL: Index of string descriptor providing a URL where the user can go to get more
detailed information about the product and the various Alternate Modes it supports */ detailed information about the product and the various Alternate Modes it supports */
0x02, /* bNumberOfAlternateModes: Number of Alternate modes supported. The 0x02, /* bNumberOfAlternateModes: Number of Alternate modes supported. The
maximum value that this field can be set to is MAX_NUM_ALT_MODE. */ maximum value that this field can be set to is MAX_NUM_ALT_MODE. */
0x00, /* bPreferredAlternateMode: Index of the preferred Alternate Mode. System 0x00, /* bPreferredAlternateMode: Index of the preferred Alternate Mode. System
software may use this information to provide the user with a better user experience. */ software may use this information to provide the user with a better user experience. */
0x00, 0x00, /* VCONN Power needed by the adapter for full functionality 000b = 1W */ 0x00, 0x00, /* VCONN Power needed by the adapter for full functionality 000b = 1W */
0x01,0x00,0x00,0x00, /* bmConfigured. 01b: Alternate Mode configuration not attempted or exited */ 0x01, 0x00, 0x00, 0x00, /* bmConfigured. 01b: Alternate Mode configuration not attempted or exited */
0x00,0x00,0x00,0x00, 0x00, 0x00, 0x00, 0x00,
0x00,0x00,0x00,0x00, 0x00, 0x00, 0x00, 0x00,
0x00,0x00,0x00,0x00, 0x00, 0x00, 0x00, 0x00,
0x00,0x00,0x00,0x00, 0x00, 0x00, 0x00, 0x00,
0x00,0x00,0x00,0x00, 0x00, 0x00, 0x00, 0x00,
0x00,0x00,0x00,0x00, 0x00, 0x00, 0x00, 0x00,
0x00,0x00,0x00,0x00, 0x00, 0x00, 0x00, 0x00,
0x21, 0x01, /* bcdVersion = 0x0121 */ 0x21, 0x01, /* bcdVersion = 0x0121 */
0x00, /* bAdditionalFailureInfo */ 0x00, /* bAdditionalFailureInfo */
0x00, /* bReserved */ 0x00, /* bReserved */
LOBYTE(USBD_VID), LOBYTE(USBD_VID),
HIBYTE(USBD_VID), /* wSVID[0]: Standard or Vendor ID. This shall match one of the SVIDs HIBYTE(USBD_VID), /* wSVID[0]: Standard or Vendor ID. This shall match one of the SVIDs
returned in response to a USB PD Discover SVIDs command */ returned in response to a USB PD Discover SVIDs command */
0x00, /* bAlternateMode[0] Index of the Alternate Mode within the SVID as 0x00, /* bAlternateMode[0] Index of the Alternate Mode within the SVID as
returned in response to a Discover Modes command. Example: returned in response to a Discover Modes command. Example:
0 <20> first Mode entry 0 <20> first Mode entry
1 <20> second mode entry */ 1 <20> second mode entry */
USBD_BB_ALTMODE0_STRING_INDEX, /* iAlternateModeString[0]: Index of string descriptor describing protocol. USBD_BB_ALTMODE0_STRING_INDEX, /* iAlternateModeString[0]: Index of string descriptor describing protocol.
It is optional to support this string. */ It is optional to support this string. */
LOBYTE(USBD_VID), LOBYTE(USBD_VID),
HIBYTE(USBD_VID), /* wSVID[1]: Standard or Vendor ID. This shall match one of the SVIDs HIBYTE(USBD_VID), /* wSVID[1]: Standard or Vendor ID. This shall match one of the SVIDs
returned in response to a USB PD Discover SVIDs command */ returned in response to a USB PD Discover SVIDs command */
0x01, /* bAlternateMode[1] Index of the Alternate Mode within the SVID as 0x01, /* bAlternateMode[1] Index of the Alternate Mode within the SVID as
returned in response to a Discover Modes command. Example: returned in response to a Discover Modes command. Example:
0 <20> first Mode entry 0 <20> first Mode entry
1 <20> second Mode entry */ 1 <20> second Mode entry */
USBD_BB_ALTMODE1_STRING_INDEX, /* iAlternateModeString[1]: Index of string descriptor describing protocol. USBD_BB_ALTMODE1_STRING_INDEX, /* iAlternateModeString[1]: Index of string descriptor describing protocol.
It is optional to support this string. */ It is optional to support this string. */
/* Alternate Mode Desc */ /* Alternate Mode Desc */
/* ----------- Device Capability Descriptor: BillBoard Alternate Mode Desc ---------- */ /* ----------- Device Capability Descriptor: BillBoard Alternate Mode Desc ---------- */
0x08, /* bLength */ 0x08, /* bLength */
0x10, /* bDescriptorType: Device Descriptor Type */ 0x10, /* bDescriptorType: Device Descriptor Type */
0x0F, /* bDevCapabilityType: BILLBOARD ALTERNATE MODE CAPABILITY */ 0x0F, /* bDevCapabilityType: BILLBOARD ALTERNATE MODE CAPABILITY */
0x00, /* bIndex: Index of Alternate Mode described in the Billboard Capability Desc */ 0x00, /* bIndex: Index of Alternate Mode described in the Billboard Capability Desc */
0x10, 0x00, 0x00, 0x00, /* dwAlternateModeVdo: contents of the Mode VDO for the alternate mode identified by bIndex */ 0x10, 0x00, 0x00, 0x00, /* dwAlternateModeVdo: contents of the Mode VDO for the alternate mode identified by bIndex */
0x08, /* bLength */ 0x08, /* bLength */
0x10, /* bDescriptorType: Device Descriptor Type */ 0x10, /* bDescriptorType: Device Descriptor Type */
0x0F, /* bDevCapabilityType: BILLBOARD ALTERNATE MODE CAPABILITY */ 0x0F, /* bDevCapabilityType: BILLBOARD ALTERNATE MODE CAPABILITY */
0x01, /* bIndex: Index of Alternate Mode described in the Billboard Capability Desc */ 0x01, /* bIndex: Index of Alternate Mode described in the Billboard Capability Desc */
0x20, 0x00, 0x00, 0x00, /* dwAlternateModeVdo: contents of the Mode VDO for the alternate mode identified by bIndex */ 0x20, 0x00, 0x00, 0x00, /* dwAlternateModeVdo: contents of the Mode VDO for the alternate mode identified by bIndex */
}; };
#endif #endif
@@ -395,10 +395,10 @@ static void Get_SerialNum(void)
* @param length : pointer to data length variable * @param length : pointer to data length variable
* @retval pointer to descriptor buffer * @retval pointer to descriptor buffer
*/ */
uint8_t *USBD_USR_BOSDescriptor(USBD_SpeedTypeDef speed , uint16_t *length) uint8_t *USBD_USR_BOSDescriptor(USBD_SpeedTypeDef speed, uint16_t *length)
{ {
*length = sizeof(USBD_BOSDesc); *length = sizeof(USBD_BOSDesc);
return (uint8_t*)USBD_BOSDesc; return (uint8_t *)USBD_BOSDesc;
} }
#endif #endif

View File

@@ -77,20 +77,25 @@
*/ */
/** /**
* @brief USBD_CtlSendData * @brief USBD_CtlSendData
* send data on the ctl pipe * send data on the ctl pipe
* @param pdev: device instance * @param pdev: device instance
* @param buff: pointer to data buffer * @param buff: pointer to data buffer
* @param len: length of data to be sent * @param len: length of data to be sent
* @retval status * @retval status
*/ */
USBD_StatusTypeDef USBD_CtlSendData(USBD_HandleTypeDef *pdev, USBD_StatusTypeDef USBD_CtlSendData(USBD_HandleTypeDef *pdev,
uint8_t *pbuf, uint32_t len) uint8_t *pbuf, uint32_t len)
{ {
/* Set EP0 State */ /* Set EP0 State */
pdev->ep0_state = USBD_EP0_DATA_IN; pdev->ep0_state = USBD_EP0_DATA_IN;
pdev->ep_in[0].total_length = len; pdev->ep_in[0].total_length = len;
#ifdef USBD_AVOID_PACKET_SPLIT_MPS
pdev->ep_in[0].rem_length = 0U;
#else
pdev->ep_in[0].rem_length = len; pdev->ep_in[0].rem_length = len;
#endif
/* Start the transfer */ /* Start the transfer */
(void)USBD_LL_Transmit(pdev, 0x00U, pbuf, len); (void)USBD_LL_Transmit(pdev, 0x00U, pbuf, len);
@@ -99,13 +104,13 @@ USBD_StatusTypeDef USBD_CtlSendData(USBD_HandleTypeDef *pdev,
} }
/** /**
* @brief USBD_CtlContinueSendData * @brief USBD_CtlContinueSendData
* continue sending data on the ctl pipe * continue sending data on the ctl pipe
* @param pdev: device instance * @param pdev: device instance
* @param buff: pointer to data buffer * @param buff: pointer to data buffer
* @param len: length of data to be sent * @param len: length of data to be sent
* @retval status * @retval status
*/ */
USBD_StatusTypeDef USBD_CtlContinueSendData(USBD_HandleTypeDef *pdev, USBD_StatusTypeDef USBD_CtlContinueSendData(USBD_HandleTypeDef *pdev,
uint8_t *pbuf, uint32_t len) uint8_t *pbuf, uint32_t len)
{ {
@@ -116,20 +121,25 @@ USBD_StatusTypeDef USBD_CtlContinueSendData(USBD_HandleTypeDef *pdev,
} }
/** /**
* @brief USBD_CtlPrepareRx * @brief USBD_CtlPrepareRx
* receive data on the ctl pipe * receive data on the ctl pipe
* @param pdev: device instance * @param pdev: device instance
* @param buff: pointer to data buffer * @param buff: pointer to data buffer
* @param len: length of data to be received * @param len: length of data to be received
* @retval status * @retval status
*/ */
USBD_StatusTypeDef USBD_CtlPrepareRx(USBD_HandleTypeDef *pdev, USBD_StatusTypeDef USBD_CtlPrepareRx(USBD_HandleTypeDef *pdev,
uint8_t *pbuf, uint32_t len) uint8_t *pbuf, uint32_t len)
{ {
/* Set EP0 State */ /* Set EP0 State */
pdev->ep0_state = USBD_EP0_DATA_OUT; pdev->ep0_state = USBD_EP0_DATA_OUT;
pdev->ep_out[0].total_length = len; pdev->ep_out[0].total_length = len;
#ifdef USBD_AVOID_PACKET_SPLIT_MPS
pdev->ep_out[0].rem_length = 0U;
#else
pdev->ep_out[0].rem_length = len; pdev->ep_out[0].rem_length = len;
#endif
/* Start the transfer */ /* Start the transfer */
(void)USBD_LL_PrepareReceive(pdev, 0U, pbuf, len); (void)USBD_LL_PrepareReceive(pdev, 0U, pbuf, len);
@@ -138,13 +148,13 @@ USBD_StatusTypeDef USBD_CtlPrepareRx(USBD_HandleTypeDef *pdev,
} }
/** /**
* @brief USBD_CtlContinueRx * @brief USBD_CtlContinueRx
* continue receive data on the ctl pipe * continue receive data on the ctl pipe
* @param pdev: device instance * @param pdev: device instance
* @param buff: pointer to data buffer * @param buff: pointer to data buffer
* @param len: length of data to be received * @param len: length of data to be received
* @retval status * @retval status
*/ */
USBD_StatusTypeDef USBD_CtlContinueRx(USBD_HandleTypeDef *pdev, USBD_StatusTypeDef USBD_CtlContinueRx(USBD_HandleTypeDef *pdev,
uint8_t *pbuf, uint32_t len) uint8_t *pbuf, uint32_t len)
{ {
@@ -154,11 +164,11 @@ USBD_StatusTypeDef USBD_CtlContinueRx(USBD_HandleTypeDef *pdev,
} }
/** /**
* @brief USBD_CtlSendStatus * @brief USBD_CtlSendStatus
* send zero lzngth packet on the ctl pipe * send zero lzngth packet on the ctl pipe
* @param pdev: device instance * @param pdev: device instance
* @retval status * @retval status
*/ */
USBD_StatusTypeDef USBD_CtlSendStatus(USBD_HandleTypeDef *pdev) USBD_StatusTypeDef USBD_CtlSendStatus(USBD_HandleTypeDef *pdev)
{ {
/* Set EP0 State */ /* Set EP0 State */
@@ -171,11 +181,11 @@ USBD_StatusTypeDef USBD_CtlSendStatus(USBD_HandleTypeDef *pdev)
} }
/** /**
* @brief USBD_CtlReceiveStatus * @brief USBD_CtlReceiveStatus
* receive zero lzngth packet on the ctl pipe * receive zero lzngth packet on the ctl pipe
* @param pdev: device instance * @param pdev: device instance
* @retval status * @retval status
*/ */
USBD_StatusTypeDef USBD_CtlReceiveStatus(USBD_HandleTypeDef *pdev) USBD_StatusTypeDef USBD_CtlReceiveStatus(USBD_HandleTypeDef *pdev)
{ {
/* Set EP0 State */ /* Set EP0 State */
@@ -188,12 +198,12 @@ USBD_StatusTypeDef USBD_CtlReceiveStatus(USBD_HandleTypeDef *pdev)
} }
/** /**
* @brief USBD_GetRxCount * @brief USBD_GetRxCount
* returns the received data length * returns the received data length
* @param pdev: device instance * @param pdev: device instance
* @param ep_addr: endpoint address * @param ep_addr: endpoint address
* @retval Rx Data blength * @retval Rx Data blength
*/ */
uint32_t USBD_GetRxCount(USBD_HandleTypeDef *pdev, uint8_t ep_addr) uint32_t USBD_GetRxCount(USBD_HandleTypeDef *pdev, uint8_t ep_addr)
{ {
return USBD_LL_GetRxDataSize(pdev, ep_addr); return USBD_LL_GetRxDataSize(pdev, ep_addr);

View File

@@ -29,21 +29,6 @@ This software component is licensed by ST under Ultimate Liberty license SLA004
Details about the content of this release are available in the release note [here](https://htmlpreview.github.io/?https://github.com/STMicroelectronics/stm32_mw_usb_device/blob/master/Release_Notes.html). Details about the content of this release are available in the release note [here](https://htmlpreview.github.io/?https://github.com/STMicroelectronics/stm32_mw_usb_device/blob/master/Release_Notes.html).
## Compatibility information
This table shows the correspondence between the USB Device MW version and the corresponding HAL version of the targeted series. It is **crucial** that you use a consistent set of versions for the MW - HAL, as mentioned in this table.
Note that:
* in case a series does not support a particular tag, it is not mentioned in front of it.
* in case a series supports a recent tag, it is not mentioned in front of older ones.
USB Device | HAL |
---------- | ---------- |
Tag v2.5.1 | Tag v1.10.2 ([stm32l0xx_hal_driver](https://github.com/STMicroelectronics/stm32l0xx_hal_driver))
Tag v2.5.2 | Tag v1.4.0 ([stm32l1xx_hal_driver](https://github.com/STMicroelectronics/stm32l1xx_hal_driver))
Tag v2.5.3 | Tag v1.7.3 ([stm32f0xx_hal_driver](https://github.com/STMicroelectronics/stm32f0xx_hal_driver))<br>Tag v1.1.4 ([stm32f1xx_hal_driver](https://github.com/STMicroelectronics/stm32f1xx_hal_driver))<br>Tag v1.2.4 ([stm32f2xx_hal_driver](https://github.com/STMicroelectronics/stm32f2xx_hal_driver))<br>Tag v1.5.3 ([stm32f3xx_hal_driver](https://github.com/STMicroelectronics/stm32f3xx_hal_driver))
Tag v2.6.0 | Tag v1.7.8 ([stm32f4xx_hal_driver](https://github.com/STMicroelectronics/stm32f4xx_hal_driver))<br>Tag v1.2.8 ([stm32f7xx_hal_driver](https://github.com/STMicroelectronics/stm32f7xx_hal_driver))<br>Tag v1.9.0 ([stm32h7xx_hal_driver](https://github.com/STMicroelectronics/stm32h7xx_hal_driver))<br>Tag v1.12.0 ([stm32l4xx_hal_driver](https://github.com/STMicroelectronics/stm32l4xx_hal_driver))<br>Tag v1.6.0 ([stm32wbxx_hal_driver](https://github.com/STMicroelectronics/stm32wbxx_hal_driver))
## Troubleshooting ## Troubleshooting
If you have any issue with the **software content** of this repository, you can file an issue [here](https://github.com/STMicroelectronics/stm32_mw_usb_device/issues/new/choose). If you have any issue with the **software content** of this repository, you can file an issue [here](https://github.com/STMicroelectronics/stm32_mw_usb_device/issues/new/choose).

View File

@@ -14,6 +14,8 @@
<meta http-equiv="Content-Type" content="text/html; charset=windows-1252"> <meta http-equiv="Content-Type" content="text/html; charset=windows-1252">
<link rel="File-List" href="Release_Notes_for_STM32F2xx_StdPeriph_Driver_files/filelist.xml"> <link rel="File-List" href="Release_Notes_for_STM32F2xx_StdPeriph_Driver_files/filelist.xml">
<link rel="Edit-Time-Data" href="Release_Notes_for_STM32F2xx_StdPeriph_Driver_files/editdata.mso"><!--[if !mso]> <link rel="Edit-Time-Data" href="Release_Notes_for_STM32F2xx_StdPeriph_Driver_files/editdata.mso"><!--[if !mso]>
@@ -920,10 +922,105 @@ ul
</tbody></table> </tbody></table>
<p class="MsoNormal"><span style="font-family: &quot;Arial&quot;,&quot;sans-serif&quot;; display: none;"><o:p>&nbsp;</o:p></span></p> <p class="MsoNormal"><span style="font-family: &quot;Arial&quot;,&quot;sans-serif&quot;; display: none;"><o:p>&nbsp;</o:p></span></p>
<table class="MsoNormalTable" style="width: 675pt;" border="0" cellpadding="0" width="900"> <table class="MsoNormalTable" style="width: 675pt;" border="0" cellpadding="0" width="900">
<tbody><tr style=""> <tbody><tr>
<td style="padding: 0in;" valign="top"> <td style="padding: 0in;" valign="top">
<h2 style="background: rgb(51, 102, 255) none repeat scroll 0% 50%; -moz-background-clip: initial; -moz-background-origin: initial; -moz-background-inline-policy: initial;"><a name="History"></a><span style="font-size: 12pt; color: white;">Update History</span></h2> <h2 style="background: rgb(51, 102, 255) none repeat scroll 0% 50%; -moz-background-clip: initial; -moz-background-origin: initial; -moz-background-inline-policy: initial;"><a name="History"></a><span style="font-size: 12pt; color: white;">Update History</span></h2>
<h3 style="background: rgb(51, 102, 255) none repeat scroll 0% 50%; -moz-background-clip: initial; -moz-background-origin: initial; -moz-background-inline-policy: initial; margin-right: 500pt; width: 180px;"><span style="font-size: 10pt; font-family: Arial; color: white;">V2.6.0 / 27-December-2019</span></h3><p class="MsoNormal" style="margin: 4.5pt 0cm 4.5pt 18pt;"><b style=""><u><span style="font-size: 10pt; font-family: Verdana; color: black;">Main
<h3 style="background: rgb(51, 102, 255) none repeat scroll 0% 50%; -moz-background-clip: initial; -moz-background-origin: initial; -moz-background-inline-policy: initial; margin-right: 500pt; width: 180px;"><span style="font-size: 10pt; font-family: Arial; color: white;">V2.8.0 / 10-Mars-2021</span></h3><p class="MsoNormal" style="margin: 4.5pt 0cm 4.5pt 18pt;"><b style=""><u><span style="font-size: 10pt; font-family: Verdana; color: black;">Main
Changes</span></u></b></p><ul style="margin-top: 0cm;" type="square"><li>Integration of&nbsp; new USB device Class driver:</li><ul><li>USB Printer Class driver based on&nbsp;Universal Serial Bus
Device Class Definition
for
Printing Devices Version 1.1</li></ul><li>USB All Classes:</li><ul><li>Fix USB buffer overflow vulnerability for CDC, CDC-ECM, CDC-RNDIS, DFU, AUDIO, CustomHID, and Video Classes</li><li>fix compilation warning with C++ due to missing casting during class handler allocation</li><li>Enhance comments of USB configuration descriptors fields</li></ul><li>USB Video Class:</li><ul><li>fix missing closing bracket for extern "C" in usbd_video.h</li><li>fix USBCV test with Uncompressed video format support</li></ul></ul><h3 style="background: rgb(51, 102, 255) none repeat scroll 0% 50%; -moz-background-clip: initial; -moz-background-origin: initial; -moz-background-inline-policy: initial; margin-right: 500pt; width: 180px;"><span style="font-size: 10pt; font-family: Arial; color: white;">V2.7.1 / 18-August-2020</span></h3>
<b style=""><u><span style="font-size: 10pt; font-family: Verdana; color: black;"></span></u></b><p class="MsoNormal" style="margin: 4.5pt 0cm 4.5pt 18pt;"><b style=""><u><span style="font-size: 10pt; font-family: Verdana; color: black;">Main
Changes</span></u></b></p>
<ul style="margin-top: 0cm;" type="square">
<li>USB All Class:</li>
<ul>
<li>Add NULL pointer access check to Class handler<br>
</li>
</ul>
</ul>
<h3 style="background: rgb(51, 102, 255) none repeat scroll 0% 50%; -moz-background-clip: initial; -moz-background-origin: initial; -moz-background-inline-policy: initial; margin-right: 500pt; width: 180px;"><span style="font-size: 10pt; font-family: Arial; color: white;">V2.7.0 / 12-August-2020</span></h3>
<p class="MsoNormal" style="margin: 4.5pt 0cm 4.5pt 18pt;"><b style=""><u><span style="font-size: 10pt; font-family: Verdana; color: black;">Main
Changes</span></u></b></p><ul style="margin-top: 0cm;" type="square"><li>Integration of&nbsp; new USB device Class driver:</li><ul><li>USB video Class driver based on USB-IF video class definition version 1.1</li></ul></ul>
<ul style="margin-top: 0cm;" type="square"><li>USB Core:</li><ul><li>Enhance NULL pointer check in Core APIs</li><li>Allow supporting both USER and USER Class string desc</li><li>Add support of USB controller which handles packet-size splitting by hardware</li><li>Avoid compilation warning due macro redefinition</li><li>change
added to USBD_HandleTypeDef structure: dev_state, old_dev_state and
ep0_state declaration become volatile to disable compiler optimization</li><li>Word spelling correction and file indentation improved</li><li>usbd_conf.h/c Template file updated to suggest using by default a static memory allocation for Class handler</li></ul></ul><ul style="margin-top: 0cm;" type="square"><li>USB All Classes</li><ul><li>Word spelling correction and file indentation improved</li><li>Allow updating device config descriptor Max power from user code usbd_conf.h using USBD_MAX_POWER define</li><li>Fix device config descriptor bmAttributes value which depends on user code define USBD_SELF_POWERED</li></ul></ul><ul style="margin-top: 0cm;" type="square"><li>USB CDC Class:</li><ul><li>Class specific request, add protection to limit the maximum data length to be sent by the CDC device</li></ul></ul><ul style="margin-top: 0cm;" type="square"><li>USB CustomHID Class:</li><ul><li>Allow changing CustomHID data EP size from user code </li></ul></ul>
<br><h3 style="background: rgb(51, 102, 255) none repeat scroll 0% 50%; -moz-background-clip: initial; -moz-background-origin: initial; -moz-background-inline-policy: initial; margin-right: 500pt; width: 180px;"><span style="font-size: 10pt; font-family: Arial; color: white;">V2.6.1 / 05-June-2020</span></h3>
<p class="MsoNormal" style="margin: 4.5pt 0cm 4.5pt 18pt;"><b style=""><u><span style="font-size: 10pt; font-family: Verdana; color: black;">Main
Changes</span></u></b><u><span style="font-size: 10pt; font-family: Verdana; color: black;"><o:p></o:p></span></u></p>
<ul style="margin-top: 0cm;" type="square">
<li>USB Core:</li>
<ul>
<li>minor rework on USBD_Init() USBD_DeInit()</li>
<li>Fix warning issue with Keil due to missing return value of setup API<br>
</li>
</ul>
<li>USB CDC Class:</li>
<ul>
<li>Fix file indentation</li>
<li>Avoid accessing to NULL pointer in case
TransmitCplt() user fops is not defined to allow application
compatibility with device library version below v2.6.0<br>
</li>
</ul>
</ul>
<br>
<ul style="margin-top: 0cm;" type="square">
<li>Fix minor misra-c 2012 violations</li>
</ul>
<h3 style="background: rgb(51, 102, 255) none repeat scroll 0% 50%; -moz-background-clip: initial; -moz-background-origin: initial; -moz-background-inline-policy: initial; margin-right: 500pt; width: 180px;"><span style="font-size: 10pt; font-family: Arial; color: white;">V2.6.0 / 27-December-2019</span></h3>
<p class="MsoNormal" style="margin: 4.5pt 0cm 4.5pt 18pt;"><b style=""><u><span style="font-size: 10pt; font-family: Verdana; color: black;">Main
Changes</span></u></b><u><span style="font-size: 10pt; font-family: Verdana; color: black;"><o:p></o:p></span></u></p> Changes</span></u></b><u><span style="font-size: 10pt; font-family: Verdana; color: black;"><o:p></o:p></span></u></p>
@@ -946,7 +1043,7 @@ Changes</span></u></b><u><span style="font-size: 10pt; font-family: Verdana; col
<ul style="margin-top: 0cm;" type="square"><li>Integration of three new USB device Class drivers:</li><ul><li>USB CDC ECM Class driver</li><li>USB CDC RNDIS Microsoft Class driver</li><li>USB Billboard Class driver</li></ul><li>Fix mondatory misra-c 2012 violations</li><li>update user core and class template files</li><li>USB Core:</li><ul><li>Fix unexpected EP0 stall during enumeration phase&nbsp;</li><li>Improve APIs error&nbsp;management and prevent accessing NULL pointers</li></ul><li>USB MSC Class:</li><ul><li>Fix USBCV specific class tests</li><li>Fix mutliple error with SCSI commands handling</li><li>Protect medium access when host ask for medium ejection</li></ul><li>USB CDC Class:</li><ul><li>Add new function to inform user that current IN transfer is completed</li><li>update transmit and receive APIs to transfer up to 64KB</li></ul></ul><ul style="margin-top: 0cm;" type="square"><li>USB AUDIO Class:</li><ul><li>Fix audio sync start buffer size</li><li>update user callback periodicTC args by adding pointer to user buffer and size</li></ul><li>USB CustomHID Class:</li><ul><li>Rework the OUT transfer complete and prevent automaticly re-enabling the OUT EP&nbsp;</li><li>Add new user API to restart the OUT transfer: USBD_CUSTOM_HID_ReceivePacket()</li></ul></ul><h3 style="background: rgb(51, 102, 255) none repeat scroll 0% 50%; -moz-background-clip: initial; -moz-background-origin: initial; -moz-background-inline-policy: initial; margin-right: 500pt; width: 180px;"><span style="font-size: 10pt; font-family: Arial; color: white;">V2.5.3 / 30-April-2019</span></h3><p class="MsoNormal" style="margin: 4.5pt 0cm 4.5pt 18pt;"><b style=""><u><span style="font-size: 10pt; font-family: Verdana; color: black;">Main <ul style="margin-top: 0cm;" type="square"><li>Integration of three new USB device Class drivers:</li><ul><li>USB CDC ECM Class driver</li><li>USB CDC RNDIS Microsoft Class driver</li><li>USB Billboard Class driver</li></ul><li>Fix mandatory misra-c 2012 violations</li><li>update user core and class template files</li><li>USB Core:</li><ul><li>Fix unexpected EP0 stall during enumeration phase&nbsp;</li><li>Improve APIs error&nbsp;management and prevent accessing NULL pointers</li></ul><li>USB MSC Class:</li><ul><li>Fix USBCV specific class tests</li><li>Fix multiple error with SCSI commands handling</li><li>Protect medium access when host ask for medium ejection</li></ul><li>USB CDC Class:</li><ul><li>Add new function to inform user that current IN transfer is completed</li><li>update transmit and receive APIs to transfer up to 64KB</li></ul></ul><ul style="margin-top: 0cm;" type="square"><li>USB AUDIO Class:</li><ul><li>Fix audio sync start buffer size</li><li>update user callback periodicTC args by adding pointer to user buffer and size</li></ul><li>USB CustomHID Class:</li><ul><li>Rework the OUT transfer complete and prevent automatically re-enabling the OUT EP&nbsp;</li><li>Add new user API to restart the OUT transfer: USBD_CUSTOM_HID_ReceivePacket()</li></ul></ul><h3 style="background: rgb(51, 102, 255) none repeat scroll 0% 50%; -moz-background-clip: initial; -moz-background-origin: initial; -moz-background-inline-policy: initial; margin-right: 500pt; width: 180px;"><span style="font-size: 10pt; font-family: Arial; color: white;">V2.5.3 / 30-April-2019</span></h3><p class="MsoNormal" style="margin: 4.5pt 0cm 4.5pt 18pt;"><b style=""><u><span style="font-size: 10pt; font-family: Verdana; color: black;">Main
Changes</span></u></b><u><span style="font-size: 10pt; font-family: Verdana; color: black;"><o:p></o:p></span></u></p> Changes</span></u></b><u><span style="font-size: 10pt; font-family: Verdana; color: black;"><o:p></o:p></span></u></p>
@@ -969,7 +1066,7 @@ Changes</span></u></b><u><span style="font-size: 10pt; font-family: Verdana; col
<ul style="margin-top: 0cm;" type="square"><li>Fix misra-c 2012 high severity violations</li><li>Core driver:</li><ul><li>protect shared macros __ALIGN_BEGIN, __ALIGN_END with C directive #ifndef</li><li>update Core driver and DFU Class driver to use&nbsp;USBD_SUPPORT_USER_STRING_DESC insead of &nbsp;USBD_SUPPORT_USER_STRING</li><li>&nbsp;prevent accessing to NULL pointer if the get descriptor functions are not defined</li><li>Update on USBD_LL_Resume(),&nbsp; restore the device state only if the current state is USBD_STATE_SUSPENDED </li></ul></ul><h3 style="background: rgb(51, 102, 255) none repeat scroll 0% 50%; -moz-background-clip: initial; -moz-background-origin: initial; -moz-background-inline-policy: initial; margin-right: 500pt; width: 180px;"><span style="font-size: 10pt; font-family: Arial; color: white;">V2.5.2 / 27-Mars-2019</span></h3><p class="MsoNormal" style="margin: 4.5pt 0cm 4.5pt 18pt;"><b style=""><u><span style="font-size: 10pt; font-family: Verdana; color: black;">Main <ul style="margin-top: 0cm;" type="square"><li>Fix misra-c 2012 high severity violations</li><li>Core driver:</li><ul><li>protect shared macros __ALIGN_BEGIN, __ALIGN_END with C directive #ifndef</li><li>update Core driver and DFU Class driver to use&nbsp;USBD_SUPPORT_USER_STRING_DESC instead of &nbsp;USBD_SUPPORT_USER_STRING</li><li>&nbsp;prevent accessing to NULL pointer if the get descriptor functions are not defined</li><li>Update on USBD_LL_Resume(),&nbsp; restore the device state only if the current state is USBD_STATE_SUSPENDED </li></ul></ul><h3 style="background: rgb(51, 102, 255) none repeat scroll 0% 50%; -moz-background-clip: initial; -moz-background-origin: initial; -moz-background-inline-policy: initial; margin-right: 500pt; width: 180px;"><span style="font-size: 10pt; font-family: Arial; color: white;">V2.5.2 / 27-Mars-2019</span></h3><p class="MsoNormal" style="margin: 4.5pt 0cm 4.5pt 18pt;"><b style=""><u><span style="font-size: 10pt; font-family: Verdana; color: black;">Main
Changes</span></u></b><u><span style="font-size: 10pt; font-family: Verdana; color: black;"><o:p></o:p></span></u></p> Changes</span></u></b><u><span style="font-size: 10pt; font-family: Verdana; color: black;"><o:p></o:p></span></u></p>
@@ -1405,7 +1502,7 @@ compliance with the License. You may obtain a copy of the License at:</p><p styl
Microcontrollers visit </span><u><span style="color: blue;"><a href="http://www.st.com/internet/mcu/family/141.jsp" target="_blank">www.st.com/STM32</a></span></u></span><span style="font-size: 10pt; font-family: &quot;Verdana&quot;,&quot;sans-serif&quot;;"><u><span style="color: blue;"><a href="http://www.st.com/stm32" target="_blank"></a></span></u></span><span style="color: black;"><o:p></o:p></span></p> Microcontrollers visit </span><u><span style="color: blue;"><a href="http://www.st.com/internet/mcu/family/141.jsp" target="_blank">www.st.com/STM32</a></span></u></span><span style="font-size: 10pt; font-family: &quot;Verdana&quot;,&quot;sans-serif&quot;;"><u><span style="color: blue;"><a href="http://www.st.com/stm32" target="_blank"></a></span></u></span><span style="color: black;"><o:p></o:p></span></p>
</td> </td>
</tr> </tr>
</tbody></table> <tr><td style="padding: 0in;" valign="top"></td></tr></tbody></table>
<p class="MsoNormal"><span style="font-size: 10pt;"><o:p></o:p></span></p> <p class="MsoNormal"><span style="font-size: 10pt;"><o:p></o:p></span></p>
</td> </td>
</tr> </tr>