Hoernchen has uploaded this change for review. ( https://gerrit.osmocom.org/c/osmo-asf4-dfu/+/42178?usp=email )
Change subject: dfu: fix bState transition/reporting order as per dfu spec ......................................................................
dfu: fix bState transition/reporting order as per dfu spec
DFU spec wants the next state, not the current one.
Change-Id: I06519c73cdb0b082002632da9cfe7436c63f52b0 --- M usb/class/dfu/device/dfudf.c 1 file changed, 10 insertions(+), 8 deletions(-)
git pull ssh://gerrit.osmocom.org:29418/osmo-asf4-dfu refs/changes/78/42178/1
diff --git a/usb/class/dfu/device/dfudf.c b/usb/class/dfu/device/dfudf.c index 223999a..5c5682e 100644 --- a/usb/class/dfu/device/dfudf.c +++ b/usb/class/dfu/device/dfudf.c @@ -160,14 +160,9 @@ to_return = ERR_UNSUPPORTED_OP; // stall control pipe (don't reply to the request) break; case USB_DFU_GETSTATUS: // get status - response[0] = dfu_status; // set status - response[1] = 10; // set poll timeout (24 bits, in milliseconds) to small value for periodical poll - response[2] = 0; // set poll timeout (24 bits, in milliseconds) to small value for periodical poll - response[3] = 0; // set poll timeout (24 bits, in milliseconds) to small value for periodical poll - response[4] = dfu_state; // set state - response[5] = 0; // string not used - to_return = usbdc_xfer(ep, response, 6, false); // send back status - if (USB_DFU_STATE_DFU_DNLOAD_SYNC == dfu_state) { // download has not completed + // per DFU 1.1 spec, bState must report the state the device will enter + // after this response, so perform state transitions before building response + if (USB_DFU_STATE_DFU_DNLOAD_SYNC == dfu_state) { dfu_state = USB_DFU_STATE_DFU_DNBUSY; // switch to busy state } else if (USB_DFU_STATE_DFU_MANIFEST_SYNC == dfu_state) { if (!dfu_manifestation_complete) { @@ -178,6 +173,13 @@ dfu_state = USB_DFU_STATE_DFU_MANIFEST_WAIT_RESET; // wait for reset } } + response[0] = dfu_status; // set status + response[1] = 10; // set poll timeout (24 bits, in milliseconds) to small value for periodical poll + response[2] = 0; // set poll timeout (24 bits, in milliseconds) to small value for periodical poll + response[3] = 0; // set poll timeout (24 bits, in milliseconds) to small value for periodical poll + response[4] = dfu_state; // set state (post-transition) + response[5] = 0; // string not used + to_return = usbdc_xfer(ep, response, 6, false); // send back status break; case USB_DFU_GETSTATE: // get state response[0] = dfu_state; // return state