]> git.sur5r.net Git - u-boot/blobdiff - drivers/usb/musb-new/sunxi.c
usb: sunxi: Switch to use generic-phy
[u-boot] / drivers / usb / musb-new / sunxi.c
index 5728a3f384f5512c837ec373b25511066cf7765a..08de9c69c71c2462cb6b815d891e51c06395d18d 100644 (file)
  */
 #include <common.h>
 #include <dm.h>
+#include <generic-phy.h>
+#include <phy-sun4i-usb.h>
 #include <asm/arch/cpu.h>
 #include <asm/arch/clock.h>
 #include <asm/arch/gpio.h>
-#include <asm/arch/usb_phy.h>
 #include <asm-generic/gpio.h>
 #include <dm/lists.h>
 #include <dm/root.h>
@@ -86,6 +87,7 @@ struct sunxi_glue {
        struct sunxi_ccm_reg *ccm;
        struct sunxi_musb_config *cfg;
        struct device dev;
+       struct phy *phy;
 };
 #define to_sunxi_glue(d)       container_of(d, struct sunxi_glue, dev)
 
@@ -218,6 +220,7 @@ static bool enabled = false;
 
 static int sunxi_musb_enable(struct musb *musb)
 {
+       struct sunxi_glue *glue = to_sunxi_glue(musb->controller);
        int ret;
 
        pr_debug("%s():\n", __func__);
@@ -232,17 +235,23 @@ static int sunxi_musb_enable(struct musb *musb)
        musb_writeb(musb->mregs, USBC_REG_o_VEND0, 0);
 
        if (is_host_enabled(musb)) {
-               ret = sunxi_usb_phy_vbus_detect(0);
+               ret = sun4i_usb_phy_vbus_detect(glue->phy);
                if (ret == 1) {
                        printf("A charger is plugged into the OTG: ");
                        return -ENODEV;
                }
-               ret = sunxi_usb_phy_id_detect(0);
+
+               ret = sun4i_usb_phy_id_detect(glue->phy);
                if (ret == 1) {
                        printf("No host cable detected: ");
                        return -ENODEV;
                }
-               sunxi_usb_phy_power_on(0); /* port power on */
+
+               ret = generic_phy_power_on(glue->phy);
+               if (ret) {
+                       pr_err("failed to power on USB PHY\n");
+                       return ret;
+               }
        }
 
        USBC_ForceVbusValidToHigh(musb->mregs);
@@ -253,13 +262,21 @@ static int sunxi_musb_enable(struct musb *musb)
 
 static void sunxi_musb_disable(struct musb *musb)
 {
+       struct sunxi_glue *glue = to_sunxi_glue(musb->controller);
+       int ret;
+
        pr_debug("%s():\n", __func__);
 
        if (!enabled)
                return;
 
-       if (is_host_enabled(musb))
-               sunxi_usb_phy_power_off(0); /* port power off */
+       if (is_host_enabled(musb)) {
+               ret = generic_phy_power_off(glue->phy);
+               if (ret) {
+                       pr_err("failed to power off USB PHY\n");
+                       return;
+               }
+       }
 
        USBC_ForceVbusValidToLow(musb->mregs);
        mdelay(200); /* Wait for the current session to timeout */
@@ -270,9 +287,16 @@ static void sunxi_musb_disable(struct musb *musb)
 static int sunxi_musb_init(struct musb *musb)
 {
        struct sunxi_glue *glue = to_sunxi_glue(musb->controller);
+       int ret;
 
        pr_debug("%s():\n", __func__);
 
+       ret = generic_phy_init(glue->phy);
+       if (ret) {
+               pr_err("failed to init USB PHY\n");
+               return ret;
+       }
+
        musb->isr = sunxi_musb_interrupt;
 
        setbits_le32(&glue->ccm->ahb_gate0, BIT(AHB_GATE_OFFSET_USB0));
@@ -286,8 +310,6 @@ static int sunxi_musb_init(struct musb *musb)
                             BIT(glue->cfg->rst_bit));
 #endif
 
-       sunxi_usb_phy_init(0);
-
        USBC_ConfigFIFO_Base();
        USBC_EnableDpDmPullUp(musb->mregs);
        USBC_EnableIdPullUp(musb->mregs);
@@ -383,6 +405,7 @@ static int musb_usb_probe(struct udevice *dev)
        struct usb_bus_priv *priv = dev_get_uclass_priv(dev);
        struct musb_hdrc_platform_data pdata;
        void *base = dev_read_addr_ptr(dev);
+       struct phy phy;
        int ret;
 
        if (!base)
@@ -396,6 +419,13 @@ static int musb_usb_probe(struct udevice *dev)
        if (IS_ERR(glue->ccm))
                return PTR_ERR(glue->ccm);
 
+       ret = generic_phy_get_by_name(dev, "usb", &phy);
+       if (ret) {
+               pr_err("failed to get usb PHY\n");
+               return ret;
+       }
+
+       glue->phy = &phy;
        priv->desc_before_addr = true;
 
        memset(&pdata, 0, sizeof(pdata));
@@ -426,10 +456,18 @@ static int musb_usb_remove(struct udevice *dev)
 {
        struct sunxi_glue *glue = dev_get_priv(dev);
        struct musb_host_data *host = &glue->mdata;
+       int ret;
+
+       if (generic_phy_valid(glue->phy)) {
+               ret = generic_phy_exit(glue->phy);
+               if (ret) {
+                       pr_err("failed to exit %s USB PHY\n", dev->name);
+                       return ret;
+               }
+       }
 
        musb_stop(host->host);
 
-       sunxi_usb_phy_exit(0);
 #ifdef CONFIG_SUNXI_GEN_SUN6I
        clrbits_le32(&glue->ccm->ahb_reset0_cfg, BIT(AHB_GATE_OFFSET_USB0));
        if (glue->cfg->rst_bit)