Skip to content

Commit

Permalink
Merge tag 'usb-3.18-rc3' of git://git.kernel.org/pub/scm/linux/kernel…
Browse files Browse the repository at this point in the history
…/git/gregkh/usb

Pull USB fixes from Greg KH:
 "Here are a bunch of USB fixes for 3.18-rc3.

  Mostly usb-serial device ids and gadget fixes for issues that have
  been reported.  Full details are in the shortlog.

  All of these have been in linux-next for a while"

* tag 'usb-3.18-rc3' of git://git.kernel.org/pub/scm/linux/kernel/git/gregkh/usb: (42 commits)
  usb: chipidea: Fix oops when removing the ci_hdrc module
  usb: gadget: function: Fixed the return value on error path
  usb: dwc2: gadget: disable phy before turning off power regulators
  usb: gadget: function: Remove redundant usb_free_all_descriptors
  usb: dwc3: gadget: Properly initialize LINK TRB
  usb: dwc2: gadget: fix gadget unregistration in udc_stop() function
  usb: dwc2: Bits in bitfield should add up to 32
  usb: dwc2: gadget: sparse warning of context imbalance
  usb: gadget: udc: core: fix kernel oops with soft-connect
  usb: musb: musb_dsps: fix NULL pointer in suspend
  usb: musb: dsps: start OTG timer on resume again
  usb: gadget: loopback: don't queue requests to bogus endpoints
  usb: ffs: fix regression when quirk_ep_out_aligned_size flag is set
  usb: gadget: f_fs: remove redundant ffs_data_get()
  usb: gadget: udc: USB_GADGET_XILINX should depend on HAS_DMA
  Revert "usb: dwc3: dwc3-omap: Disable/Enable only wrapper interrupts in prepare/complete"
  usb: gadget: composite: enable BESL support
  usb: musb: cppi41: restart hrtimer only if not yet done
  usb: dwc3: ep0: fix Data Phase for transfer sizes aligned to wMaxPacketSize
  usb: serial: ftdi_sio: add "bricked" FTDI device PID
  ...
  • Loading branch information
Linus Torvalds committed Nov 1, 2014
2 parents 4f4274a + 9c19db5 commit 528a506
Show file tree
Hide file tree
Showing 32 changed files with 319 additions and 173 deletions.
1 change: 0 additions & 1 deletion drivers/usb/chipidea/core.c
Original file line number Diff line number Diff line change
Expand Up @@ -742,7 +742,6 @@ static int ci_hdrc_remove(struct platform_device *pdev)
ci_role_destroy(ci);
ci_hdrc_enter_lpm(ci, true);
usb_phy_shutdown(ci->transceiver);
kfree(ci->hw_bank.regmap);

return 0;
}
Expand Down
2 changes: 1 addition & 1 deletion drivers/usb/dwc2/core.h
Original file line number Diff line number Diff line change
Expand Up @@ -619,7 +619,7 @@ struct dwc2_hsotg {
unsigned port_suspend_change:1;
unsigned port_over_current_change:1;
unsigned port_l1_change:1;
unsigned reserved:26;
unsigned reserved:25;
} b;
} flags;

Expand Down
14 changes: 7 additions & 7 deletions drivers/usb/dwc2/gadget.c
Original file line number Diff line number Diff line change
Expand Up @@ -2561,8 +2561,10 @@ static int s3c_hsotg_ep_enable(struct usb_ep *ep,
hs_ep->fifo_size = val;
break;
}
if (i == 8)
return -ENOMEM;
if (i == 8) {
ret = -ENOMEM;
goto error;
}
}

