stm32/usb: Verify number of used endpoints doesn't exceed maximum.
This commit is contained in:
parent
6705767da1
commit
bcaafa3823
|
@ -57,6 +57,19 @@
|
||||||
#endif
|
#endif
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
// Maximum number of endpoints (excluding EP0)
|
||||||
|
#if defined(STM32L0) || defined(STM32WB)
|
||||||
|
#define MAX_ENDPOINT(dev_id) (7)
|
||||||
|
#elif defined(STM32L4)
|
||||||
|
#define MAX_ENDPOINT(dev_id) (5)
|
||||||
|
#elif defined(STM32F4)
|
||||||
|
#define MAX_ENDPOINT(dev_id) ((dev_id) == USB_PHY_FS_ID ? 3 : 5)
|
||||||
|
#elif defined(STM32F7)
|
||||||
|
#define MAX_ENDPOINT(dev_id) ((dev_id) == USB_PHY_FS_ID ? 5 : 8)
|
||||||
|
#elif defined(STM32H7)
|
||||||
|
#define MAX_ENDPOINT(dev_id) (8)
|
||||||
|
#endif
|
||||||
|
|
||||||
STATIC void pyb_usb_vcp_init0(void);
|
STATIC void pyb_usb_vcp_init0(void);
|
||||||
|
|
||||||
// this will be persistent across a soft-reset
|
// this will be persistent across a soft-reset
|
||||||
|
@ -240,7 +253,7 @@ bool pyb_usb_dev_init(int dev_id, uint16_t vid, uint16_t pid, uint8_t mode, size
|
||||||
// configure the VID, PID and the USBD mode (interfaces it will expose)
|
// configure the VID, PID and the USBD mode (interfaces it will expose)
|
||||||
int cdc_only = (mode & USBD_MODE_IFACE_MASK) == USBD_MODE_CDC;
|
int cdc_only = (mode & USBD_MODE_IFACE_MASK) == USBD_MODE_CDC;
|
||||||
USBD_SetVIDPIDRelease(&usb_dev->usbd_cdc_msc_hid_state, vid, pid, 0x0200, cdc_only);
|
USBD_SetVIDPIDRelease(&usb_dev->usbd_cdc_msc_hid_state, vid, pid, 0x0200, cdc_only);
|
||||||
if (USBD_SelectMode(&usb_dev->usbd_cdc_msc_hid_state, mode, hid_info) != 0) {
|
if (USBD_SelectMode(&usb_dev->usbd_cdc_msc_hid_state, mode, hid_info, MAX_ENDPOINT(dev_id)) != 0) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -165,7 +165,7 @@ static inline uint32_t usbd_cdc_max_packet(USBD_HandleTypeDef *pdev) {
|
||||||
}
|
}
|
||||||
|
|
||||||
// returns 0 on success, -1 on failure
|
// returns 0 on success, -1 on failure
|
||||||
int USBD_SelectMode(usbd_cdc_msc_hid_state_t *usbd, uint32_t mode, USBD_HID_ModeInfoTypeDef *hid_info);
|
int USBD_SelectMode(usbd_cdc_msc_hid_state_t *usbd, uint32_t mode, USBD_HID_ModeInfoTypeDef *hid_info, uint8_t max_endpoint);
|
||||||
// returns the current usb mode
|
// returns the current usb mode
|
||||||
uint8_t USBD_GetMode(usbd_cdc_msc_hid_state_t *usbd);
|
uint8_t USBD_GetMode(usbd_cdc_msc_hid_state_t *usbd);
|
||||||
|
|
||||||
|
|
|
@ -489,7 +489,7 @@ uint8_t USBD_GetMode(usbd_cdc_msc_hid_state_t *usbd) {
|
||||||
return usbd->usbd_mode;
|
return usbd->usbd_mode;
|
||||||
}
|
}
|
||||||
|
|
||||||
int USBD_SelectMode(usbd_cdc_msc_hid_state_t *usbd, uint32_t mode, USBD_HID_ModeInfoTypeDef *hid_info) {
|
int USBD_SelectMode(usbd_cdc_msc_hid_state_t *usbd, uint32_t mode, USBD_HID_ModeInfoTypeDef *hid_info, uint8_t max_endpoint) {
|
||||||
// save mode
|
// save mode
|
||||||
usbd->usbd_mode = mode;
|
usbd->usbd_mode = mode;
|
||||||
|
|
||||||
|
@ -656,6 +656,17 @@ int USBD_SelectMode(usbd_cdc_msc_hid_state_t *usbd, uint32_t mode, USBD_HID_Mode
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Verify that the endpoints that are used fit within the maximum number
|
||||||
|
d = usbd->usbd_config_desc;
|
||||||
|
const uint8_t *d_top = d + n;
|
||||||
|
while (d < d_top) {
|
||||||
|
if (d[0] == 7 && d[1] == USB_DESC_TYPE_ENDPOINT && (d[2] & 0x7f) > max_endpoint) {
|
||||||
|
// Endpoint out of range of hardware
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
d += d[0];
|
||||||
|
}
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue