summaryrefslogtreecommitdiff
path: root/drivers/usb
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/usb')
-rw-r--r--drivers/usb/dwc3/dwc3-generic.c9
-rw-r--r--drivers/usb/eth/asix88179.c45
-rw-r--r--drivers/usb/gadget/Kconfig4
-rw-r--r--drivers/usb/gadget/ci_udc.c24
-rw-r--r--drivers/usb/gadget/ci_udc.h1
-rw-r--r--drivers/usb/host/Kconfig4
-rw-r--r--drivers/usb/host/xhci-rcar-r8a779x_usb3_v3.h2
-rw-r--r--drivers/usb/host/xhci-rcar.c2
8 files changed, 72 insertions, 19 deletions
diff --git a/drivers/usb/dwc3/dwc3-generic.c b/drivers/usb/dwc3/dwc3-generic.c
index 2ab41cbae45..55e62b35c61 100644
--- a/drivers/usb/dwc3/dwc3-generic.c
+++ b/drivers/usb/dwc3/dwc3-generic.c
@@ -51,7 +51,8 @@ struct dwc3_generic_host_priv {
};
static int dwc3_generic_probe(struct udevice *dev,
- struct dwc3_generic_priv *priv)
+ struct dwc3_generic_priv *priv,
+ enum usb_dr_mode mode)
{
int rc;
struct dwc3_generic_plat *plat = dev_get_plat(dev);
@@ -62,7 +63,7 @@ static int dwc3_generic_probe(struct udevice *dev,
dwc3->dev = dev;
dwc3->maximum_speed = plat->maximum_speed;
- dwc3->dr_mode = plat->dr_mode;
+ dwc3->dr_mode = mode;
#if CONFIG_IS_ENABLED(OF_CONTROL)
dwc3_of_parse(dwc3);
@@ -197,7 +198,7 @@ static int dwc3_generic_peripheral_probe(struct udevice *dev)
{
struct dwc3_generic_priv *priv = dev_get_priv(dev);
- return dwc3_generic_probe(dev, priv);
+ return dwc3_generic_probe(dev, priv, USB_DR_MODE_PERIPHERAL);
}
static int dwc3_generic_peripheral_remove(struct udevice *dev)
@@ -241,7 +242,7 @@ static int dwc3_generic_host_probe(struct udevice *dev)
struct dwc3_generic_host_priv *priv = dev_get_priv(dev);
int rc;
- rc = dwc3_generic_probe(dev, &priv->gen_priv);
+ rc = dwc3_generic_probe(dev, &priv->gen_priv, USB_DR_MODE_HOST);
if (rc)
return rc;
diff --git a/drivers/usb/eth/asix88179.c b/drivers/usb/eth/asix88179.c
index 4bd3b9d10dc..69d3073b669 100644
--- a/drivers/usb/eth/asix88179.c
+++ b/drivers/usb/eth/asix88179.c
@@ -173,9 +173,10 @@
#define USB_BULK_SEND_TIMEOUT 5000
#define USB_BULK_RECV_TIMEOUT 5000
-#define AX_RX_URB_SIZE 1024 * 0x12
+#define AX_RX_URB_SIZE 1024 * 0x1a
#define BLK_FRAME_SIZE 0x200
#define PHY_CONNECT_TIMEOUT 5000
+#define PHY_RESET_TIMEOUT 500
#define TIMEOUT_RESOLUTION 50 /* ms */
@@ -192,10 +193,10 @@
static const struct {
unsigned char ctrl, timer_l, timer_h, size, ifg;
} AX88179_BULKIN_SIZE[] = {
- {7, 0x4f, 0, 0x02, 0xff},
- {7, 0x20, 3, 0x03, 0xff},
- {7, 0xae, 7, 0x04, 0xff},
- {7, 0xcc, 0x4c, 0x04, 8},
+ {7, 0x4f, 0, 0x12, 0xff},
+ {7, 0x20, 3, 0x16, 0xff},
+ {7, 0xae, 7, 0x18, 0xff},
+ {7, 0xcc, 0x4c, 0x18, 8},
};
/* driver private */
@@ -285,6 +286,26 @@ static int asix_write_mac(struct ueth_data *dev, uint8_t *enetaddr)
return ret;
}
+static int asix_reset_phy(struct ueth_data *dev)
+{
+ u16 bmcr;
+ u32 t;
+
+ /* Reset the PHY */
+ bmcr = BMCR_RESET;
+ asix_write_cmd(dev, AX_ACCESS_PHY, 0x03, MII_BMCR, 2, &bmcr);
+
+ for (t = 0; t < PHY_RESET_TIMEOUT; t += TIMEOUT_RESOLUTION) {
+ asix_read_cmd(dev, AX_ACCESS_PHY, 0x03, MII_BMCR, 2, &bmcr);
+ if (!(bmcr & BMCR_RESET))
+ return 0;
+ mdelay(TIMEOUT_RESOLUTION);
+ }
+
+ debug("Reset PHY timeout\n");
+ return -ETIMEDOUT;
+}
+
static int asix_basic_reset(struct ueth_data *dev,
struct asix_private *dev_priv)
{
@@ -311,7 +332,7 @@ static int asix_basic_reset(struct ueth_data *dev,
memcpy(tmp, &AX88179_BULKIN_SIZE[0], 5);
asix_write_cmd(dev, AX_ACCESS_MAC, AX_RX_BULKIN_QCTRL, 5, 5, tmp);
- dev_priv->rx_urb_size = 128 * 20;
+ dev_priv->rx_urb_size = 1024 * 20;
/* Water Level configuration */
*tmp = 0x34;
@@ -344,14 +365,22 @@ static int asix_basic_reset(struct ueth_data *dev,
AX_MEDIUM_GIGAMODE | AX_MEDIUM_JUMBO_EN;
asix_write_cmd(dev, AX_ACCESS_MAC, AX_MEDIUM_STATUS_MODE, 2, 2, tmp16);
+ asix_reset_phy(dev);
+
u16 adv = 0;
- adv = ADVERTISE_ALL | ADVERTISE_CSMA | ADVERTISE_LPACK |
- ADVERTISE_NPAGE | ADVERTISE_PAUSE_ASYM | ADVERTISE_PAUSE_CAP;
+ adv = ADVERTISE_ALL | ADVERTISE_CSMA |
+ ADVERTISE_PAUSE_ASYM | ADVERTISE_PAUSE_CAP;
asix_write_cmd(dev, AX_ACCESS_PHY, 0x03, MII_ADVERTISE, 2, &adv);
adv = ADVERTISE_1000FULL;
asix_write_cmd(dev, AX_ACCESS_PHY, 0x03, MII_CTRL1000, 2, &adv);
+ /* Restart auto-negotiation */
+ u16 bmcr = 0;
+ asix_read_cmd(dev, AX_ACCESS_PHY, 0x03, MII_BMCR, 2, &bmcr);
+ bmcr |= BMCR_ANENABLE | BMCR_ANRESTART;
+ asix_write_cmd(dev, AX_ACCESS_PHY, 0x03, MII_BMCR, 2, &bmcr);
+
return 0;
}
diff --git a/drivers/usb/gadget/Kconfig b/drivers/usb/gadget/Kconfig
index 010084ef7f3..c815764c2bc 100644
--- a/drivers/usb/gadget/Kconfig
+++ b/drivers/usb/gadget/Kconfig
@@ -115,10 +115,10 @@ config USB_GADGET_DWC2_OTG
USB_GADGET to be enabled.
config USB_RENESAS_USBHS
- bool "Renesas RCar USB2.0 HS controller (gadget mode)"
+ bool "Renesas R-Car USB2.0 HS controller (gadget mode)"
select USB_GADGET_DUALSPEED
help
- The Renesas Rcar USB 2.0 high-speed gadget controller
+ The Renesas R-Car USB 2.0 high-speed gadget controller
integrated into Salvator and Kingfisher boards. Select this
option if you want the driver to operate in Peripheral mode.
This option requires USB_GADGET to be enabled.
diff --git a/drivers/usb/gadget/ci_udc.c b/drivers/usb/gadget/ci_udc.c
index bbe03cfff1f..4bff75da759 100644
--- a/drivers/usb/gadget/ci_udc.c
+++ b/drivers/usb/gadget/ci_udc.c
@@ -649,12 +649,30 @@ static void flip_ep0_direction(void)
}
}
+/*
+ * This function explicitly sets the address, without the "USBADRA" (advance)
+ * feature, which is not supported by older versions of the controller.
+ */
+static void ci_set_address(struct ci_udc *udc, u8 address)
+{
+ DBG("%s %x\n", __func__, address);
+ writel(address << 25, &udc->devaddr);
+}
+
static void handle_ep_complete(struct ci_ep *ci_ep)
{
struct ept_queue_item *item, *next_td;
int num, in, len, j;
struct ci_req *ci_req;
+ /* Set the device address that was previously sent by SET_ADDRESS */
+ if (controller.next_device_address != 0) {
+ struct ci_udc *udc = (struct ci_udc *)controller.ctrl->hcor;
+
+ ci_set_address(udc, controller.next_device_address);
+ controller.next_device_address = 0;
+ }
+
num = ci_ep->desc->bEndpointAddress & USB_ENDPOINT_NUMBER_MASK;
in = (ci_ep->desc->bEndpointAddress & USB_DIR_IN) != 0;
item = ci_get_qtd(num, in);
@@ -783,7 +801,7 @@ static void handle_setup(void)
* write address delayed (will take effect
* after the next IN txn)
*/
- writel((r.wValue << 25) | (1 << 24), &udc->devaddr);
+ controller.next_device_address = r.wValue;
req->length = 0;
usb_ep_queue(controller.gadget.ep0, req, 0);
return;
@@ -814,6 +832,9 @@ static void stop_activity(void)
int i, num, in;
struct ept_queue_head *head;
struct ci_udc *udc = (struct ci_udc *)controller.ctrl->hcor;
+
+ ci_set_address(udc, 0);
+
writel(readl(&udc->epcomp), &udc->epcomp);
#ifdef CONFIG_CI_UDC_HAS_HOSTPC
writel(readl(&udc->epsetupstat), &udc->epsetupstat);
@@ -934,6 +955,7 @@ static int ci_pullup(struct usb_gadget *gadget, int is_on)
struct ci_udc *udc = (struct ci_udc *)controller.ctrl->hcor;
if (is_on) {
/* RESET */
+ controller.next_device_address = 0;
writel(USBCMD_ITC(MICRO_8FRAME) | USBCMD_RST, &udc->usbcmd);
udelay(200);
diff --git a/drivers/usb/gadget/ci_udc.h b/drivers/usb/gadget/ci_udc.h
index bea2f9f3fe3..807f2084c1e 100644
--- a/drivers/usb/gadget/ci_udc.h
+++ b/drivers/usb/gadget/ci_udc.h
@@ -105,6 +105,7 @@ struct ci_drv {
struct ept_queue_head *epts;
uint8_t *items_mem;
struct ci_ep ep[NUM_ENDPOINTS];
+ u8 next_device_address;
};
struct ept_queue_head {
diff --git a/drivers/usb/host/Kconfig b/drivers/usb/host/Kconfig
index bb5893d56db..24786a2bc91 100644
--- a/drivers/usb/host/Kconfig
+++ b/drivers/usb/host/Kconfig
@@ -103,12 +103,12 @@ config USB_XHCI_PCI
Enables support for the PCI-based xHCI controller.
config USB_XHCI_RCAR
- bool "Renesas RCar USB 3.0 support"
+ bool "Renesas R-Car USB 3.0 support"
default y
depends on ARCH_RENESAS
help
Choose this option to add support for USB 3.0 driver on Renesas
- RCar Gen3 SoCs.
+ R-Car Gen3 SoCs.
config USB_XHCI_STI
bool "Support for STMicroelectronics STiH407 family on-chip xHCI USB controller"
diff --git a/drivers/usb/host/xhci-rcar-r8a779x_usb3_v3.h b/drivers/usb/host/xhci-rcar-r8a779x_usb3_v3.h
index 8db88f0dcfa..7c909b4697a 100644
--- a/drivers/usb/host/xhci-rcar-r8a779x_usb3_v3.h
+++ b/drivers/usb/host/xhci-rcar-r8a779x_usb3_v3.h
@@ -1,5 +1,5 @@
/*
- * Renesas RCar xHCI controller firmware version 3
+ * Renesas R-Car xHCI controller firmware version 3
*
* Copyright (c) 2014, Renesas Electronics Corporation
* All rights reserved.
diff --git a/drivers/usb/host/xhci-rcar.c b/drivers/usb/host/xhci-rcar.c
index 38c5928faed..b72807053c4 100644
--- a/drivers/usb/host/xhci-rcar.c
+++ b/drivers/usb/host/xhci-rcar.c
@@ -2,7 +2,7 @@
/*
* Copyright (C) 2017 Marek Vasut <marek.vasut@gmail.com>
*
- * Renesas RCar USB HOST xHCI Controller
+ * Renesas R-Car USB HOST xHCI Controller
*/
#include <clk.h>