1 // SPDX-License-Identifier: GPL-2.0-or-later 2 /* 3 * AXP20x PMIC USB power supply status driver 4 * 5 * Copyright (C) 2015 Hans de Goede <hdegoede@redhat.com> 6 * Copyright (C) 2014 Bruno Prémont <bonbons@linux-vserver.org> 7 */ 8 9 #include <linux/bitops.h> 10 #include <linux/device.h> 11 #include <linux/devm-helpers.h> 12 #include <linux/init.h> 13 #include <linux/interrupt.h> 14 #include <linux/kernel.h> 15 #include <linux/mfd/axp20x.h> 16 #include <linux/module.h> 17 #include <linux/of.h> 18 #include <linux/platform_device.h> 19 #include <linux/pm.h> 20 #include <linux/power_supply.h> 21 #include <linux/regmap.h> 22 #include <linux/slab.h> 23 #include <linux/iio/consumer.h> 24 #include <linux/workqueue.h> 25 26 #define DRVNAME "axp20x-usb-power-supply" 27 28 #define AXP192_USB_OTG_STATUS 0x04 29 30 #define AXP20X_PWR_STATUS_VBUS_PRESENT BIT(5) 31 #define AXP20X_PWR_STATUS_VBUS_USED BIT(4) 32 33 #define AXP20X_USB_STATUS_VBUS_VALID BIT(2) 34 35 #define AXP20X_VBUS_VHOLD_uV(b) (4000000 + (((b) >> 3) & 7) * 100000) 36 #define AXP20X_VBUS_VHOLD_MASK GENMASK(5, 3) 37 #define AXP20X_VBUS_VHOLD_OFFSET 3 38 39 #define AXP20X_ADC_EN1_VBUS_CURR BIT(2) 40 #define AXP20X_ADC_EN1_VBUS_VOLT BIT(3) 41 42 /* 43 * Note do not raise the debounce time, we must report Vusb high within 44 * 100ms otherwise we get Vbus errors in musb. 45 */ 46 #define DEBOUNCE_TIME msecs_to_jiffies(50) 47 48 struct axp_data { 49 const struct power_supply_desc *power_desc; 50 const char * const *irq_names; 51 unsigned int num_irq_names; 52 const int *curr_lim_table; 53 int curr_lim_table_size; 54 struct reg_field curr_lim_fld; 55 struct reg_field vbus_valid_bit; 56 struct reg_field vbus_mon_bit; 57 struct reg_field usb_bc_en_bit; 58 struct reg_field usb_bc_det_fld; 59 struct reg_field vbus_disable_bit; 60 bool vbus_needs_polling: 1; 61 }; 62 63 struct axp20x_usb_power { 64 struct device *dev; 65 struct regmap *regmap; 66 struct regmap_field *curr_lim_fld; 67 struct regmap_field *vbus_valid_bit; 68 struct regmap_field *vbus_mon_bit; 69 struct regmap_field *usb_bc_en_bit; 70 struct regmap_field *usb_bc_det_fld; 71 struct regmap_field *vbus_disable_bit; 72 struct power_supply *supply; 73 const struct axp_data *axp_data; 74 struct iio_channel *vbus_v; 75 struct iio_channel *vbus_i; 76 struct delayed_work vbus_detect; 77 unsigned int old_status; 78 unsigned int online; 79 unsigned int num_irqs; 80 unsigned int irqs[] __counted_by(num_irqs); 81 }; 82 83 static bool axp20x_usb_vbus_needs_polling(struct axp20x_usb_power *power) 84 { 85 /* 86 * Polling is only necessary while VBUS is offline. While online, a 87 * present->absent transition implies an online->offline transition 88 * and will trigger the VBUS_REMOVAL IRQ. 89 */ 90 if (power->axp_data->vbus_needs_polling && !power->online) 91 return true; 92 93 return false; 94 } 95 96 static irqreturn_t axp20x_usb_power_irq(int irq, void *devid) 97 { 98 struct axp20x_usb_power *power = devid; 99 100 power_supply_changed(power->supply); 101 102 mod_delayed_work(system_power_efficient_wq, &power->vbus_detect, DEBOUNCE_TIME); 103 104 return IRQ_HANDLED; 105 } 106 107 static void axp20x_usb_power_poll_vbus(struct work_struct *work) 108 { 109 struct axp20x_usb_power *power = 110 container_of(work, struct axp20x_usb_power, vbus_detect.work); 111 unsigned int val; 112 int ret; 113 114 ret = regmap_read(power->regmap, AXP20X_PWR_INPUT_STATUS, &val); 115 if (ret) 116 goto out; 117 118 val &= (AXP20X_PWR_STATUS_VBUS_PRESENT | AXP20X_PWR_STATUS_VBUS_USED); 119 if (val != power->old_status) 120 power_supply_changed(power->supply); 121 122 if (power->usb_bc_en_bit && (val & AXP20X_PWR_STATUS_VBUS_PRESENT) != 123 (power->old_status & AXP20X_PWR_STATUS_VBUS_PRESENT)) { 124 dev_dbg(power->dev, "Cable status changed, re-enabling USB BC"); 125 ret = regmap_field_write(power->usb_bc_en_bit, 1); 126 if (ret) 127 dev_err(power->dev, "failed to enable USB BC: errno %d", 128 ret); 129 } 130 131 power->old_status = val; 132 power->online = val & AXP20X_PWR_STATUS_VBUS_USED; 133 134 out: 135 if (axp20x_usb_vbus_needs_polling(power)) 136 mod_delayed_work(system_power_efficient_wq, &power->vbus_detect, DEBOUNCE_TIME); 137 } 138 139 static int axp20x_get_usb_type(struct axp20x_usb_power *power, 140 union power_supply_propval *val) 141 { 142 unsigned int reg; 143 int ret; 144 145 if (!power->usb_bc_det_fld) 146 return -EINVAL; 147 148 ret = regmap_field_read(power->usb_bc_det_fld, ®); 149 if (ret) 150 return ret; 151 152 switch (reg) { 153 case 1: 154 val->intval = POWER_SUPPLY_USB_TYPE_SDP; 155 break; 156 case 2: 157 val->intval = POWER_SUPPLY_USB_TYPE_CDP; 158 break; 159 case 3: 160 val->intval = POWER_SUPPLY_USB_TYPE_DCP; 161 break; 162 default: 163 val->intval = POWER_SUPPLY_USB_TYPE_UNKNOWN; 164 break; 165 } 166 167 return 0; 168 } 169 170 static int axp20x_usb_power_get_property(struct power_supply *psy, 171 enum power_supply_property psp, union power_supply_propval *val) 172 { 173 struct axp20x_usb_power *power = power_supply_get_drvdata(psy); 174 unsigned int input, v; 175 int ret; 176 177 switch (psp) { 178 case POWER_SUPPLY_PROP_VOLTAGE_MIN: 179 ret = regmap_read(power->regmap, AXP20X_VBUS_IPSOUT_MGMT, &v); 180 if (ret) 181 return ret; 182 183 val->intval = AXP20X_VBUS_VHOLD_uV(v); 184 return 0; 185 case POWER_SUPPLY_PROP_VOLTAGE_NOW: 186 if (IS_ENABLED(CONFIG_AXP20X_ADC)) { 187 ret = iio_read_channel_processed(power->vbus_v, 188 &val->intval); 189 if (ret) 190 return ret; 191 192 /* 193 * IIO framework gives mV but Power Supply framework 194 * gives uV. 195 */ 196 val->intval *= 1000; 197 return 0; 198 } 199 200 ret = axp20x_read_variable_width(power->regmap, 201 AXP20X_VBUS_V_ADC_H, 12); 202 if (ret < 0) 203 return ret; 204 205 val->intval = ret * 1700; /* 1 step = 1.7 mV */ 206 return 0; 207 case POWER_SUPPLY_PROP_INPUT_CURRENT_LIMIT: 208 ret = regmap_field_read(power->curr_lim_fld, &v); 209 if (ret) 210 return ret; 211 212 if (v < power->axp_data->curr_lim_table_size) 213 val->intval = power->axp_data->curr_lim_table[v]; 214 else 215 val->intval = power->axp_data->curr_lim_table[ 216 power->axp_data->curr_lim_table_size - 1]; 217 return 0; 218 case POWER_SUPPLY_PROP_CURRENT_NOW: 219 if (IS_ENABLED(CONFIG_AXP20X_ADC)) { 220 ret = iio_read_channel_processed(power->vbus_i, 221 &val->intval); 222 if (ret) 223 return ret; 224 225 /* 226 * IIO framework gives mA but Power Supply framework 227 * gives uA. 228 */ 229 val->intval *= 1000; 230 return 0; 231 } 232 233 ret = axp20x_read_variable_width(power->regmap, 234 AXP20X_VBUS_I_ADC_H, 12); 235 if (ret < 0) 236 return ret; 237 238 val->intval = ret * 375; /* 1 step = 0.375 mA */ 239 return 0; 240 241 case POWER_SUPPLY_PROP_USB_TYPE: 242 return axp20x_get_usb_type(power, val); 243 default: 244 break; 245 } 246 247 /* All the properties below need the input-status reg value */ 248 ret = regmap_read(power->regmap, AXP20X_PWR_INPUT_STATUS, &input); 249 if (ret) 250 return ret; 251 252 switch (psp) { 253 case POWER_SUPPLY_PROP_HEALTH: 254 if (!(input & AXP20X_PWR_STATUS_VBUS_PRESENT)) { 255 val->intval = POWER_SUPPLY_HEALTH_UNKNOWN; 256 break; 257 } 258 259 val->intval = POWER_SUPPLY_HEALTH_GOOD; 260 261 if (power->vbus_valid_bit) { 262 ret = regmap_field_read(power->vbus_valid_bit, &v); 263 if (ret) 264 return ret; 265 266 if (v == 0) 267 val->intval = POWER_SUPPLY_HEALTH_UNSPEC_FAILURE; 268 } 269 270 break; 271 case POWER_SUPPLY_PROP_PRESENT: 272 val->intval = !!(input & AXP20X_PWR_STATUS_VBUS_PRESENT); 273 break; 274 case POWER_SUPPLY_PROP_ONLINE: 275 val->intval = !!(input & AXP20X_PWR_STATUS_VBUS_USED); 276 break; 277 default: 278 return -EINVAL; 279 } 280 281 return 0; 282 } 283 284 static int axp20x_usb_power_set_voltage_min(struct axp20x_usb_power *power, 285 int intval) 286 { 287 int val; 288 289 switch (intval) { 290 case 4000000: 291 case 4100000: 292 case 4200000: 293 case 4300000: 294 case 4400000: 295 case 4500000: 296 case 4600000: 297 case 4700000: 298 val = (intval - 4000000) / 100000; 299 return regmap_update_bits(power->regmap, 300 AXP20X_VBUS_IPSOUT_MGMT, 301 AXP20X_VBUS_VHOLD_MASK, 302 val << AXP20X_VBUS_VHOLD_OFFSET); 303 default: 304 return -EINVAL; 305 } 306 307 return -EINVAL; 308 } 309 310 static int axp20x_usb_power_set_input_current_limit(struct axp20x_usb_power *power, 311 int intval) 312 { 313 int ret; 314 unsigned int reg; 315 const unsigned int max = power->axp_data->curr_lim_table_size; 316 317 if (intval == -1) 318 return -EINVAL; 319 320 /* 321 * BC1.2 detection can cause a race condition if we try to set a current 322 * limit while it's in progress. When it finishes it will overwrite the 323 * current limit we just set. 324 */ 325 if (power->usb_bc_en_bit) { 326 dev_dbg(power->dev, 327 "disabling BC1.2 detection because current limit was set"); 328 ret = regmap_field_write(power->usb_bc_en_bit, 0); 329 if (ret) 330 return ret; 331 } 332 333 for (reg = max - 1; reg > 0; reg--) 334 if (power->axp_data->curr_lim_table[reg] <= intval) 335 break; 336 337 dev_dbg(power->dev, "setting input current limit reg to %d (%d uA), requested %d uA", 338 reg, power->axp_data->curr_lim_table[reg], intval); 339 340 return regmap_field_write(power->curr_lim_fld, reg); 341 } 342 343 static int axp20x_usb_power_set_property(struct power_supply *psy, 344 enum power_supply_property psp, 345 const union power_supply_propval *val) 346 { 347 struct axp20x_usb_power *power = power_supply_get_drvdata(psy); 348 349 switch (psp) { 350 case POWER_SUPPLY_PROP_ONLINE: 351 if (!power->vbus_disable_bit) 352 return -EINVAL; 353 354 return regmap_field_write(power->vbus_disable_bit, !val->intval); 355 356 case POWER_SUPPLY_PROP_VOLTAGE_MIN: 357 return axp20x_usb_power_set_voltage_min(power, val->intval); 358 359 case POWER_SUPPLY_PROP_INPUT_CURRENT_LIMIT: 360 return axp20x_usb_power_set_input_current_limit(power, val->intval); 361 362 default: 363 return -EINVAL; 364 } 365 366 return -EINVAL; 367 } 368 369 static int axp20x_usb_power_prop_writeable(struct power_supply *psy, 370 enum power_supply_property psp) 371 { 372 struct axp20x_usb_power *power = power_supply_get_drvdata(psy); 373 374 /* 375 * The VBUS path select flag works differently on AXP288 and newer: 376 * - On AXP20x and AXP22x, the flag enables VBUS (ignoring N_VBUSEN). 377 * - On AXP288 and AXP8xx, the flag disables VBUS (ignoring N_VBUSEN). 378 * We only expose the control on variants where it can be used to force 379 * the VBUS input offline. 380 */ 381 if (psp == POWER_SUPPLY_PROP_ONLINE) 382 return power->vbus_disable_bit != NULL; 383 384 return psp == POWER_SUPPLY_PROP_VOLTAGE_MIN || 385 psp == POWER_SUPPLY_PROP_INPUT_CURRENT_LIMIT; 386 } 387 388 static enum power_supply_property axp20x_usb_power_properties[] = { 389 POWER_SUPPLY_PROP_HEALTH, 390 POWER_SUPPLY_PROP_PRESENT, 391 POWER_SUPPLY_PROP_ONLINE, 392 POWER_SUPPLY_PROP_VOLTAGE_MIN, 393 POWER_SUPPLY_PROP_VOLTAGE_NOW, 394 POWER_SUPPLY_PROP_INPUT_CURRENT_LIMIT, 395 POWER_SUPPLY_PROP_CURRENT_NOW, 396 }; 397 398 static enum power_supply_property axp22x_usb_power_properties[] = { 399 POWER_SUPPLY_PROP_HEALTH, 400 POWER_SUPPLY_PROP_PRESENT, 401 POWER_SUPPLY_PROP_ONLINE, 402 POWER_SUPPLY_PROP_VOLTAGE_MIN, 403 POWER_SUPPLY_PROP_INPUT_CURRENT_LIMIT, 404 }; 405 406 static enum power_supply_property axp813_usb_power_properties[] = { 407 POWER_SUPPLY_PROP_HEALTH, 408 POWER_SUPPLY_PROP_PRESENT, 409 POWER_SUPPLY_PROP_ONLINE, 410 POWER_SUPPLY_PROP_VOLTAGE_MIN, 411 POWER_SUPPLY_PROP_INPUT_CURRENT_LIMIT, 412 POWER_SUPPLY_PROP_USB_TYPE, 413 }; 414 415 static const struct power_supply_desc axp20x_usb_power_desc = { 416 .name = "axp20x-usb", 417 .type = POWER_SUPPLY_TYPE_USB, 418 .properties = axp20x_usb_power_properties, 419 .num_properties = ARRAY_SIZE(axp20x_usb_power_properties), 420 .property_is_writeable = axp20x_usb_power_prop_writeable, 421 .get_property = axp20x_usb_power_get_property, 422 .set_property = axp20x_usb_power_set_property, 423 }; 424 425 static const struct power_supply_desc axp22x_usb_power_desc = { 426 .name = "axp20x-usb", 427 .type = POWER_SUPPLY_TYPE_USB, 428 .properties = axp22x_usb_power_properties, 429 .num_properties = ARRAY_SIZE(axp22x_usb_power_properties), 430 .property_is_writeable = axp20x_usb_power_prop_writeable, 431 .get_property = axp20x_usb_power_get_property, 432 .set_property = axp20x_usb_power_set_property, 433 }; 434 435 static const struct power_supply_desc axp813_usb_power_desc = { 436 .name = "axp20x-usb", 437 .type = POWER_SUPPLY_TYPE_USB, 438 .properties = axp813_usb_power_properties, 439 .num_properties = ARRAY_SIZE(axp813_usb_power_properties), 440 .property_is_writeable = axp20x_usb_power_prop_writeable, 441 .get_property = axp20x_usb_power_get_property, 442 .set_property = axp20x_usb_power_set_property, 443 .usb_types = BIT(POWER_SUPPLY_USB_TYPE_SDP) | 444 BIT(POWER_SUPPLY_USB_TYPE_CDP) | 445 BIT(POWER_SUPPLY_USB_TYPE_DCP) | 446 BIT(POWER_SUPPLY_USB_TYPE_UNKNOWN), 447 }; 448 449 static const char * const axp20x_irq_names[] = { 450 "VBUS_PLUGIN", 451 "VBUS_REMOVAL", 452 "VBUS_VALID", 453 "VBUS_NOT_VALID", 454 }; 455 456 static const char * const axp22x_irq_names[] = { 457 "VBUS_PLUGIN", 458 "VBUS_REMOVAL", 459 }; 460 461 static int axp192_usb_curr_lim_table[] = { 462 -1, 463 -1, 464 500000, 465 100000, 466 }; 467 468 static int axp20x_usb_curr_lim_table[] = { 469 900000, 470 500000, 471 100000, 472 -1, 473 }; 474 475 static int axp221_usb_curr_lim_table[] = { 476 900000, 477 500000, 478 -1, 479 -1, 480 }; 481 482 static int axp813_usb_curr_lim_table[] = { 483 100000, 484 500000, 485 900000, 486 1500000, 487 2000000, 488 2500000, 489 3000000, 490 3500000, 491 4000000, 492 }; 493 494 static const struct axp_data axp192_data = { 495 .power_desc = &axp20x_usb_power_desc, 496 .irq_names = axp20x_irq_names, 497 .num_irq_names = ARRAY_SIZE(axp20x_irq_names), 498 .curr_lim_table = axp192_usb_curr_lim_table, 499 .curr_lim_table_size = ARRAY_SIZE(axp192_usb_curr_lim_table), 500 .curr_lim_fld = REG_FIELD(AXP20X_VBUS_IPSOUT_MGMT, 0, 1), 501 .vbus_valid_bit = REG_FIELD(AXP192_USB_OTG_STATUS, 2, 2), 502 .vbus_mon_bit = REG_FIELD(AXP20X_VBUS_MON, 3, 3), 503 }; 504 505 static const struct axp_data axp202_data = { 506 .power_desc = &axp20x_usb_power_desc, 507 .irq_names = axp20x_irq_names, 508 .num_irq_names = ARRAY_SIZE(axp20x_irq_names), 509 .curr_lim_table = axp20x_usb_curr_lim_table, 510 .curr_lim_table_size = ARRAY_SIZE(axp20x_usb_curr_lim_table), 511 .curr_lim_fld = REG_FIELD(AXP20X_VBUS_IPSOUT_MGMT, 0, 1), 512 .vbus_valid_bit = REG_FIELD(AXP20X_USB_OTG_STATUS, 2, 2), 513 .vbus_mon_bit = REG_FIELD(AXP20X_VBUS_MON, 3, 3), 514 }; 515 516 static const struct axp_data axp221_data = { 517 .power_desc = &axp22x_usb_power_desc, 518 .irq_names = axp22x_irq_names, 519 .num_irq_names = ARRAY_SIZE(axp22x_irq_names), 520 .curr_lim_table = axp221_usb_curr_lim_table, 521 .curr_lim_table_size = ARRAY_SIZE(axp221_usb_curr_lim_table), 522 .curr_lim_fld = REG_FIELD(AXP20X_VBUS_IPSOUT_MGMT, 0, 1), 523 .vbus_needs_polling = true, 524 }; 525 526 static const struct axp_data axp223_data = { 527 .power_desc = &axp22x_usb_power_desc, 528 .irq_names = axp22x_irq_names, 529 .num_irq_names = ARRAY_SIZE(axp22x_irq_names), 530 .curr_lim_table = axp20x_usb_curr_lim_table, 531 .curr_lim_table_size = ARRAY_SIZE(axp20x_usb_curr_lim_table), 532 .curr_lim_fld = REG_FIELD(AXP20X_VBUS_IPSOUT_MGMT, 0, 1), 533 .vbus_needs_polling = true, 534 }; 535 536 static const struct axp_data axp813_data = { 537 .power_desc = &axp813_usb_power_desc, 538 .irq_names = axp22x_irq_names, 539 .num_irq_names = ARRAY_SIZE(axp22x_irq_names), 540 .curr_lim_table = axp813_usb_curr_lim_table, 541 .curr_lim_table_size = ARRAY_SIZE(axp813_usb_curr_lim_table), 542 .curr_lim_fld = REG_FIELD(AXP22X_CHRG_CTRL3, 4, 7), 543 .usb_bc_en_bit = REG_FIELD(AXP288_BC_GLOBAL, 0, 0), 544 .usb_bc_det_fld = REG_FIELD(AXP288_BC_DET_STAT, 5, 7), 545 .vbus_disable_bit = REG_FIELD(AXP20X_VBUS_IPSOUT_MGMT, 7, 7), 546 .vbus_needs_polling = true, 547 }; 548 549 #ifdef CONFIG_PM_SLEEP 550 static int axp20x_usb_power_suspend(struct device *dev) 551 { 552 struct axp20x_usb_power *power = dev_get_drvdata(dev); 553 int i = 0; 554 555 /* 556 * Allow wake via VBUS_PLUGIN only. 557 * 558 * As nested threaded IRQs are not automatically disabled during 559 * suspend, we must explicitly disable the remainder of the IRQs. 560 */ 561 if (device_may_wakeup(&power->supply->dev)) 562 enable_irq_wake(power->irqs[i++]); 563 while (i < power->num_irqs) 564 disable_irq(power->irqs[i++]); 565 566 return 0; 567 } 568 569 static int axp20x_usb_power_resume(struct device *dev) 570 { 571 struct axp20x_usb_power *power = dev_get_drvdata(dev); 572 int i = 0; 573 574 if (device_may_wakeup(&power->supply->dev)) 575 disable_irq_wake(power->irqs[i++]); 576 while (i < power->num_irqs) 577 enable_irq(power->irqs[i++]); 578 579 mod_delayed_work(system_power_efficient_wq, &power->vbus_detect, DEBOUNCE_TIME); 580 581 return 0; 582 } 583 #endif 584 585 static SIMPLE_DEV_PM_OPS(axp20x_usb_power_pm_ops, axp20x_usb_power_suspend, 586 axp20x_usb_power_resume); 587 588 static int configure_iio_channels(struct platform_device *pdev, 589 struct axp20x_usb_power *power) 590 { 591 power->vbus_v = devm_iio_channel_get(&pdev->dev, "vbus_v"); 592 if (IS_ERR(power->vbus_v)) { 593 if (PTR_ERR(power->vbus_v) == -ENODEV) 594 return -EPROBE_DEFER; 595 return PTR_ERR(power->vbus_v); 596 } 597 598 power->vbus_i = devm_iio_channel_get(&pdev->dev, "vbus_i"); 599 if (IS_ERR(power->vbus_i)) { 600 if (PTR_ERR(power->vbus_i) == -ENODEV) 601 return -EPROBE_DEFER; 602 return PTR_ERR(power->vbus_i); 603 } 604 605 return 0; 606 } 607 608 static int configure_adc_registers(struct axp20x_usb_power *power) 609 { 610 /* Enable vbus voltage and current measurement */ 611 return regmap_update_bits(power->regmap, AXP20X_ADC_EN1, 612 AXP20X_ADC_EN1_VBUS_CURR | 613 AXP20X_ADC_EN1_VBUS_VOLT, 614 AXP20X_ADC_EN1_VBUS_CURR | 615 AXP20X_ADC_EN1_VBUS_VOLT); 616 } 617 618 static int axp20x_regmap_field_alloc_optional(struct device *dev, 619 struct regmap *regmap, 620 struct reg_field fdesc, 621 struct regmap_field **fieldp) 622 { 623 struct regmap_field *field; 624 625 if (fdesc.reg == 0) { 626 *fieldp = NULL; 627 return 0; 628 } 629 630 field = devm_regmap_field_alloc(dev, regmap, fdesc); 631 if (IS_ERR(field)) 632 return PTR_ERR(field); 633 634 *fieldp = field; 635 return 0; 636 } 637 638 static int axp20x_usb_power_probe(struct platform_device *pdev) 639 { 640 struct axp20x_dev *axp20x = dev_get_drvdata(pdev->dev.parent); 641 struct power_supply_config psy_cfg = {}; 642 struct axp20x_usb_power *power; 643 const struct axp_data *axp_data; 644 int i, irq, ret; 645 646 if (!of_device_is_available(pdev->dev.of_node)) 647 return -ENODEV; 648 649 if (!axp20x) { 650 dev_err(&pdev->dev, "Parent drvdata not set\n"); 651 return -EINVAL; 652 } 653 654 axp_data = of_device_get_match_data(&pdev->dev); 655 656 power = devm_kzalloc(&pdev->dev, 657 struct_size(power, irqs, axp_data->num_irq_names), 658 GFP_KERNEL); 659 if (!power) 660 return -ENOMEM; 661 662 platform_set_drvdata(pdev, power); 663 664 power->dev = &pdev->dev; 665 power->axp_data = axp_data; 666 power->regmap = axp20x->regmap; 667 power->num_irqs = axp_data->num_irq_names; 668 669 power->curr_lim_fld = devm_regmap_field_alloc(&pdev->dev, power->regmap, 670 axp_data->curr_lim_fld); 671 if (IS_ERR(power->curr_lim_fld)) 672 return PTR_ERR(power->curr_lim_fld); 673 674 ret = axp20x_regmap_field_alloc_optional(&pdev->dev, power->regmap, 675 axp_data->vbus_valid_bit, 676 &power->vbus_valid_bit); 677 if (ret) 678 return ret; 679 680 ret = axp20x_regmap_field_alloc_optional(&pdev->dev, power->regmap, 681 axp_data->vbus_mon_bit, 682 &power->vbus_mon_bit); 683 if (ret) 684 return ret; 685 686 ret = axp20x_regmap_field_alloc_optional(&pdev->dev, power->regmap, 687 axp_data->usb_bc_en_bit, 688 &power->usb_bc_en_bit); 689 if (ret) 690 return ret; 691 692 ret = axp20x_regmap_field_alloc_optional(&pdev->dev, power->regmap, 693 axp_data->usb_bc_det_fld, 694 &power->usb_bc_det_fld); 695 if (ret) 696 return ret; 697 698 ret = axp20x_regmap_field_alloc_optional(&pdev->dev, power->regmap, 699 axp_data->vbus_disable_bit, 700 &power->vbus_disable_bit); 701 if (ret) 702 return ret; 703 704 ret = devm_delayed_work_autocancel(&pdev->dev, &power->vbus_detect, 705 axp20x_usb_power_poll_vbus); 706 if (ret) 707 return ret; 708 709 if (power->vbus_mon_bit) { 710 /* Enable vbus valid checking */ 711 ret = regmap_field_write(power->vbus_mon_bit, 1); 712 if (ret) 713 return ret; 714 715 if (IS_ENABLED(CONFIG_AXP20X_ADC)) 716 ret = configure_iio_channels(pdev, power); 717 else 718 ret = configure_adc_registers(power); 719 720 if (ret) 721 return ret; 722 } 723 724 if (power->usb_bc_en_bit) { 725 /* Enable USB Battery Charging specification detection */ 726 ret = regmap_field_write(power->usb_bc_en_bit, 1); 727 if (ret) 728 return ret; 729 } 730 731 psy_cfg.of_node = pdev->dev.of_node; 732 psy_cfg.drv_data = power; 733 734 power->supply = devm_power_supply_register(&pdev->dev, 735 axp_data->power_desc, 736 &psy_cfg); 737 if (IS_ERR(power->supply)) 738 return PTR_ERR(power->supply); 739 740 /* Request irqs after registering, as irqs may trigger immediately */ 741 for (i = 0; i < axp_data->num_irq_names; i++) { 742 irq = platform_get_irq_byname(pdev, axp_data->irq_names[i]); 743 if (irq < 0) 744 return irq; 745 746 power->irqs[i] = regmap_irq_get_virq(axp20x->regmap_irqc, irq); 747 ret = devm_request_any_context_irq(&pdev->dev, power->irqs[i], 748 axp20x_usb_power_irq, 0, 749 DRVNAME, power); 750 if (ret < 0) { 751 dev_err(&pdev->dev, "Error requesting %s IRQ: %d\n", 752 axp_data->irq_names[i], ret); 753 return ret; 754 } 755 } 756 757 if (axp20x_usb_vbus_needs_polling(power)) 758 queue_delayed_work(system_power_efficient_wq, &power->vbus_detect, 0); 759 760 return 0; 761 } 762 763 static const struct of_device_id axp20x_usb_power_match[] = { 764 { 765 .compatible = "x-powers,axp192-usb-power-supply", 766 .data = &axp192_data, 767 }, { 768 .compatible = "x-powers,axp202-usb-power-supply", 769 .data = &axp202_data, 770 }, { 771 .compatible = "x-powers,axp221-usb-power-supply", 772 .data = &axp221_data, 773 }, { 774 .compatible = "x-powers,axp223-usb-power-supply", 775 .data = &axp223_data, 776 }, { 777 .compatible = "x-powers,axp813-usb-power-supply", 778 .data = &axp813_data, 779 }, { /* sentinel */ } 780 }; 781 MODULE_DEVICE_TABLE(of, axp20x_usb_power_match); 782 783 static struct platform_driver axp20x_usb_power_driver = { 784 .probe = axp20x_usb_power_probe, 785 .driver = { 786 .name = DRVNAME, 787 .of_match_table = axp20x_usb_power_match, 788 .pm = &axp20x_usb_power_pm_ops, 789 }, 790 }; 791 792 module_platform_driver(axp20x_usb_power_driver); 793 794 MODULE_AUTHOR("Hans de Goede <hdegoede@redhat.com>"); 795 MODULE_DESCRIPTION("AXP20x PMIC USB power supply status driver"); 796 MODULE_LICENSE("GPL"); 797