diff options
| author | NConrad <[email protected]> | 2022-06-24 23:06:32 -0400 |
|---|---|---|
| committer | NConrad <[email protected]> | 2022-06-24 23:06:32 -0400 |
| commit | 239b5d52790051949c281e60ba96ac674669f026 (patch) | |
| tree | d0daab9a1d6518916c3fae1edc3c25b809da23a0 /src/class | |
| parent | 3d4d37375bbfb0bc88127be3aa79930e865f35b5 (diff) | |
USBTMC: Manually stall and unstall EP when clear(ENDPOINT_HALT) is received.
Diffstat (limited to 'src/class')
| -rw-r--r-- | src/class/usbtmc/usbtmc_device.c | 16 |
1 files changed, 15 insertions, 1 deletions
diff --git a/src/class/usbtmc/usbtmc_device.c b/src/class/usbtmc/usbtmc_device.c index 9608e4835..b5232ab91 100644 --- a/src/class/usbtmc/usbtmc_device.c +++ b/src/class/usbtmc/usbtmc_device.c @@ -597,18 +597,31 @@ bool usbtmcd_control_xfer_cb(uint8_t rhport, uint8_t stage, tusb_control_request { uint32_t ep_addr = (request->wIndex); + // At this point, a transfer MAY be in progress. Based on USB spec, when clearing bulk EP HALT, + // the EP transfer buffer needs to be cleared and DTOG needs to be reset, even if + // the EP is not halted. The only USBD API interface to do this is to stall and then unstall the EP. if(ep_addr == usbtmc_state.ep_bulk_out) { criticalEnter(); + usbd_edpt_stall(rhport, ep_addr); + usbd_edpt_clear_stall(rhport, ep_addr); usbtmc_state.state = STATE_NAK; // USBD core has placed EP in NAK state for us criticalLeave(); tud_usbtmc_bulkOut_clearFeature_cb(); } else if (ep_addr == usbtmc_state.ep_bulk_in) { + usbd_edpt_stall(rhport, ep_addr); + usbd_edpt_clear_stall(rhport, ep_addr); tud_usbtmc_bulkIn_clearFeature_cb(); } - else + else if ((usbtmc_state.ep_int_in != 0) && (ep_addr == usbtmc_state.ep_int_in)) + { + // Clearing interrupt in EP + usbd_edpt_stall(rhport, ep_addr); + usbd_edpt_clear_stall(rhport, ep_addr); + } + else { return false; } @@ -836,6 +849,7 @@ bool usbtmcd_control_xfer_cb(uint8_t rhport, uint8_t stage, tusb_control_request }, .StatusByte = tud_usbtmc_get_stb_cb(&(rsp.USBTMC_status)) }; + // USB488 spec states that transfer must be queued before control request response sent. usbd_edpt_xfer(rhport, usbtmc_state.ep_int_in, (void*)&intMsg, sizeof(intMsg)); } else |