/* for non control endpoints, set PID to D0 */
Expand All @@ -2579,6 +2581,7 @@ static int s3c_hsotg_ep_enable(struct usb_ep *ep,
/* enable the endpoint interrupt */
s3c_hsotg_ctrl_epint(hsotg, index, dir_in, 1);

error:
spin_unlock_irqrestore(&hsotg->lock, flags);
return ret;
}
Expand Down Expand Up @@ -2934,9 +2937,7 @@ static int s3c_hsotg_udc_stop(struct usb_gadget *gadget,

spin_lock_irqsave(&hsotg->lock, flags);

if (!driver)
hsotg->driver = NULL;

hsotg->driver = NULL;
hsotg->gadget.speed = USB_SPEED_UNKNOWN;

spin_unlock_irqrestore(&hsotg->lock, flags);
Expand Down Expand Up @@ -3567,6 +3568,7 @@ static int s3c_hsotg_probe(struct platform_device *pdev)
s3c_hsotg_initep(hsotg, &hsotg->eps[epnum], epnum);

/* disable power and clock */
s3c_hsotg_phy_disable(hsotg);

ret = regulator_bulk_disable(ARRAY_SIZE(hsotg->supplies),
hsotg->supplies);
Expand All @@ -3575,8 +3577,6 @@ static int s3c_hsotg_probe(struct platform_device *pdev)
goto err_ep_mem;
}

s3c_hsotg_phy_disable(hsotg);

ret = usb_add_gadget_udc(&pdev->dev, &hsotg->gadget);
if (ret)
goto err_ep_mem;
Expand Down
15 changes: 2 additions & 13 deletions drivers/usb/dwc3/dwc3-omap.c
Original file line number Diff line number Diff line change
Expand Up @@ -597,27 +597,16 @@ static int dwc3_omap_prepare(struct device *dev)
{
struct dwc3_omap *omap = dev_get_drvdata(dev);

dwc3_omap_write_irqmisc_set(omap, 0x00);
dwc3_omap_disable_irqs(omap);

return 0;
}

static void dwc3_omap_complete(struct device *dev)
{
struct dwc3_omap *omap = dev_get_drvdata(dev);
u32 reg;

reg = (USBOTGSS_IRQMISC_OEVT |
USBOTGSS_IRQMISC_DRVVBUS_RISE |
USBOTGSS_IRQMISC_CHRGVBUS_RISE |
USBOTGSS_IRQMISC_DISCHRGVBUS_RISE |
USBOTGSS_IRQMISC_IDPULLUP_RISE |
USBOTGSS_IRQMISC_DRVVBUS_FALL |
USBOTGSS_IRQMISC_CHRGVBUS_FALL |
USBOTGSS_IRQMISC_DISCHRGVBUS_FALL |
USBOTGSS_IRQMISC_IDPULLUP_FALL);

dwc3_omap_write_irqmisc_set(omap, reg);
dwc3_omap_enable_irqs(omap);
}

static int dwc3_omap_suspend(struct device *dev)
Expand Down
2 changes: 2 additions & 0 deletions drivers/usb/dwc3/dwc3-pci.c
Original file line number Diff line number Diff line change
Expand Up @@ -30,6 +30,7 @@
#define PCI_DEVICE_ID_SYNOPSYS_HAPSUSB3 0xabcd
#define PCI_DEVICE_ID_INTEL_BYT 0x0f37
#define PCI_DEVICE_ID_INTEL_MRFLD 0x119e
#define PCI_DEVICE_ID_INTEL_BSW 0x22B7

struct dwc3_pci {
struct device *dev;
Expand Down Expand Up @@ -181,6 +182,7 @@ static const struct pci_device_id dwc3_pci_id_table[] = {
PCI_DEVICE(PCI_VENDOR_ID_SYNOPSYS,
PCI_DEVICE_ID_SYNOPSYS_HAPSUSB3),
},
{ PCI_DEVICE(PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_BSW), },
{ PCI_DEVICE(PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_BYT), },
{ PCI_DEVICE(PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_MRFLD), },
{ } /* Terminating Entry */
Expand Down
48 changes: 36 additions & 12 deletions drivers/usb/dwc3/ep0.c
Original file line number Diff line number Diff line change
Expand Up @@ -256,7 +256,7 @@ static void dwc3_ep0_stall_and_restart(struct dwc3 *dwc)

/* stall is always issued on EP0 */
dep = dwc->eps[0];
__dwc3_gadget_ep_set_halt(dep, 1);
__dwc3_gadget_ep_set_halt(dep, 1, false);
dep->flags = DWC3_EP_ENABLED;
dwc->delayed_status = false;

Expand All @@ -271,7 +271,7 @@ static void dwc3_ep0_stall_and_restart(struct dwc3 *dwc)
dwc3_ep0_out_start(dwc);
}

