Skip to content

Commit

Permalink
usb: dwc3: ep0: fix SetFeature(TEST)
Browse files Browse the repository at this point in the history
When host requests us to enter a test mode,
we cannot directly enter the test mode before
Status Phase is completed, otherwise the core
will never be able to deliver the Status ZLP
to host, because it has already entered the
requested Test Mode.

In order to fix the error, we move the actual
start of Test Mode right after we receive
Transfer Complete event of the status phase.

Signed-off-by: Gerard Cauvy <g-cauvy1@ti.com>
Signed-off-by: Felipe Balbi <balbi@ti.com>
  • Loading branch information
Gerard Cauvy authored and Felipe Balbi committed Feb 10, 2012
1 parent 0907254 commit 3b63736
Show file tree
Hide file tree
Showing 3 changed files with 17 additions and 8 deletions.
3 changes: 3 additions & 0 deletions drivers/usb/dwc3/core.h
Original file line number Diff line number Diff line change
Expand Up @@ -684,6 +684,9 @@ struct dwc3 {

struct dwc3_hwparams hwparams;
struct dentry *root;

u8 test_mode;
u8 test_mode_nr;
};

/* -------------------------------------------------------------------------- */
Expand Down
21 changes: 13 additions & 8 deletions drivers/usb/dwc3/ep0.c
Original file line number Diff line number Diff line change
Expand Up @@ -316,7 +316,6 @@ static int dwc3_ep0_handle_feature(struct dwc3 *dwc,
u32 wValue;
u32 wIndex;
int ret;
u32 mode;

wValue = le16_to_cpu(ctrl->wValue);
wIndex = le16_to_cpu(ctrl->wIndex);
Expand Down Expand Up @@ -355,13 +354,8 @@ static int dwc3_ep0_handle_feature(struct dwc3 *dwc,
if (!set)
return -EINVAL;

mode = wIndex >> 8;
ret = dwc3_gadget_set_test_mode(dwc, mode);
if (ret < 0) {
dev_dbg(dwc->dev, "Invalid Test #%d\n",
mode);
return ret;
}
dwc->test_mode_nr = wIndex >> 8;
dwc->test_mode = true;
}
break;

Expand Down Expand Up @@ -604,6 +598,17 @@ static void dwc3_ep0_complete_req(struct dwc3 *dwc,
dwc3_gadget_giveback(dep, r, 0);
}

if (dwc->test_mode) {
int ret;

ret = dwc3_gadget_set_test_mode(dwc, dwc->test_mode_nr);
if (ret < 0) {
dev_dbg(dwc->dev, "Invalid Test #%d\n",
dwc->test_mode_nr);
dwc3_ep0_stall_and_restart(dwc);
}
}

dwc->ep0state = EP0_SETUP_PHASE;
dwc3_ep0_out_start(dwc);
}
Expand Down
1 change: 1 addition & 0 deletions drivers/usb/dwc3/gadget.c
Original file line number Diff line number Diff line change
Expand Up @@ -1962,6 +1962,7 @@ static void dwc3_gadget_reset_interrupt(struct dwc3 *dwc)
reg = dwc3_readl(dwc->regs, DWC3_DCTL);
reg &= ~DWC3_DCTL_TSTCTRL_MASK;
dwc3_writel(dwc->regs, DWC3_DCTL, reg);
dwc->test_mode = false;

dwc3_stop_active_transfers(dwc);
dwc3_clear_stall_all_ep(dwc);
Expand Down

0 comments on commit 3b63736

Please sign in to comment.