1 // SPDX-License-Identifier: GPL-2.0-only 2 /* 3 * tusb1210.c - TUSB1210 USB ULPI PHY driver 4 * 5 * Copyright (C) 2015 Intel Corporation 6 * 7 * Author: Heikki Krogerus <heikki.krogerus@linux.intel.com> 8 */ 9 #include <linux/module.h> 10 #include <linux/bitfield.h> 11 #include <linux/delay.h> 12 #include <linux/ulpi/driver.h> 13 #include <linux/ulpi/regs.h> 14 #include <linux/gpio/consumer.h> 15 #include <linux/phy/ulpi_phy.h> 16 #include <linux/power_supply.h> 17 #include <linux/property.h> 18 #include <linux/workqueue.h> 19 20 #define TI_VENDOR_ID 0x0451 21 #define TI_DEVICE_TUSB1210 0x1507 22 #define TI_DEVICE_TUSB1211 0x1508 23 24 #define TUSB1211_POWER_CONTROL 0x3d 25 #define TUSB1211_POWER_CONTROL_SET 0x3e 26 #define TUSB1211_POWER_CONTROL_CLEAR 0x3f 27 #define TUSB1211_POWER_CONTROL_SW_CONTROL BIT(0) 28 #define TUSB1211_POWER_CONTROL_DET_COMP BIT(1) 29 #define TUSB1211_POWER_CONTROL_DP_VSRC_EN BIT(6) 30 31 #define TUSB1210_VENDOR_SPECIFIC2 0x80 32 #define TUSB1210_VENDOR_SPECIFIC2_IHSTX_MASK GENMASK(3, 0) 33 #define TUSB1210_VENDOR_SPECIFIC2_ZHSDRV_MASK GENMASK(5, 4) 34 #define TUSB1210_VENDOR_SPECIFIC2_DP_MASK BIT(6) 35 36 #define TUSB1211_VENDOR_SPECIFIC3 0x85 37 #define TUSB1211_VENDOR_SPECIFIC3_SET 0x86 38 #define TUSB1211_VENDOR_SPECIFIC3_CLEAR 0x87 39 #define TUSB1211_VENDOR_SPECIFIC3_SW_USB_DET BIT(4) 40 #define TUSB1211_VENDOR_SPECIFIC3_CHGD_IDP_SRC_EN BIT(6) 41 42 #define TUSB1210_RESET_TIME_MS 50 43 44 #define TUSB1210_CHG_DET_MAX_RETRIES 5 45 46 /* TUSB1210 charger detection work states */ 47 enum tusb1210_chg_det_state { 48 TUSB1210_CHG_DET_CONNECTING, 49 TUSB1210_CHG_DET_START_DET, 50 TUSB1210_CHG_DET_READ_DET, 51 TUSB1210_CHG_DET_FINISH_DET, 52 TUSB1210_CHG_DET_CONNECTED, 53 TUSB1210_CHG_DET_DISCONNECTING, 54 TUSB1210_CHG_DET_DISCONNECTING_DONE, 55 TUSB1210_CHG_DET_DISCONNECTED, 56 }; 57 58 struct tusb1210 { 59 struct device *dev; 60 struct phy *phy; 61 struct gpio_desc *gpio_reset; 62 struct gpio_desc *gpio_cs; 63 u8 otg_ctrl; 64 u8 vendor_specific2; 65 #ifdef CONFIG_POWER_SUPPLY 66 enum power_supply_usb_type chg_type; 67 enum tusb1210_chg_det_state chg_det_state; 68 int chg_det_retries; 69 struct delayed_work chg_det_work; 70 struct notifier_block psy_nb; 71 struct power_supply *psy; 72 #endif 73 }; 74 75 static int tusb1210_ulpi_write(struct tusb1210 *tusb, u8 reg, u8 val) 76 { 77 struct device *dev = tusb->dev; 78 int ret; 79 80 ret = ulpi_write(to_ulpi_dev(dev), reg, val); 81 if (ret) 82 dev_err(dev, "error %d writing val 0x%02x to reg 0x%02x\n", ret, val, reg); 83 84 return ret; 85 } 86 87 static int tusb1210_ulpi_read(struct tusb1210 *tusb, u8 reg, u8 *val) 88 { 89 struct device *dev = tusb->dev; 90 int ret; 91 92 ret = ulpi_read(to_ulpi_dev(dev), reg); 93 if (ret >= 0) { 94 *val = ret; 95 ret = 0; 96 } else { 97 dev_err(dev, "error %d reading reg 0x%02x\n", ret, reg); 98 } 99 100 return ret; 101 } 102 103 static int tusb1210_power_on(struct phy *phy) 104 { 105 struct tusb1210 *tusb = phy_get_drvdata(phy); 106 107 gpiod_set_value_cansleep(tusb->gpio_reset, 1); 108 gpiod_set_value_cansleep(tusb->gpio_cs, 1); 109 110 msleep(TUSB1210_RESET_TIME_MS); 111 112 /* Restore the optional eye diagram optimization value */ 113 tusb1210_ulpi_write(tusb, TUSB1210_VENDOR_SPECIFIC2, tusb->vendor_specific2); 114 115 return 0; 116 } 117 118 static int tusb1210_power_off(struct phy *phy) 119 { 120 struct tusb1210 *tusb = phy_get_drvdata(phy); 121 122 gpiod_set_value_cansleep(tusb->gpio_reset, 0); 123 gpiod_set_value_cansleep(tusb->gpio_cs, 0); 124 125 return 0; 126 } 127 128 static int tusb1210_set_mode(struct phy *phy, enum phy_mode mode, int submode) 129 { 130 struct tusb1210 *tusb = phy_get_drvdata(phy); 131 int ret; 132 u8 reg; 133 134 ret = tusb1210_ulpi_read(tusb, ULPI_OTG_CTRL, ®); 135 if (ret < 0) 136 return ret; 137 138 switch (mode) { 139 case PHY_MODE_USB_HOST: 140 reg |= (ULPI_OTG_CTRL_DRVVBUS_EXT 141 | ULPI_OTG_CTRL_ID_PULLUP 142 | ULPI_OTG_CTRL_DP_PULLDOWN 143 | ULPI_OTG_CTRL_DM_PULLDOWN); 144 tusb1210_ulpi_write(tusb, ULPI_OTG_CTRL, reg); 145 reg |= ULPI_OTG_CTRL_DRVVBUS; 146 break; 147 case PHY_MODE_USB_DEVICE: 148 reg &= ~(ULPI_OTG_CTRL_DRVVBUS 149 | ULPI_OTG_CTRL_DP_PULLDOWN 150 | ULPI_OTG_CTRL_DM_PULLDOWN); 151 tusb1210_ulpi_write(tusb, ULPI_OTG_CTRL, reg); 152 reg &= ~ULPI_OTG_CTRL_DRVVBUS_EXT; 153 break; 154 default: 155 /* nothing */ 156 return 0; 157 } 158 159 tusb->otg_ctrl = reg; 160 return tusb1210_ulpi_write(tusb, ULPI_OTG_CTRL, reg); 161 } 162 163 #ifdef CONFIG_POWER_SUPPLY 164 static const char * const tusb1210_chg_det_states[] = { 165 "CHG_DET_CONNECTING", 166 "CHG_DET_START_DET", 167 "CHG_DET_READ_DET", 168 "CHG_DET_FINISH_DET", 169 "CHG_DET_CONNECTED", 170 "CHG_DET_DISCONNECTING", 171 "CHG_DET_DISCONNECTING_DONE", 172 "CHG_DET_DISCONNECTED", 173 }; 174 175 static void tusb1210_reset(struct tusb1210 *tusb) 176 { 177 gpiod_set_value_cansleep(tusb->gpio_reset, 0); 178 usleep_range(200, 500); 179 gpiod_set_value_cansleep(tusb->gpio_reset, 1); 180 } 181 182 static void tusb1210_chg_det_set_type(struct tusb1210 *tusb, 183 enum power_supply_usb_type type) 184 { 185 dev_dbg(tusb->dev, "charger type: %d\n", type); 186 tusb->chg_type = type; 187 tusb->chg_det_retries = 0; 188 power_supply_changed(tusb->psy); 189 } 190 191 static void tusb1210_chg_det_set_state(struct tusb1210 *tusb, 192 enum tusb1210_chg_det_state new_state, 193 int delay_ms) 194 { 195 if (delay_ms) 196 dev_dbg(tusb->dev, "chg_det new state %s in %d ms\n", 197 tusb1210_chg_det_states[new_state], delay_ms); 198 199 tusb->chg_det_state = new_state; 200 mod_delayed_work(system_long_wq, &tusb->chg_det_work, 201 msecs_to_jiffies(delay_ms)); 202 } 203 204 static void tusb1210_chg_det_handle_ulpi_error(struct tusb1210 *tusb) 205 { 206 tusb1210_reset(tusb); 207 if (tusb->chg_det_retries < TUSB1210_CHG_DET_MAX_RETRIES) { 208 tusb->chg_det_retries++; 209 tusb1210_chg_det_set_state(tusb, TUSB1210_CHG_DET_START_DET, 210 TUSB1210_RESET_TIME_MS); 211 } else { 212 tusb1210_chg_det_set_state(tusb, TUSB1210_CHG_DET_FINISH_DET, 213 TUSB1210_RESET_TIME_MS); 214 } 215 } 216 217 /* 218 * Boards using a TUSB121x for charger-detection have 3 power_supply class devs: 219 * 220 * tusb1211-charger-detect(1) -> charger -> fuel-gauge 221 * 222 * To determine if an USB charger is connected to the board, the online prop of 223 * the charger psy needs to be read. Since the tusb1211-charger-detect psy is 224 * the start of the supplier -> supplied-to chain, power_supply_am_i_supplied() 225 * cannot be used here. 226 * 227 * Instead, below is a list of the power_supply names of known chargers for 228 * these boards and the charger psy is looked up by name from this list. 229 * 230 * (1) modelling the external USB charger 231 */ 232 static const char * const tusb1210_chargers[] = { 233 "bq24190-charger", 234 }; 235 236 static bool tusb1210_get_online(struct tusb1210 *tusb) 237 { 238 struct power_supply *charger = NULL; 239 union power_supply_propval val; 240 bool online = false; 241 int i, ret; 242 243 for (i = 0; i < ARRAY_SIZE(tusb1210_chargers) && !charger; i++) 244 charger = power_supply_get_by_name(tusb1210_chargers[i]); 245 246 if (!charger) 247 return false; 248 249 ret = power_supply_get_property(charger, POWER_SUPPLY_PROP_ONLINE, &val); 250 if (ret == 0) 251 online = val.intval; 252 253 power_supply_put(charger); 254 255 return online; 256 } 257 258 static void tusb1210_chg_det_work(struct work_struct *work) 259 { 260 struct tusb1210 *tusb = container_of(work, struct tusb1210, chg_det_work.work); 261 bool vbus_present = tusb1210_get_online(tusb); 262 int ret; 263 u8 val; 264 265 dev_dbg(tusb->dev, "chg_det state %s vbus_present %d\n", 266 tusb1210_chg_det_states[tusb->chg_det_state], vbus_present); 267 268 switch (tusb->chg_det_state) { 269 case TUSB1210_CHG_DET_CONNECTING: 270 tusb->chg_type = POWER_SUPPLY_USB_TYPE_UNKNOWN; 271 tusb->chg_det_retries = 0; 272 /* Power on USB controller for ulpi_read()/_write() */ 273 ret = pm_runtime_resume_and_get(tusb->dev->parent); 274 if (ret < 0) { 275 dev_err(tusb->dev, "error %d runtime-resuming\n", ret); 276 /* Should never happen, skip charger detection */ 277 tusb1210_chg_det_set_state(tusb, TUSB1210_CHG_DET_CONNECTED, 0); 278 return; 279 } 280 tusb1210_chg_det_set_state(tusb, TUSB1210_CHG_DET_START_DET, 0); 281 break; 282 case TUSB1210_CHG_DET_START_DET: 283 /* 284 * Use the builtin charger detection FSM to keep things simple. 285 * This only detects DCP / SDP. This is good enough for the few 286 * boards which actually rely on the phy for charger detection. 287 */ 288 mutex_lock(&tusb->phy->mutex); 289 ret = tusb1210_ulpi_write(tusb, TUSB1211_VENDOR_SPECIFIC3_SET, 290 TUSB1211_VENDOR_SPECIFIC3_SW_USB_DET); 291 mutex_unlock(&tusb->phy->mutex); 292 if (ret) { 293 tusb1210_chg_det_handle_ulpi_error(tusb); 294 break; 295 } 296 297 /* Wait 400 ms for the charger detection FSM to finish */ 298 tusb1210_chg_det_set_state(tusb, TUSB1210_CHG_DET_READ_DET, 400); 299 break; 300 case TUSB1210_CHG_DET_READ_DET: 301 mutex_lock(&tusb->phy->mutex); 302 ret = tusb1210_ulpi_read(tusb, TUSB1211_POWER_CONTROL, &val); 303 mutex_unlock(&tusb->phy->mutex); 304 if (ret) { 305 tusb1210_chg_det_handle_ulpi_error(tusb); 306 break; 307 } 308 309 if (val & TUSB1211_POWER_CONTROL_DET_COMP) 310 tusb1210_chg_det_set_type(tusb, POWER_SUPPLY_USB_TYPE_DCP); 311 else 312 tusb1210_chg_det_set_type(tusb, POWER_SUPPLY_USB_TYPE_SDP); 313 314 tusb1210_chg_det_set_state(tusb, TUSB1210_CHG_DET_FINISH_DET, 0); 315 break; 316 case TUSB1210_CHG_DET_FINISH_DET: 317 mutex_lock(&tusb->phy->mutex); 318 319 /* Set SW_CONTROL to stop the charger-det FSM */ 320 ret = tusb1210_ulpi_write(tusb, TUSB1211_POWER_CONTROL_SET, 321 TUSB1211_POWER_CONTROL_SW_CONTROL); 322 323 /* Clear DP_VSRC_EN which may have been enabled by the charger-det FSM */ 324 ret |= tusb1210_ulpi_write(tusb, TUSB1211_POWER_CONTROL_CLEAR, 325 TUSB1211_POWER_CONTROL_DP_VSRC_EN); 326 327 /* Clear CHGD_IDP_SRC_EN (may have been enabled by the charger-det FSM) */ 328 ret |= tusb1210_ulpi_write(tusb, TUSB1211_VENDOR_SPECIFIC3_CLEAR, 329 TUSB1211_VENDOR_SPECIFIC3_CHGD_IDP_SRC_EN); 330 331 /* If any of the above fails reset the phy */ 332 if (ret) { 333 tusb1210_reset(tusb); 334 msleep(TUSB1210_RESET_TIME_MS); 335 } 336 337 /* Restore phy-parameters and OTG_CTRL register */ 338 tusb1210_ulpi_write(tusb, ULPI_OTG_CTRL, tusb->otg_ctrl); 339 tusb1210_ulpi_write(tusb, TUSB1210_VENDOR_SPECIFIC2, 340 tusb->vendor_specific2); 341 342 mutex_unlock(&tusb->phy->mutex); 343 344 pm_runtime_put(tusb->dev->parent); 345 tusb1210_chg_det_set_state(tusb, TUSB1210_CHG_DET_CONNECTED, 0); 346 break; 347 case TUSB1210_CHG_DET_CONNECTED: 348 if (!vbus_present) 349 tusb1210_chg_det_set_state(tusb, TUSB1210_CHG_DET_DISCONNECTING, 0); 350 break; 351 case TUSB1210_CHG_DET_DISCONNECTING: 352 /* 353 * The phy seems to take approx. 600ms longer then the charger 354 * chip (which is used to get vbus_present) to determine Vbus 355 * session end. Wait 800ms to ensure the phy has detected and 356 * signalled Vbus session end. 357 */ 358 tusb1210_chg_det_set_state(tusb, TUSB1210_CHG_DET_DISCONNECTING_DONE, 800); 359 break; 360 case TUSB1210_CHG_DET_DISCONNECTING_DONE: 361 /* 362 * The phy often stops reacting to ulpi_read()/_write requests 363 * after a Vbus-session end. Reset it to work around this. 364 */ 365 tusb1210_reset(tusb); 366 tusb1210_chg_det_set_type(tusb, POWER_SUPPLY_USB_TYPE_UNKNOWN); 367 tusb1210_chg_det_set_state(tusb, TUSB1210_CHG_DET_DISCONNECTED, 0); 368 break; 369 case TUSB1210_CHG_DET_DISCONNECTED: 370 if (vbus_present) 371 tusb1210_chg_det_set_state(tusb, TUSB1210_CHG_DET_CONNECTING, 0); 372 break; 373 } 374 } 375 376 static int tusb1210_psy_notifier(struct notifier_block *nb, 377 unsigned long event, void *ptr) 378 { 379 struct tusb1210 *tusb = container_of(nb, struct tusb1210, psy_nb); 380 struct power_supply *psy = ptr; 381 382 if (psy != tusb->psy && psy->desc->type == POWER_SUPPLY_TYPE_USB) 383 queue_delayed_work(system_long_wq, &tusb->chg_det_work, 0); 384 385 return NOTIFY_OK; 386 } 387 388 static int tusb1210_psy_get_prop(struct power_supply *psy, 389 enum power_supply_property psp, 390 union power_supply_propval *val) 391 { 392 struct tusb1210 *tusb = power_supply_get_drvdata(psy); 393 394 switch (psp) { 395 case POWER_SUPPLY_PROP_ONLINE: 396 val->intval = tusb1210_get_online(tusb); 397 break; 398 case POWER_SUPPLY_PROP_USB_TYPE: 399 val->intval = tusb->chg_type; 400 break; 401 case POWER_SUPPLY_PROP_CURRENT_MAX: 402 if (tusb->chg_type == POWER_SUPPLY_USB_TYPE_DCP) 403 val->intval = 2000000; 404 else 405 val->intval = 500000; 406 break; 407 default: 408 return -EINVAL; 409 } 410 411 return 0; 412 } 413 414 static const enum power_supply_usb_type tusb1210_psy_usb_types[] = { 415 POWER_SUPPLY_USB_TYPE_SDP, 416 POWER_SUPPLY_USB_TYPE_DCP, 417 POWER_SUPPLY_USB_TYPE_UNKNOWN, 418 }; 419 420 static const enum power_supply_property tusb1210_psy_props[] = { 421 POWER_SUPPLY_PROP_ONLINE, 422 POWER_SUPPLY_PROP_USB_TYPE, 423 POWER_SUPPLY_PROP_CURRENT_MAX, 424 }; 425 426 static const struct power_supply_desc tusb1210_psy_desc = { 427 .name = "tusb1211-charger-detect", 428 .type = POWER_SUPPLY_TYPE_USB, 429 .usb_types = tusb1210_psy_usb_types, 430 .num_usb_types = ARRAY_SIZE(tusb1210_psy_usb_types), 431 .properties = tusb1210_psy_props, 432 .num_properties = ARRAY_SIZE(tusb1210_psy_props), 433 .get_property = tusb1210_psy_get_prop, 434 }; 435 436 /* Setup charger detection if requested, on errors continue without chg-det */ 437 static void tusb1210_probe_charger_detect(struct tusb1210 *tusb) 438 { 439 struct power_supply_config psy_cfg = { .drv_data = tusb }; 440 struct device *dev = tusb->dev; 441 struct ulpi *ulpi = to_ulpi_dev(dev); 442 int ret; 443 444 if (!device_property_read_bool(dev->parent, "linux,phy_charger_detect")) 445 return; 446 447 if (ulpi->id.product != TI_DEVICE_TUSB1211) { 448 dev_err(dev, "error charger detection is only supported on the TUSB1211\n"); 449 return; 450 } 451 452 ret = tusb1210_ulpi_read(tusb, ULPI_OTG_CTRL, &tusb->otg_ctrl); 453 if (ret) 454 return; 455 456 tusb->psy = power_supply_register(dev, &tusb1210_psy_desc, &psy_cfg); 457 if (IS_ERR(tusb->psy)) 458 return; 459 460 /* 461 * Delay initial run by 2 seconds to allow the charger driver, 462 * which is used to determine vbus_present, to load. 463 */ 464 tusb->chg_det_state = TUSB1210_CHG_DET_DISCONNECTED; 465 INIT_DELAYED_WORK(&tusb->chg_det_work, tusb1210_chg_det_work); 466 queue_delayed_work(system_long_wq, &tusb->chg_det_work, 2 * HZ); 467 468 tusb->psy_nb.notifier_call = tusb1210_psy_notifier; 469 power_supply_reg_notifier(&tusb->psy_nb); 470 } 471 472 static void tusb1210_remove_charger_detect(struct tusb1210 *tusb) 473 { 474 475 if (!IS_ERR_OR_NULL(tusb->psy)) { 476 power_supply_unreg_notifier(&tusb->psy_nb); 477 cancel_delayed_work_sync(&tusb->chg_det_work); 478 power_supply_unregister(tusb->psy); 479 } 480 } 481 #else 482 static void tusb1210_probe_charger_detect(struct tusb1210 *tusb) { } 483 static void tusb1210_remove_charger_detect(struct tusb1210 *tusb) { } 484 #endif 485 486 static const struct phy_ops phy_ops = { 487 .power_on = tusb1210_power_on, 488 .power_off = tusb1210_power_off, 489 .set_mode = tusb1210_set_mode, 490 .owner = THIS_MODULE, 491 }; 492 493 static int tusb1210_probe(struct ulpi *ulpi) 494 { 495 struct device *dev = &ulpi->dev; 496 struct tusb1210 *tusb; 497 u8 val, reg; 498 int ret; 499 500 tusb = devm_kzalloc(dev, sizeof(*tusb), GFP_KERNEL); 501 if (!tusb) 502 return -ENOMEM; 503 504 tusb->dev = dev; 505 506 tusb->gpio_reset = devm_gpiod_get_optional(dev, "reset", GPIOD_OUT_LOW); 507 if (IS_ERR(tusb->gpio_reset)) 508 return PTR_ERR(tusb->gpio_reset); 509 510 gpiod_set_value_cansleep(tusb->gpio_reset, 1); 511 512 tusb->gpio_cs = devm_gpiod_get_optional(dev, "cs", GPIOD_OUT_LOW); 513 if (IS_ERR(tusb->gpio_cs)) 514 return PTR_ERR(tusb->gpio_cs); 515 516 gpiod_set_value_cansleep(tusb->gpio_cs, 1); 517 518 /* 519 * VENDOR_SPECIFIC2 register in TUSB1210 can be used for configuring eye 520 * diagram optimization and DP/DM swap. 521 */ 522 523 ret = tusb1210_ulpi_read(tusb, TUSB1210_VENDOR_SPECIFIC2, ®); 524 if (ret) 525 return ret; 526 527 /* High speed output drive strength configuration */ 528 if (!device_property_read_u8(dev, "ihstx", &val)) 529 u8p_replace_bits(®, val, (u8)TUSB1210_VENDOR_SPECIFIC2_IHSTX_MASK); 530 531 /* High speed output impedance configuration */ 532 if (!device_property_read_u8(dev, "zhsdrv", &val)) 533 u8p_replace_bits(®, val, (u8)TUSB1210_VENDOR_SPECIFIC2_ZHSDRV_MASK); 534 535 /* DP/DM swap control */ 536 if (!device_property_read_u8(dev, "datapolarity", &val)) 537 u8p_replace_bits(®, val, (u8)TUSB1210_VENDOR_SPECIFIC2_DP_MASK); 538 539 ret = tusb1210_ulpi_write(tusb, TUSB1210_VENDOR_SPECIFIC2, reg); 540 if (ret) 541 return ret; 542 543 tusb->vendor_specific2 = reg; 544 545 tusb1210_probe_charger_detect(tusb); 546 547 tusb->phy = ulpi_phy_create(ulpi, &phy_ops); 548 if (IS_ERR(tusb->phy)) { 549 ret = PTR_ERR(tusb->phy); 550 goto err_remove_charger; 551 } 552 553 phy_set_drvdata(tusb->phy, tusb); 554 ulpi_set_drvdata(ulpi, tusb); 555 return 0; 556 557 err_remove_charger: 558 tusb1210_remove_charger_detect(tusb); 559 return ret; 560 } 561 562 static void tusb1210_remove(struct ulpi *ulpi) 563 { 564 struct tusb1210 *tusb = ulpi_get_drvdata(ulpi); 565 566 ulpi_phy_destroy(ulpi, tusb->phy); 567 tusb1210_remove_charger_detect(tusb); 568 } 569 570 static const struct ulpi_device_id tusb1210_ulpi_id[] = { 571 { TI_VENDOR_ID, TI_DEVICE_TUSB1210 }, 572 { TI_VENDOR_ID, TI_DEVICE_TUSB1211 }, 573 { }, 574 }; 575 MODULE_DEVICE_TABLE(ulpi, tusb1210_ulpi_id); 576 577 static struct ulpi_driver tusb1210_driver = { 578 .id_table = tusb1210_ulpi_id, 579 .probe = tusb1210_probe, 580 .remove = tusb1210_remove, 581 .driver = { 582 .name = "tusb1210", 583 .owner = THIS_MODULE, 584 }, 585 }; 586 587 module_ulpi_driver(tusb1210_driver); 588 589 MODULE_AUTHOR("Intel Corporation"); 590 MODULE_LICENSE("GPL v2"); 591 MODULE_DESCRIPTION("TUSB1210 ULPI PHY driver"); 592