* @three_stage_setup: set if we perform a three phase setup
* @ep0_status_pending: ep0 status response without a req is pending
* @ep0_bounced: true when we used bounce buffer
+ * @ep0_expect_in: true when we expect a DATA IN transfer
* @ep0_next_event: hold the next expected event
* @ep0state: state of endpoint zero
* @link_state: link state
unsigned three_stage_setup:1;
unsigned ep0_status_pending:1;
unsigned ep0_bounced:1;
+ unsigned ep0_expect_in:1;
enum dwc3_ep0_next ep0_next_event;
enum dwc3_ep0_state ep0state;
dwc->ep0_next_event = DWC3_EP0_NRDY_DATA;
}
+ dwc->ep0_expect_in = !!(ctrl->bRequestType & USB_DIR_IN);
+
if ((ctrl->bRequestType & USB_TYPE_MASK) == USB_TYPE_STANDARD)
ret = dwc3_ep0_std_request(dwc, ctrl);
else
return;
}
+ /*
+ * One of the possible error cases is when Host _does_
+ * request for Data Phase, but it does so on the wrong
+ * direction.
+ *
+ * Here, we already know ep0_next_event is DATA (see above),
+ * so we only need to check for direction.
+ */
+ if (dwc->ep0_expect_in != event->endpoint_number) {
+ dev_vdbg(dwc->dev, "Wrong direction for Data phase\n");
+ dwc3_ep0_stall_and_restart(dwc);
+ return;
+ }
+
dwc3_ep0_do_control_data(dwc, event);
break;