1 // SPDX-License-Identifier: GPL-2.0 2 /* 3 * Cadence USBSS DRD Driver. 4 * 5 * Copyright (C) 2018-2019 Cadence. 6 * Copyright (C) 2019 Texas Instruments 7 * 8 * Author: Pawel Laszczak <pawell@cadence.com> 9 * Roger Quadros <rogerq@ti.com> 10 * 11 * 12 */ 13 #include <dm.h> 14 #include <linux/delay.h> 15 #include <linux/iopoll.h> 16 #include <linux/kernel.h> 17 #include <linux/usb/otg.h> 18 19 #include "gadget.h" 20 #include "drd.h" 21 #include "core.h" 22 23 #define readl_poll_timeout_atomic readl_poll_timeout 24 #define usleep_range(a, b) udelay((b)) 25 /** 26 * cdns3_set_mode - change mode of OTG Core 27 * @cdns: pointer to context structure 28 * @mode: selected mode from cdns_role 29 * 30 * Returns 0 on success otherwise negative errno 31 */ 32 int cdns3_set_mode(struct cdns3 *cdns, enum usb_dr_mode mode) 33 { 34 int ret = 0; 35 u32 reg; 36 37 switch (mode) { 38 case USB_DR_MODE_PERIPHERAL: 39 break; 40 case USB_DR_MODE_HOST: 41 break; 42 case USB_DR_MODE_OTG: 43 dev_dbg(cdns->dev, "Set controller to OTG mode\n"); 44 if (cdns->version == CDNS3_CONTROLLER_V1) { 45 reg = readl(&cdns->otg_v1_regs->override); 46 reg |= OVERRIDE_IDPULLUP; 47 writel(reg, &cdns->otg_v1_regs->override); 48 } else { 49 reg = readl(&cdns->otg_v0_regs->ctrl1); 50 reg |= OVERRIDE_IDPULLUP_V0; 51 writel(reg, &cdns->otg_v0_regs->ctrl1); 52 } 53 54 /* 55 * Hardware specification says: "ID_VALUE must be valid within 56 * 50ms after idpullup is set to '1" so driver must wait 57 * 50ms before reading this pin. 58 */ 59 usleep_range(50000, 60000); 60 break; 61 default: 62 dev_err(cdns->dev, "Unsupported mode of operation %d\n", mode); 63 return -EINVAL; 64 } 65 66 return ret; 67 } 68 69 int cdns3_get_id(struct cdns3 *cdns) 70 { 71 int id; 72 73 id = readl(&cdns->otg_regs->sts) & OTGSTS_ID_VALUE; 74 dev_dbg(cdns->dev, "OTG ID: %d", id); 75 76 return id; 77 } 78 79 int cdns3_get_vbus(struct cdns3 *cdns) 80 { 81 int vbus; 82 83 vbus = !!(readl(&cdns->otg_regs->sts) & OTGSTS_VBUS_VALID); 84 dev_dbg(cdns->dev, "OTG VBUS: %d", vbus); 85 86 return vbus; 87 } 88 89 int cdns3_is_host(struct cdns3 *cdns) 90 { 91 if (cdns->dr_mode == USB_DR_MODE_HOST) 92 return 1; 93 else if (!cdns3_get_id(cdns)) 94 return 1; 95 96 return 0; 97 } 98 99 int cdns3_is_device(struct cdns3 *cdns) 100 { 101 if (cdns->dr_mode == USB_DR_MODE_PERIPHERAL) 102 return 1; 103 else if (cdns->dr_mode == USB_DR_MODE_OTG) 104 if (cdns3_get_id(cdns)) 105 return 1; 106 107 return 0; 108 } 109 110 /** 111 * cdns3_drd_switch_host - start/stop host 112 * @cdns: Pointer to controller context structure 113 * @on: 1 for start, 0 for stop 114 * 115 * Returns 0 on success otherwise negative errno 116 */ 117 int cdns3_drd_switch_host(struct cdns3 *cdns, int on) 118 { 119 int ret, val; 120 u32 reg = OTGCMD_OTG_DIS; 121 122 /* switch OTG core */ 123 if (on) { 124 writel(OTGCMD_HOST_BUS_REQ | reg, &cdns->otg_regs->cmd); 125 126 dev_dbg(cdns->dev, "Waiting till Host mode is turned on\n"); 127 ret = readl_poll_timeout_atomic(&cdns->otg_regs->sts, val, 128 val & OTGSTS_XHCI_READY, 129 100000); 130 if (ret) { 131 dev_err(cdns->dev, "timeout waiting for xhci_ready\n"); 132 return ret; 133 } 134 } else { 135 writel(OTGCMD_HOST_BUS_DROP | OTGCMD_DEV_BUS_DROP | 136 OTGCMD_DEV_POWER_OFF | OTGCMD_HOST_POWER_OFF, 137 &cdns->otg_regs->cmd); 138 /* Waiting till H_IDLE state.*/ 139 readl_poll_timeout_atomic(&cdns->otg_regs->state, val, 140 !(val & OTGSTATE_HOST_STATE_MASK), 141 2000000); 142 } 143 144 return 0; 145 } 146 147 /** 148 * cdns3_drd_switch_gadget - start/stop gadget 149 * @cdns: Pointer to controller context structure 150 * @on: 1 for start, 0 for stop 151 * 152 * Returns 0 on success otherwise negative errno 153 */ 154 int cdns3_drd_switch_gadget(struct cdns3 *cdns, int on) 155 { 156 int ret, val; 157 u32 reg = OTGCMD_OTG_DIS; 158 159 /* switch OTG core */ 160 if (on) { 161 writel(OTGCMD_DEV_BUS_REQ | reg, &cdns->otg_regs->cmd); 162 163 dev_dbg(cdns->dev, "Waiting till Device mode is turned on\n"); 164 165 ret = readl_poll_timeout_atomic(&cdns->otg_regs->sts, val, 166 val & OTGSTS_DEV_READY, 167 100000); 168 if (ret) { 169 dev_err(cdns->dev, "timeout waiting for dev_ready\n"); 170 return ret; 171 } 172 } else { 173 /* 174 * driver should wait at least 10us after disabling Device 175 * before turning-off Device (DEV_BUS_DROP) 176 */ 177 usleep_range(20, 30); 178 writel(OTGCMD_HOST_BUS_DROP | OTGCMD_DEV_BUS_DROP | 179 OTGCMD_DEV_POWER_OFF | OTGCMD_HOST_POWER_OFF, 180 &cdns->otg_regs->cmd); 181 /* Waiting till DEV_IDLE state.*/ 182 readl_poll_timeout_atomic(&cdns->otg_regs->state, val, 183 !(val & OTGSTATE_DEV_STATE_MASK), 184 2000000); 185 } 186 187 return 0; 188 } 189 190 /** 191 * cdns3_init_otg_mode - initialize drd controller 192 * @cdns: Pointer to controller context structure 193 * 194 * Returns 0 on success otherwise negative errno 195 */ 196 static int cdns3_init_otg_mode(struct cdns3 *cdns) 197 { 198 int ret = 0; 199 200 /* clear all interrupts */ 201 writel(~0, &cdns->otg_regs->ivect); 202 203 ret = cdns3_set_mode(cdns, USB_DR_MODE_OTG); 204 if (ret) 205 return ret; 206 207 return ret; 208 } 209 210 /** 211 * cdns3_drd_update_mode - initialize mode of operation 212 * @cdns: Pointer to controller context structure 213 * 214 * Returns 0 on success otherwise negative errno 215 */ 216 int cdns3_drd_update_mode(struct cdns3 *cdns) 217 { 218 int ret = 0; 219 220 switch (cdns->dr_mode) { 221 case USB_DR_MODE_PERIPHERAL: 222 ret = cdns3_set_mode(cdns, USB_DR_MODE_PERIPHERAL); 223 break; 224 case USB_DR_MODE_HOST: 225 ret = cdns3_set_mode(cdns, USB_DR_MODE_HOST); 226 break; 227 case USB_DR_MODE_OTG: 228 ret = cdns3_init_otg_mode(cdns); 229 break; 230 default: 231 dev_err(cdns->dev, "Unsupported mode of operation %d\n", 232 cdns->dr_mode); 233 return -EINVAL; 234 } 235 236 return ret; 237 } 238 239 int cdns3_drd_init(struct cdns3 *cdns) 240 { 241 void __iomem *regs; 242 int ret = 0; 243 u32 state; 244 245 regs = dev_remap_addr_name(cdns->dev, "otg"); 246 if (!regs) 247 return -EINVAL; 248 249 /* Detection of DRD version. Controller has been released 250 * in two versions. Both are similar, but they have same changes 251 * in register maps. 252 * The first register in old version is command register and it's read 253 * only, so driver should read 0 from it. On the other hand, in v1 254 * the first register contains device ID number which is not set to 0. 255 * Driver uses this fact to detect the proper version of 256 * controller. 257 */ 258 cdns->otg_v0_regs = regs; 259 if (!readl(&cdns->otg_v0_regs->cmd)) { 260 cdns->version = CDNS3_CONTROLLER_V0; 261 cdns->otg_v1_regs = NULL; 262 cdns->otg_regs = regs; 263 writel(1, &cdns->otg_v0_regs->simulate); 264 dev_info(cdns->dev, "DRD version v0 (%08x)\n", 265 readl(&cdns->otg_v0_regs->version)); 266 } else { 267 cdns->otg_v0_regs = NULL; 268 cdns->otg_v1_regs = regs; 269 cdns->otg_regs = (void *)&cdns->otg_v1_regs->cmd; 270 cdns->version = CDNS3_CONTROLLER_V1; 271 writel(1, &cdns->otg_v1_regs->simulate); 272 dev_info(cdns->dev, "DRD version v1 (ID: %08x, rev: %08x)\n", 273 readl(&cdns->otg_v1_regs->did), 274 readl(&cdns->otg_v1_regs->rid)); 275 } 276 277 state = OTGSTS_STRAP(readl(&cdns->otg_regs->sts)); 278 279 /* Update dr_mode according to STRAP configuration. */ 280 cdns->dr_mode = USB_DR_MODE_OTG; 281 if (state == OTGSTS_STRAP_HOST) { 282 dev_dbg(cdns->dev, "Controller strapped to HOST\n"); 283 cdns->dr_mode = USB_DR_MODE_HOST; 284 } else if (state == OTGSTS_STRAP_GADGET) { 285 dev_dbg(cdns->dev, "Controller strapped to PERIPHERAL\n"); 286 cdns->dr_mode = USB_DR_MODE_PERIPHERAL; 287 } 288 289 state = readl(&cdns->otg_regs->sts); 290 if (OTGSTS_OTG_NRDY(state) != 0) { 291 dev_err(cdns->dev, "Cadence USB3 OTG device not ready\n"); 292 return -ENODEV; 293 } 294 295 return ret; 296 } 297 298 int cdns3_drd_exit(struct cdns3 *cdns) 299 { 300 return 0; 301 } 302