[U-Boot] [PATCH v4 15/17] musb-new: sunxi: Use CLK and RESET support
Jagan Teki
jagan at amarulasolutions.com
Sun Aug 26 12:38:24 UTC 2018
Now clock and reset drivers are available for respective
SoC's so use clk and reset ops on musb driver.
Tested-by: Jagan Teki <jagan at amarulasolutions.com>
Acked-by: Maxime Ripard <maxime.ripard at bootlin.com>
Signed-off-by: Jagan Teki <jagan at amarulasolutions.com>
---
drivers/usb/musb-new/sunxi.c | 87 +++++++++++++++++++++---------------
1 file changed, 51 insertions(+), 36 deletions(-)
diff --git a/drivers/usb/musb-new/sunxi.c b/drivers/usb/musb-new/sunxi.c
index 6cf9826cda..7126152a21 100644
--- a/drivers/usb/musb-new/sunxi.c
+++ b/drivers/usb/musb-new/sunxi.c
@@ -16,9 +16,11 @@
* This file is part of the Inventra Controller Driver for Linux.
*/
#include <common.h>
+#include <clk.h>
#include <dm.h>
#include <generic-phy.h>
#include <phy-sun4i-usb.h>
+#include <reset.h>
#include <asm/arch/cpu.h>
#include <asm/arch/clock.h>
#include <asm/arch/gpio.h>
@@ -76,23 +78,18 @@
* From usbc/usbc.c
******************************************************************************/
-#define OFF_SUN6I_AHB_RESET0 0x2c0
-
struct sunxi_musb_config {
struct musb_hdrc_config *config;
bool has_reset;
- u8 rst_bit;
- u8 clkgate_bit;
- u32 off_reset0;
};
struct sunxi_glue {
struct musb_host_data mdata;
- struct sunxi_ccm_reg *ccm;
- u32 *reg_reset0;
struct sunxi_musb_config *cfg;
struct device dev;
struct phy phy;
+ struct clk clk;
+ struct reset_ctl rst;
};
#define to_sunxi_glue(d) container_of(d, struct sunxi_glue, dev)
@@ -296,24 +293,27 @@ static int sunxi_musb_init(struct musb *musb)
pr_debug("%s():\n", __func__);
- ret = generic_phy_init(&glue->phy);
+ ret = clk_enable(&glue->clk);
if (ret) {
- pr_err("failed to init USB PHY\n");
+ dev_err(dev, "failed to enable clock\n");
return ret;
}
- musb->isr = sunxi_musb_interrupt;
-
- setbits_le32(&glue->ccm->ahb_gate0, BIT(AHB_GATE_OFFSET_USB0));
- if (glue->cfg->clkgate_bit)
- setbits_le32(&glue->ccm->ahb_gate0,
- BIT(glue->cfg->clkgate_bit));
+ if (glue->cfg->has_reset) {
+ ret = reset_deassert(&glue->rst);
+ if (ret) {
+ dev_err(dev, "failed to deassert reset\n");
+ goto err_clk;
+ }
+ }
- if (glue->cfg->has_reset)
- setbits_le32(glue->reg_reset0, BIT(AHB_GATE_OFFSET_USB0));
+ ret = generic_phy_init(&glue->phy);
+ if (ret) {
+ pr_err("failed to init USB PHY\n");
+ goto err_rst;
+ }
- if (glue->cfg->rst_bit)
- setbits_le32(glue->reg_reset0, BIT(glue->cfg->rst_bit));
+ musb->isr = sunxi_musb_interrupt;
USBC_ConfigFIFO_Base();
USBC_EnableDpDmPullUp(musb->mregs);
@@ -329,6 +329,13 @@ static int sunxi_musb_init(struct musb *musb)
USBC_ForceVbusValidToHigh(musb->mregs);
return 0;
+
+err_rst:
+ if (glue->cfg->has_reset)
+ reset_assert(&glue->rst);
+err_clk:
+ clk_disable(&glue->clk);
+ return ret;
}
static int sunxi_musb_exit(struct musb *musb)
@@ -344,16 +351,19 @@ static int sunxi_musb_exit(struct musb *musb)
}
}
- if (glue->cfg->has_reset)
- clrbits_le32(glue->reg_reset0, BIT(AHB_GATE_OFFSET_USB0));
-
- if (glue->cfg->rst_bit)
- clrbits_le32(glue->reg_reset0, BIT(glue->cfg->rst_bit));
+ if (glue->cfg->has_reset) {
+ ret = reset_assert(&glue->rst);
+ if (ret) {
+ dev_err(dev, "failed to deassert reset\n");
+ return ret;
+ }
+ }
- clrbits_le32(&glue->ccm->ahb_gate0, BIT(AHB_GATE_OFFSET_USB0));
- if (glue->cfg->clkgate_bit)
- clrbits_le32(&glue->ccm->ahb_gate0,
- BIT(glue->cfg->clkgate_bit));
+ ret = clk_disable(&glue->clk);
+ if (ret) {
+ dev_err(dev, "failed to enable clock\n");
+ return ret;
+ }
return 0;
}
@@ -447,11 +457,19 @@ static int musb_usb_probe(struct udevice *dev)
if (!glue->cfg)
return -EINVAL;
- glue->ccm = (struct sunxi_ccm_reg *)SUNXI_CCM_BASE;
- if (IS_ERR(glue->ccm))
- return PTR_ERR(glue->ccm);
+ ret = clk_get_by_index(dev, 0, &glue->clk);
+ if (ret) {
+ dev_err(dev, "failed to get clock\n");
+ return ret;
+ }
- glue->reg_reset0 = (void *)glue->ccm + glue->cfg->off_reset0;
+ if (glue->cfg->has_reset) {
+ ret = reset_get_by_index(dev, 0, &glue->rst);
+ if (ret) {
+ dev_err(dev, "failed to get reset\n");
+ return ret;
+ }
+ }
ret = generic_phy_get_by_name(dev, "usb", &glue->phy);
if (ret) {
@@ -493,6 +511,7 @@ static int musb_usb_remove(struct udevice *dev)
struct musb_host_data *host = &glue->mdata;
musb_stop(host->host);
+
free(host->host);
host->host = NULL;
@@ -507,15 +526,11 @@ static const struct sunxi_musb_config sun4i_a10_cfg = {
static const struct sunxi_musb_config sun6i_a31_cfg = {
.config = &musb_config,
.has_reset = true,
- .off_reset0 = OFF_SUN6I_AHB_RESET0,
};
static const struct sunxi_musb_config sun8i_h3_cfg = {
.config = &musb_config_h3,
.has_reset = true,
- .rst_bit = 23,
- .clkgate_bit = 23,
- .off_reset0 = OFF_SUN6I_AHB_RESET0,
};
static const struct udevice_id sunxi_musb_ids[] = {
--
2.18.0.321.gffc6fa0e3
More information about the U-Boot
mailing list