Skip to content

Commit d26320d

Browse files
tore-espressifDazza0
authored andcommitted
fix(usb/host): Correctly parse bInterval field in HighSpeed EP descriptors
For LS and FS interrupt endpoint: interval = bInterval For isochronous and HS interrupt endpoint: interval = 2^(bInterval-1)
1 parent 388360c commit d26320d

File tree

3 files changed

+21
-34
lines changed

3 files changed

+21
-34
lines changed

components/hal/include/hal/usb_dwc_hal.h

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -139,7 +139,7 @@ typedef struct {
139139
uint32_t val;
140140
};
141141
struct {
142-
usb_hal_interval_t interval; /**< The interval of the endpoint */
142+
unsigned int interval; /**< The interval of the endpoint in frames (FS) or microframes (HS) */
143143
uint32_t phase_offset_frames; /**< Phase offset in number of frames */
144144
} periodic; /**< Characteristic for periodic (interrupt/isochronous) endpoints only */
145145
} usb_dwc_hal_ep_char_t;

components/hal/include/hal/usb_dwc_types.h

Lines changed: 0 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -51,19 +51,6 @@ typedef enum {
5151
USB_HAL_FRAME_LIST_LEN_64 = 64,
5252
} usb_hal_frame_list_len_t;
5353

54-
/**
55-
* @brief Support intervals in number of USB frames (i.e., 1ms)
56-
*/
57-
typedef enum {
58-
USB_HAL_INTERVAL_1 = 1,
59-
USB_HAL_INTERVAL_2 = 2,
60-
USB_HAL_INTERVAL_4 = 4,
61-
USB_HAL_INTERVAL_8 = 8,
62-
USB_HAL_INTERVAL_16 = 16,
63-
USB_HAL_INTERVAL_32 = 32,
64-
USB_HAL_INTERVAL_64 = 64,
65-
} usb_hal_interval_t;
66-
6754
#ifdef __cplusplus
6855
}
6956
#endif

components/usb/hcd_dwc.c

Lines changed: 20 additions & 20 deletions
Original file line numberDiff line numberDiff line change
@@ -1578,31 +1578,31 @@ static void pipe_set_ep_char(const hcd_pipe_config_t *pipe_config, usb_transfer_
15781578
// Calculate the pipe's interval in terms of USB frames
15791579
// @see USB-OTG programming guide chapter 6.5 for more information
15801580
if (type == USB_TRANSFER_TYPE_INTR || type == USB_TRANSFER_TYPE_ISOCHRONOUS) {
1581-
unsigned int interval_frames;
1582-
unsigned int xfer_list_len;
1583-
if (type == USB_TRANSFER_TYPE_INTR) {
1584-
interval_frames = pipe_config->ep_desc->bInterval;
1585-
xfer_list_len = XFER_LIST_LEN_INTR;
1581+
// Convert bInterval field to real value
1582+
// @see USB 2.0 specs, Table 9-13
1583+
unsigned int interval_value;
1584+
if (type == USB_TRANSFER_TYPE_INTR && pipe_config->dev_speed != USB_SPEED_HIGH) {
1585+
interval_value = pipe_config->ep_desc->bInterval;
15861586
} else {
1587-
interval_frames = (1 << (pipe_config->ep_desc->bInterval - 1));
1588-
xfer_list_len = XFER_LIST_LEN_ISOC;
1587+
interval_value = (1 << (pipe_config->ep_desc->bInterval - 1));
15891588
}
15901589
// Round down interval to nearest power of 2
1591-
if (interval_frames >= 32) {
1592-
interval_frames = 32;
1593-
} else if (interval_frames >= 16) {
1594-
interval_frames = 16;
1595-
} else if (interval_frames >= 8) {
1596-
interval_frames = 8;
1597-
} else if (interval_frames >= 4) {
1598-
interval_frames = 4;
1599-
} else if (interval_frames >= 2) {
1600-
interval_frames = 2;
1601-
} else if (interval_frames >= 1) {
1602-
interval_frames = 1;
1590+
if (interval_value >= 32) {
1591+
interval_value = 32;
1592+
} else if (interval_value >= 16) {
1593+
interval_value = 16;
1594+
} else if (interval_value >= 8) {
1595+
interval_value = 8;
1596+
} else if (interval_value >= 4) {
1597+
interval_value = 4;
1598+
} else if (interval_value >= 2) {
1599+
interval_value = 2;
1600+
} else if (interval_value >= 1) {
1601+
interval_value = 1;
16031602
}
1604-
ep_char->periodic.interval = interval_frames;
1603+
ep_char->periodic.interval = interval_value;
16051604
// We are the Nth pipe to be allocated. Use N as a phase offset
1605+
unsigned int xfer_list_len = (type == USB_TRANSFER_TYPE_INTR) ? XFER_LIST_LEN_INTR : XFER_LIST_LEN_ISOC;
16061606
ep_char->periodic.phase_offset_frames = pipe_idx & (xfer_list_len - 1);
16071607
} else {
16081608
ep_char->periodic.interval = 0;

0 commit comments

Comments
 (0)