@@ -136,13 +136,23 @@ mp_obj_t common_hal_usb_core_device_get_manufacturer(usb_core_device_obj_t *self
136
136
}
137
137
138
138
void common_hal_usb_core_device_set_configuration (usb_core_device_obj_t * self , mp_int_t configuration ) {
139
- if (configuration == 0x100 ) {
140
- tusb_desc_configuration_t desc ;
141
- if (!tuh_descriptor_get_configuration (self -> device_number , 0 , & desc , sizeof (desc ), _transfer_done_cb , 0 ) ||
142
- !_wait_for_callback ()) {
143
- return ;
144
- }
145
- configuration = desc .bConfigurationValue ;
139
+ // We assume that the config index is one less than the value.
140
+ uint8_t config_index = configuration - 1 ;
141
+ // Get the configuration descriptor and cache it. We'll use it later to open
142
+ // endpoints.
143
+
144
+ // Get only the config descriptor first.
145
+ tusb_desc_configuration_t desc ;
146
+ if (!tuh_descriptor_get_configuration (self -> device_number , config_index , & desc , sizeof (desc ), _transfer_done_cb , 0 ) ||
147
+ !_wait_for_callback ()) {
148
+ return ;
149
+ }
150
+
151
+ // Get the config descriptor plus interfaces and endpoints.
152
+ self -> configuration_descriptor = m_realloc (self -> configuration_descriptor , desc .wTotalLength );
153
+ if (!tuh_descriptor_get_configuration (self -> device_number , config_index , self -> configuration_descriptor , desc .wTotalLength , _transfer_done_cb , 0 ) ||
154
+ !_wait_for_callback ()) {
155
+ return ;
146
156
}
147
157
tuh_configuration_set (self -> device_number , configuration , _transfer_done_cb , 0 );
148
158
_wait_for_callback ();
@@ -163,6 +173,7 @@ STATIC size_t _xfer(tuh_xfer_t *xfer, mp_int_t timeout) {
163
173
RUN_BACKGROUND_TASKS ;
164
174
}
165
175
if (mp_hal_is_interrupted ()) {
176
+ tuh_edpt_abort_xfer (xfer -> daddr , xfer -> ep_addr );
166
177
return 0 ;
167
178
}
168
179
xfer_result_t result = _xfer_result ;
@@ -171,6 +182,7 @@ STATIC size_t _xfer(tuh_xfer_t *xfer, mp_int_t timeout) {
171
182
mp_raise_usb_core_USBError (translate ("Pipe error" ));
172
183
}
173
184
if (result == 0xff ) {
185
+ tuh_edpt_abort_xfer (xfer -> daddr , xfer -> ep_addr );
174
186
mp_raise_usb_core_USBTimeoutError ();
175
187
}
176
188
if (result == XFER_RESULT_SUCCESS ) {
@@ -195,17 +207,13 @@ STATIC bool _open_endpoint(usb_core_device_obj_t *self, mp_int_t endpoint) {
195
207
return true;
196
208
}
197
209
198
- // Fetch the full configuration descriptor and search for the endpoint's descriptor.
199
- uint8_t desc_buf [128 ];
200
- if (!tuh_descriptor_get_configuration (self -> device_number , self -> configuration_index , & desc_buf , sizeof (desc_buf ), _transfer_done_cb , 0 ) ||
201
- !_wait_for_callback ()) {
202
- return false;
210
+ if (self -> configuration_descriptor == NULL ) {
211
+ mp_raise_usb_core_USBError (translate ("No configuration set" ));
203
212
}
204
- tusb_desc_configuration_t * desc_cfg = (tusb_desc_configuration_t * )desc_buf ;
213
+
214
+ tusb_desc_configuration_t * desc_cfg = (tusb_desc_configuration_t * )self -> configuration_descriptor ;
205
215
206
216
uint32_t total_length = tu_le16toh (desc_cfg -> wTotalLength );
207
- // Cap to the buffer size we requested.
208
- total_length = MIN (total_length , sizeof (desc_buf ));
209
217
uint8_t const * desc_end = ((uint8_t const * )desc_cfg ) + total_length ;
210
218
uint8_t const * p_desc = tu_desc_next (desc_cfg );
211
219
@@ -291,6 +299,7 @@ mp_int_t common_hal_usb_core_device_ctrl_transfer(usb_core_device_obj_t *self,
291
299
RUN_BACKGROUND_TASKS ;
292
300
}
293
301
if (mp_hal_is_interrupted ()) {
302
+ tuh_edpt_abort_xfer (xfer .daddr , xfer .ep_addr );
294
303
return 0 ;
295
304
}
296
305
xfer_result_t result = _xfer_result ;
@@ -299,6 +308,7 @@ mp_int_t common_hal_usb_core_device_ctrl_transfer(usb_core_device_obj_t *self,
299
308
mp_raise_usb_core_USBError (translate ("Pipe error" ));
300
309
}
301
310
if (result == 0xff ) {
311
+ tuh_edpt_abort_xfer (xfer .daddr , xfer .ep_addr );
302
312
mp_raise_usb_core_USBTimeoutError ();
303
313
}
304
314
if (result == XFER_RESULT_SUCCESS ) {
0 commit comments