int dwc3_gadget_ep0_set_halt(struct usb_ep *ep, int value)
int __dwc3_gadget_ep0_set_halt(struct usb_ep *ep, int value)
{
struct dwc3_ep *dep = to_dwc3_ep(ep);
struct dwc3 *dwc = dep->dwc;
Expand All @@ -281,6 +281,20 @@ int dwc3_gadget_ep0_set_halt(struct usb_ep *ep, int value)
return 0;
}

int dwc3_gadget_ep0_set_halt(struct usb_ep *ep, int value)
{
struct dwc3_ep *dep = to_dwc3_ep(ep);
struct dwc3 *dwc = dep->dwc;
unsigned long flags;
int ret;

spin_lock_irqsave(&dwc->lock, flags);
ret = __dwc3_gadget_ep0_set_halt(ep, value);
spin_unlock_irqrestore(&dwc->lock, flags);

return ret;
}

void dwc3_ep0_out_start(struct dwc3 *dwc)
{
int ret;
Expand Down Expand Up @@ -466,7 +480,7 @@ static int dwc3_ep0_handle_feature(struct dwc3 *dwc,
return -EINVAL;
if (set == 0 && (dep->flags & DWC3_EP_WEDGE))
break;
ret = __dwc3_gadget_ep_set_halt(dep, set);
ret = __dwc3_gadget_ep_set_halt(dep, set, true);
if (ret)
return -EINVAL;
break;
Expand Down Expand Up @@ -775,9 +789,6 @@ static void dwc3_ep0_complete_data(struct dwc3 *dwc,

dwc->ep0_next_event = DWC3_EP0_NRDY_STATUS;

r = next_request(&ep0->request_list);
ur = &r->request;

trb = dwc->ep0_trb;

status = DWC3_TRB_SIZE_TRBSTS(trb->size);
Expand All @@ -790,6 +801,12 @@ static void dwc3_ep0_complete_data(struct dwc3 *dwc,
return;
}

r = next_request(&ep0->request_list);
if (!r)
return;

ur = &r->request;

length = trb->size & DWC3_TRB_SIZE_MASK;

if (dwc->ep0_bounced) {
Expand All @@ -811,12 +828,19 @@ static void dwc3_ep0_complete_data(struct dwc3 *dwc,

dwc3_ep0_stall_and_restart(dwc);
} else {
/*
* handle the case where we have to send a zero packet. This
* seems to be case when req.length > maxpacket. Could it be?
*/
if (r)
dwc3_gadget_giveback(ep0, r, 0);
dwc3_gadget_giveback(ep0, r, 0);

if (IS_ALIGNED(ur->length, ep0->endpoint.maxpacket) &&
ur->length && ur->zero) {
int ret;

dwc->ep0_next_event = DWC3_EP0_COMPLETE;

ret = dwc3_ep0_start_trans(dwc, epnum,
dwc->ctrl_req_addr, 0,
DWC3_TRBCTL_CONTROL_DATA);
WARN_ON(ret < 0);
}
}
}

Expand Down
39 changes: 23 additions & 16 deletions drivers/usb/dwc3/gadget.c
Original file line number Diff line number Diff line change
Expand Up @@ -525,12 +525,11 @@ static int __dwc3_gadget_ep_enable(struct dwc3_ep *dep,
if (!usb_endpoint_xfer_isoc(desc))
return 0;

memset(&trb_link, 0, sizeof(trb_link));

/* Link TRB for ISOC. The HWO bit is never reset */
trb_st_hw = &dep->trb_pool[0];

trb_link = &dep->trb_pool[DWC3_TRB_NUM - 1];
memset(trb_link, 0, sizeof(*trb_link));

trb_link->bpl = lower_32_bits(dwc3_trb_dma_offset(dep, trb_st_hw));
trb_link->bph = upper_32_bits(dwc3_trb_dma_offset(dep, trb_st_hw));
Expand Down Expand Up @@ -581,7 +580,7 @@ static int __dwc3_gadget_ep_disable(struct dwc3_ep *dep)

/* make sure HW endpoint isn't stalled */
if (dep->flags & DWC3_EP_STALL)
__dwc3_gadget_ep_set_halt(dep, 0);
__dwc3_gadget_ep_set_halt(dep, 0, false);

reg = dwc3_readl(dwc->regs, DWC3_DALEPENA);
reg &= ~DWC3_DALEPENA_EP(dep->number);
Expand Down Expand Up @@ -1202,15 +1201,28 @@ static int dwc3_gadget_ep_dequeue(struct usb_ep *ep,
return ret;
}

int __dwc3_gadget_ep_set_halt(struct dwc3_ep *dep, int value)
int __dwc3_gadget_ep_set_halt(struct dwc3_ep *dep, int value, int protocol)
{
struct dwc3_gadget_ep_cmd_params params;
struct dwc3 *dwc = dep->dwc;
int ret;

if (usb_endpoint_xfer_isoc(dep->endpoint.desc)) {
dev_err(dwc->dev, "%s is of Isochronous type\n", dep->name);
return -EINVAL;
}

memset(&params, 0x00, sizeof(params));

if (value) {
if (!protocol && ((dep->direction && dep->flags & DWC3_EP_BUSY) ||
(!list_empty(&dep->req_queued) ||
!list_empty(&dep->request_list)))) {
dev_dbg(dwc->dev, "%s: pending request, cannot halt\n",
dep->name);
return -EAGAIN;
}

ret = dwc3_send_gadget_ep_cmd(dwc, dep->number,
DWC3_DEPCMD_SETSTALL, &params);
if (ret)
Expand Down Expand Up @@ -1241,15 +1253,7 @@ static int dwc3_gadget_ep_set_halt(struct usb_ep *ep, int value)
int ret;

spin_lock_irqsave(&dwc->lock, flags);

if (usb_endpoint_xfer_isoc(dep->endpoint.desc)) {
dev_err(dwc->dev, "%s is of Isochronous type\n", dep->name);
ret = -EINVAL;
goto out;
}

ret = __dwc3_gadget_ep_set_halt(dep, value);
out:
ret = __dwc3_gadget_ep_set_halt(dep, value, false);
spin_unlock_irqrestore(&dwc->lock, flags);

return ret;
Expand All @@ -1260,15 +1264,18 @@ static int dwc3_gadget_ep_set_wedge(struct usb_ep *ep)
struct dwc3_ep *dep = to_dwc3_ep(ep);
struct dwc3 *dwc = dep->dwc;
unsigned long flags;
int ret;

spin_lock_irqsave(&dwc->lock, flags);
dep->flags |= DWC3_EP_WEDGE;
spin_unlock_irqrestore(&dwc->lock, flags);

if (dep->number == 0 || dep->number == 1)
return dwc3_gadget_ep0_set_halt(ep, 1);
ret = __dwc3_gadget_ep0_set_halt(ep, 1);
else
return dwc3_gadget_ep_set_halt(ep, 1);
ret = __dwc3_gadget_ep_set_halt(dep, 1, false);
spin_unlock_irqrestore(&dwc->lock, flags);

return ret;
}

/* -------------------------------------------------------------------------- */
Expand Down
3 changes: 2 additions & 1 deletion drivers/usb/dwc3/gadget.h
Original file line number Diff line number Diff line change
Expand Up @@ -82,10 +82,11 @@ void dwc3_gadget_giveback(struct dwc3_ep *dep, struct dwc3_request *req,
void dwc3_ep0_interrupt(struct dwc3 *dwc,
const struct dwc3_event_depevt *event);
void dwc3_ep0_out_start(struct dwc3 *dwc);
int __dwc3_gadget_ep0_set_halt(struct usb_ep *ep, int value);
int dwc3_gadget_ep0_set_halt(struct usb_ep *ep, int value);
int dwc3_gadget_ep0_queue(struct usb_ep *ep, struct usb_request *request,
gfp_t gfp_flags);
int __dwc3_gadget_ep_set_halt(struct dwc3_ep *dep, int value);
int __dwc3_gadget_ep_set_halt(struct dwc3_ep *dep, int value, int protocol);

/**
* dwc3_gadget_ep_get_transfer_index - Gets transfer index from HW
Expand Down
Loading

0 comments on commit 528a506

Please sign in to comment.