1 /* 2 * Copyright (C) 2015 Alexey Brodkin <abrodkin@synopsys.com> 3 * 4 * SPDX-License-Identifier: GPL-2.0+ 5 */ 6 7 #include <common.h> 8 #include <clk.h> 9 #include <dm/ofnode.h> 10 #include <generic-phy.h> 11 #include <reset.h> 12 #include <asm/io.h> 13 #include <dm.h> 14 #include "ehci.h" 15 #include <power/regulator.h> 16 17 /* 18 * Even though here we don't explicitly use "struct ehci_ctrl" 19 * ehci_register() expects it to be the first thing that resides in 20 * device's private data. 21 */ 22 struct generic_ehci { 23 struct ehci_ctrl ctrl; 24 struct clk *clocks; 25 struct reset_ctl *resets; 26 struct phy phy; 27 #ifdef CONFIG_DM_REGULATOR 28 struct udevice *vbus_supply; 29 #endif 30 int clock_count; 31 int reset_count; 32 }; 33 34 #ifdef CONFIG_DM_REGULATOR 35 static int ehci_enable_vbus_supply(struct udevice *dev) 36 { 37 struct generic_ehci *priv = dev_get_priv(dev); 38 int ret; 39 40 ret = device_get_supply_regulator(dev, "vbus-supply", 41 &priv->vbus_supply); 42 if (ret && ret != -ENOENT) 43 return ret; 44 45 if (priv->vbus_supply) { 46 ret = regulator_set_enable(priv->vbus_supply, true); 47 if (ret) { 48 dev_err(dev, "Error enabling VBUS supply\n"); 49 return ret; 50 } 51 } else { 52 dev_dbg(dev, "No vbus supply\n"); 53 } 54 55 return 0; 56 } 57 58 static int ehci_disable_vbus_supply(struct generic_ehci *priv) 59 { 60 if (priv->vbus_supply) 61 return regulator_set_enable(priv->vbus_supply, false); 62 else 63 return 0; 64 } 65 #else 66 static int ehci_enable_vbus_supply(struct udevice *dev) 67 { 68 return 0; 69 } 70 71 static int ehci_disable_vbus_supply(struct generic_ehci *priv) 72 { 73 return 0; 74 } 75 #endif 76 77 static int ehci_usb_probe(struct udevice *dev) 78 { 79 struct generic_ehci *priv = dev_get_priv(dev); 80 struct ehci_hccr *hccr; 81 struct ehci_hcor *hcor; 82 int i, err, ret, clock_nb, reset_nb; 83 84 err = 0; 85 priv->clock_count = 0; 86 clock_nb = ofnode_count_phandle_with_args(dev_ofnode(dev), "clocks", 87 "#clock-cells"); 88 if (clock_nb > 0) { 89 priv->clocks = devm_kcalloc(dev, clock_nb, sizeof(struct clk), 90 GFP_KERNEL); 91 if (!priv->clocks) 92 return -ENOMEM; 93 94 for (i = 0; i < clock_nb; i++) { 95 err = clk_get_by_index(dev, i, &priv->clocks[i]); 96 97 if (err < 0) 98 break; 99 err = clk_enable(&priv->clocks[i]); 100 if (err) { 101 dev_err(dev, "failed to enable clock %d\n", i); 102 clk_free(&priv->clocks[i]); 103 goto clk_err; 104 } 105 priv->clock_count++; 106 } 107 } else { 108 if (clock_nb != -ENOENT) { 109 dev_err(dev, "failed to get clock phandle(%d)\n", 110 clock_nb); 111 return clock_nb; 112 } 113 } 114 115 priv->reset_count = 0; 116 reset_nb = ofnode_count_phandle_with_args(dev_ofnode(dev), "resets", 117 "#reset-cells"); 118 if (reset_nb > 0) { 119 priv->resets = devm_kcalloc(dev, reset_nb, 120 sizeof(struct reset_ctl), 121 GFP_KERNEL); 122 if (!priv->resets) 123 return -ENOMEM; 124 125 for (i = 0; i < reset_nb; i++) { 126 err = reset_get_by_index(dev, i, &priv->resets[i]); 127 if (err < 0) 128 break; 129 130 if (reset_deassert(&priv->resets[i])) { 131 dev_err(dev, "failed to deassert reset %d\n", 132 i); 133 reset_free(&priv->resets[i]); 134 goto reset_err; 135 } 136 priv->reset_count++; 137 } 138 } else { 139 if (reset_nb != -ENOENT) { 140 dev_err(dev, "failed to get reset phandle(%d)\n", 141 reset_nb); 142 goto clk_err; 143 } 144 } 145 146 err = ehci_enable_vbus_supply(dev); 147 if (err) 148 goto reset_err; 149 150 err = ehci_setup_phy(dev, &priv->phy, 0); 151 if (err) 152 goto regulator_err; 153 154 hccr = map_physmem(dev_read_addr(dev), 0x100, MAP_NOCACHE); 155 hcor = (struct ehci_hcor *)((uintptr_t)hccr + 156 HC_LENGTH(ehci_readl(&hccr->cr_capbase))); 157 158 err = ehci_register(dev, hccr, hcor, NULL, 0, USB_INIT_HOST); 159 if (err) 160 goto phy_err; 161 162 return 0; 163 164 phy_err: 165 ret = ehci_shutdown_phy(dev, &priv->phy); 166 if (ret) 167 dev_err(dev, "failed to shutdown usb phy\n"); 168 169 regulator_err: 170 ret = ehci_disable_vbus_supply(priv); 171 if (ret) 172 dev_err(dev, "failed to disable VBUS supply\n"); 173 174 reset_err: 175 ret = reset_release_all(priv->resets, priv->reset_count); 176 if (ret) 177 dev_err(dev, "failed to assert all resets\n"); 178 clk_err: 179 ret = clk_release_all(priv->clocks, priv->clock_count); 180 if (ret) 181 dev_err(dev, "failed to disable all clocks\n"); 182 183 return err; 184 } 185 186 static int ehci_usb_remove(struct udevice *dev) 187 { 188 struct generic_ehci *priv = dev_get_priv(dev); 189 int ret; 190 191 ret = ehci_deregister(dev); 192 if (ret) 193 return ret; 194 195 ret = ehci_shutdown_phy(dev, &priv->phy); 196 if (ret) 197 return ret; 198 199 ret = ehci_disable_vbus_supply(priv); 200 if (ret) 201 return ret; 202 203 ret = reset_release_all(priv->resets, priv->reset_count); 204 if (ret) 205 return ret; 206 207 return clk_release_all(priv->clocks, priv->clock_count); 208 } 209 210 static const struct udevice_id ehci_usb_ids[] = { 211 { .compatible = "generic-ehci" }, 212 { } 213 }; 214 215 U_BOOT_DRIVER(ehci_generic) = { 216 .name = "ehci_generic", 217 .id = UCLASS_USB, 218 .of_match = ehci_usb_ids, 219 .probe = ehci_usb_probe, 220 .remove = ehci_usb_remove, 221 .ops = &ehci_usb_ops, 222 .priv_auto_alloc_size = sizeof(struct generic_ehci), 223 .flags = DM_FLAG_ALLOC_PRIV_DMA, 224 }; 225