0001
0002
0003
0004
0005
0006
0007
0008
0009
0010
0011
0012 #include <linux/kernel.h>
0013 #include <linux/interrupt.h>
0014 #include <linux/delay.h>
0015 #include <linux/iopoll.h>
0016 #include <linux/usb/otg.h>
0017
0018 #include "drd.h"
0019 #include "core.h"
0020
0021
0022
0023
0024
0025
0026
0027
0028 static int cdns_set_mode(struct cdns *cdns, enum usb_dr_mode mode)
0029 {
0030 void __iomem *override_reg;
0031 u32 reg;
0032
0033 switch (mode) {
0034 case USB_DR_MODE_PERIPHERAL:
0035 break;
0036 case USB_DR_MODE_HOST:
0037 break;
0038 case USB_DR_MODE_OTG:
0039 dev_dbg(cdns->dev, "Set controller to OTG mode\n");
0040
0041 if (cdns->version == CDNSP_CONTROLLER_V2)
0042 override_reg = &cdns->otg_cdnsp_regs->override;
0043 else if (cdns->version == CDNS3_CONTROLLER_V1)
0044 override_reg = &cdns->otg_v1_regs->override;
0045 else
0046 override_reg = &cdns->otg_v0_regs->ctrl1;
0047
0048 reg = readl(override_reg);
0049
0050 if (cdns->version != CDNS3_CONTROLLER_V0)
0051 reg |= OVERRIDE_IDPULLUP;
0052 else
0053 reg |= OVERRIDE_IDPULLUP_V0;
0054
0055 writel(reg, override_reg);
0056
0057 if (cdns->version == CDNS3_CONTROLLER_V1) {
0058
0059
0060
0061
0062
0063
0064 if (cdns->phyrst_a_enable) {
0065 reg = readl(&cdns->otg_v1_regs->phyrst_cfg);
0066 reg |= PHYRST_CFG_PHYRST_A_ENABLE;
0067 writel(reg, &cdns->otg_v1_regs->phyrst_cfg);
0068 }
0069 }
0070
0071
0072
0073
0074
0075
0076 usleep_range(50000, 60000);
0077 break;
0078 default:
0079 dev_err(cdns->dev, "Unsupported mode of operation %d\n", mode);
0080 return -EINVAL;
0081 }
0082
0083 return 0;
0084 }
0085
0086 int cdns_get_id(struct cdns *cdns)
0087 {
0088 int id;
0089
0090 id = readl(&cdns->otg_regs->sts) & OTGSTS_ID_VALUE;
0091 dev_dbg(cdns->dev, "OTG ID: %d", id);
0092
0093 return id;
0094 }
0095
0096 int cdns_get_vbus(struct cdns *cdns)
0097 {
0098 int vbus;
0099
0100 vbus = !!(readl(&cdns->otg_regs->sts) & OTGSTS_VBUS_VALID);
0101 dev_dbg(cdns->dev, "OTG VBUS: %d", vbus);
0102
0103 return vbus;
0104 }
0105
0106 void cdns_clear_vbus(struct cdns *cdns)
0107 {
0108 u32 reg;
0109
0110 if (cdns->version != CDNSP_CONTROLLER_V2)
0111 return;
0112
0113 reg = readl(&cdns->otg_cdnsp_regs->override);
0114 reg |= OVERRIDE_SESS_VLD_SEL;
0115 writel(reg, &cdns->otg_cdnsp_regs->override);
0116 }
0117 EXPORT_SYMBOL_GPL(cdns_clear_vbus);
0118
0119 void cdns_set_vbus(struct cdns *cdns)
0120 {
0121 u32 reg;
0122
0123 if (cdns->version != CDNSP_CONTROLLER_V2)
0124 return;
0125
0126 reg = readl(&cdns->otg_cdnsp_regs->override);
0127 reg &= ~OVERRIDE_SESS_VLD_SEL;
0128 writel(reg, &cdns->otg_cdnsp_regs->override);
0129 }
0130 EXPORT_SYMBOL_GPL(cdns_set_vbus);
0131
0132 bool cdns_is_host(struct cdns *cdns)
0133 {
0134 if (cdns->dr_mode == USB_DR_MODE_HOST)
0135 return true;
0136 else if (cdns_get_id(cdns) == CDNS3_ID_HOST)
0137 return true;
0138
0139 return false;
0140 }
0141
0142 bool cdns_is_device(struct cdns *cdns)
0143 {
0144 if (cdns->dr_mode == USB_DR_MODE_PERIPHERAL)
0145 return true;
0146 else if (cdns->dr_mode == USB_DR_MODE_OTG)
0147 if (cdns_get_id(cdns) == CDNS3_ID_PERIPHERAL)
0148 return true;
0149
0150 return false;
0151 }
0152
0153
0154
0155
0156
0157 static void cdns_otg_disable_irq(struct cdns *cdns)
0158 {
0159 writel(0, &cdns->otg_irq_regs->ien);
0160 }
0161
0162
0163
0164
0165
0166 static void cdns_otg_enable_irq(struct cdns *cdns)
0167 {
0168 writel(OTGIEN_ID_CHANGE_INT | OTGIEN_VBUSVALID_RISE_INT |
0169 OTGIEN_VBUSVALID_FALL_INT, &cdns->otg_irq_regs->ien);
0170 }
0171
0172
0173
0174
0175
0176
0177
0178 int cdns_drd_host_on(struct cdns *cdns)
0179 {
0180 u32 val, ready_bit;
0181 int ret;
0182
0183
0184 writel(OTGCMD_HOST_BUS_REQ | OTGCMD_OTG_DIS,
0185 &cdns->otg_regs->cmd);
0186
0187 if (cdns->version == CDNSP_CONTROLLER_V2)
0188 ready_bit = OTGSTS_CDNSP_XHCI_READY;
0189 else
0190 ready_bit = OTGSTS_CDNS3_XHCI_READY;
0191
0192 dev_dbg(cdns->dev, "Waiting till Host mode is turned on\n");
0193 ret = readl_poll_timeout_atomic(&cdns->otg_regs->sts, val,
0194 val & ready_bit, 1, 100000);
0195
0196 if (ret)
0197 dev_err(cdns->dev, "timeout waiting for xhci_ready\n");
0198
0199 phy_set_mode(cdns->usb3_phy, PHY_MODE_USB_HOST);
0200 return ret;
0201 }
0202
0203
0204
0205
0206
0207 void cdns_drd_host_off(struct cdns *cdns)
0208 {
0209 u32 val;
0210
0211 writel(OTGCMD_HOST_BUS_DROP | OTGCMD_DEV_BUS_DROP |
0212 OTGCMD_DEV_POWER_OFF | OTGCMD_HOST_POWER_OFF,
0213 &cdns->otg_regs->cmd);
0214
0215
0216 readl_poll_timeout_atomic(&cdns->otg_regs->state, val,
0217 !(val & OTGSTATE_HOST_STATE_MASK),
0218 1, 2000000);
0219 phy_set_mode(cdns->usb3_phy, PHY_MODE_INVALID);
0220 }
0221
0222
0223
0224
0225
0226
0227
0228 int cdns_drd_gadget_on(struct cdns *cdns)
0229 {
0230 u32 reg = OTGCMD_OTG_DIS;
0231 u32 ready_bit;
0232 int ret, val;
0233
0234
0235 writel(OTGCMD_DEV_BUS_REQ | reg, &cdns->otg_regs->cmd);
0236
0237 dev_dbg(cdns->dev, "Waiting till Device mode is turned on\n");
0238
0239 if (cdns->version == CDNSP_CONTROLLER_V2)
0240 ready_bit = OTGSTS_CDNSP_DEV_READY;
0241 else
0242 ready_bit = OTGSTS_CDNS3_DEV_READY;
0243
0244 ret = readl_poll_timeout_atomic(&cdns->otg_regs->sts, val,
0245 val & ready_bit, 1, 100000);
0246 if (ret) {
0247 dev_err(cdns->dev, "timeout waiting for dev_ready\n");
0248 return ret;
0249 }
0250
0251 phy_set_mode(cdns->usb3_phy, PHY_MODE_USB_DEVICE);
0252 return 0;
0253 }
0254 EXPORT_SYMBOL_GPL(cdns_drd_gadget_on);
0255
0256
0257
0258
0259
0260 void cdns_drd_gadget_off(struct cdns *cdns)
0261 {
0262 u32 val;
0263
0264
0265
0266
0267
0268 usleep_range(20, 30);
0269 writel(OTGCMD_HOST_BUS_DROP | OTGCMD_DEV_BUS_DROP |
0270 OTGCMD_DEV_POWER_OFF | OTGCMD_HOST_POWER_OFF,
0271 &cdns->otg_regs->cmd);
0272
0273 readl_poll_timeout_atomic(&cdns->otg_regs->state, val,
0274 !(val & OTGSTATE_DEV_STATE_MASK),
0275 1, 2000000);
0276 phy_set_mode(cdns->usb3_phy, PHY_MODE_INVALID);
0277 }
0278 EXPORT_SYMBOL_GPL(cdns_drd_gadget_off);
0279
0280
0281
0282
0283
0284
0285
0286 static int cdns_init_otg_mode(struct cdns *cdns)
0287 {
0288 int ret;
0289
0290 cdns_otg_disable_irq(cdns);
0291
0292 writel(~0, &cdns->otg_irq_regs->ivect);
0293
0294 ret = cdns_set_mode(cdns, USB_DR_MODE_OTG);
0295 if (ret)
0296 return ret;
0297
0298 cdns_otg_enable_irq(cdns);
0299
0300 return 0;
0301 }
0302
0303
0304
0305
0306
0307
0308
0309 int cdns_drd_update_mode(struct cdns *cdns)
0310 {
0311 int ret;
0312
0313 switch (cdns->dr_mode) {
0314 case USB_DR_MODE_PERIPHERAL:
0315 ret = cdns_set_mode(cdns, USB_DR_MODE_PERIPHERAL);
0316 break;
0317 case USB_DR_MODE_HOST:
0318 ret = cdns_set_mode(cdns, USB_DR_MODE_HOST);
0319 break;
0320 case USB_DR_MODE_OTG:
0321 ret = cdns_init_otg_mode(cdns);
0322 break;
0323 default:
0324 dev_err(cdns->dev, "Unsupported mode of operation %d\n",
0325 cdns->dr_mode);
0326 return -EINVAL;
0327 }
0328
0329 return ret;
0330 }
0331
0332 static irqreturn_t cdns_drd_thread_irq(int irq, void *data)
0333 {
0334 struct cdns *cdns = data;
0335
0336 cdns_hw_role_switch(cdns);
0337
0338 return IRQ_HANDLED;
0339 }
0340
0341
0342
0343
0344
0345
0346
0347
0348
0349 static irqreturn_t cdns_drd_irq(int irq, void *data)
0350 {
0351 irqreturn_t ret = IRQ_NONE;
0352 struct cdns *cdns = data;
0353 u32 reg;
0354
0355 if (cdns->dr_mode != USB_DR_MODE_OTG)
0356 return IRQ_NONE;
0357
0358 if (cdns->in_lpm)
0359 return ret;
0360
0361 reg = readl(&cdns->otg_irq_regs->ivect);
0362
0363 if (!reg)
0364 return IRQ_NONE;
0365
0366 if (reg & OTGIEN_ID_CHANGE_INT) {
0367 dev_dbg(cdns->dev, "OTG IRQ: new ID: %d\n",
0368 cdns_get_id(cdns));
0369
0370 ret = IRQ_WAKE_THREAD;
0371 }
0372
0373 if (reg & (OTGIEN_VBUSVALID_RISE_INT | OTGIEN_VBUSVALID_FALL_INT)) {
0374 dev_dbg(cdns->dev, "OTG IRQ: new VBUS: %d\n",
0375 cdns_get_vbus(cdns));
0376
0377 ret = IRQ_WAKE_THREAD;
0378 }
0379
0380 writel(~0, &cdns->otg_irq_regs->ivect);
0381 return ret;
0382 }
0383
0384 int cdns_drd_init(struct cdns *cdns)
0385 {
0386 void __iomem *regs;
0387 u32 state;
0388 int ret;
0389
0390 regs = devm_ioremap_resource(cdns->dev, &cdns->otg_res);
0391 if (IS_ERR(regs))
0392 return PTR_ERR(regs);
0393
0394
0395
0396
0397
0398
0399
0400
0401
0402
0403 cdns->otg_v0_regs = regs;
0404 if (!readl(&cdns->otg_v0_regs->cmd)) {
0405 cdns->version = CDNS3_CONTROLLER_V0;
0406 cdns->otg_v1_regs = NULL;
0407 cdns->otg_cdnsp_regs = NULL;
0408 cdns->otg_regs = regs;
0409 cdns->otg_irq_regs = (struct cdns_otg_irq_regs __iomem *)
0410 &cdns->otg_v0_regs->ien;
0411 writel(1, &cdns->otg_v0_regs->simulate);
0412 dev_dbg(cdns->dev, "DRD version v0 (%08x)\n",
0413 readl(&cdns->otg_v0_regs->version));
0414 } else {
0415 cdns->otg_v0_regs = NULL;
0416 cdns->otg_v1_regs = regs;
0417 cdns->otg_cdnsp_regs = regs;
0418
0419 cdns->otg_regs = (void __iomem *)&cdns->otg_v1_regs->cmd;
0420
0421 if (readl(&cdns->otg_cdnsp_regs->did) == OTG_CDNSP_DID) {
0422 cdns->otg_irq_regs = (struct cdns_otg_irq_regs __iomem *)
0423 &cdns->otg_cdnsp_regs->ien;
0424 cdns->version = CDNSP_CONTROLLER_V2;
0425 } else {
0426 cdns->otg_irq_regs = (struct cdns_otg_irq_regs __iomem *)
0427 &cdns->otg_v1_regs->ien;
0428 writel(1, &cdns->otg_v1_regs->simulate);
0429 cdns->version = CDNS3_CONTROLLER_V1;
0430 }
0431
0432 dev_dbg(cdns->dev, "DRD version v1 (ID: %08x, rev: %08x)\n",
0433 readl(&cdns->otg_v1_regs->did),
0434 readl(&cdns->otg_v1_regs->rid));
0435 }
0436
0437 state = OTGSTS_STRAP(readl(&cdns->otg_regs->sts));
0438
0439
0440 cdns->dr_mode = USB_DR_MODE_OTG;
0441
0442 if ((cdns->version == CDNSP_CONTROLLER_V2 &&
0443 state == OTGSTS_CDNSP_STRAP_HOST) ||
0444 (cdns->version != CDNSP_CONTROLLER_V2 &&
0445 state == OTGSTS_STRAP_HOST)) {
0446 dev_dbg(cdns->dev, "Controller strapped to HOST\n");
0447 cdns->dr_mode = USB_DR_MODE_HOST;
0448 } else if ((cdns->version == CDNSP_CONTROLLER_V2 &&
0449 state == OTGSTS_CDNSP_STRAP_GADGET) ||
0450 (cdns->version != CDNSP_CONTROLLER_V2 &&
0451 state == OTGSTS_STRAP_GADGET)) {
0452 dev_dbg(cdns->dev, "Controller strapped to PERIPHERAL\n");
0453 cdns->dr_mode = USB_DR_MODE_PERIPHERAL;
0454 }
0455
0456 ret = devm_request_threaded_irq(cdns->dev, cdns->otg_irq,
0457 cdns_drd_irq,
0458 cdns_drd_thread_irq,
0459 IRQF_SHARED,
0460 dev_name(cdns->dev), cdns);
0461 if (ret) {
0462 dev_err(cdns->dev, "couldn't get otg_irq\n");
0463 return ret;
0464 }
0465
0466 state = readl(&cdns->otg_regs->sts);
0467 if (OTGSTS_OTG_NRDY(state)) {
0468 dev_err(cdns->dev, "Cadence USB3 OTG device not ready\n");
0469 return -ENODEV;
0470 }
0471
0472 return 0;
0473 }
0474
0475 int cdns_drd_exit(struct cdns *cdns)
0476 {
0477 cdns_otg_disable_irq(cdns);
0478
0479 return 0;
0480 }
0481
0482
0483
0484 bool cdns_power_is_lost(struct cdns *cdns)
0485 {
0486 if (cdns->version == CDNS3_CONTROLLER_V0) {
0487 if (!(readl(&cdns->otg_v0_regs->simulate) & BIT(0)))
0488 return true;
0489 } else {
0490 if (!(readl(&cdns->otg_v1_regs->simulate) & BIT(0)))
0491 return true;
0492 }
0493 return false;
0494 }
0495 EXPORT_SYMBOL_GPL(cdns_power_is_lost);