1 // SPDX-License-Identifier: GPL-2.0 2 /* 3 * Copyright (C) 2018 MediaTek Inc. 4 * 5 * Author: Sean Wang <sean.wang@mediatek.com> 6 * 7 */ 8 9 #include <dt-bindings/pinctrl/mt65xx.h> 10 #include <linux/device.h> 11 #include <linux/err.h> 12 #include <linux/gpio/driver.h> 13 #include <linux/platform_device.h> 14 #include <linux/io.h> 15 #include <linux/module.h> 16 #include <linux/of_irq.h> 17 18 #include "mtk-eint.h" 19 #include "pinctrl-mtk-common-v2.h" 20 21 /** 22 * struct mtk_drive_desc - the structure that holds the information 23 * of the driving current 24 * @min: the minimum current of this group 25 * @max: the maximum current of this group 26 * @step: the step current of this group 27 * @scal: the weight factor 28 * 29 * formula: output = ((input) / step - 1) * scal 30 */ 31 struct mtk_drive_desc { 32 u8 min; 33 u8 max; 34 u8 step; 35 u8 scal; 36 }; 37 38 /* The groups of drive strength */ 39 static const struct mtk_drive_desc mtk_drive[] = { 40 [DRV_GRP0] = { 4, 16, 4, 1 }, 41 [DRV_GRP1] = { 4, 16, 4, 2 }, 42 [DRV_GRP2] = { 2, 8, 2, 1 }, 43 [DRV_GRP3] = { 2, 8, 2, 2 }, 44 [DRV_GRP4] = { 2, 16, 2, 1 }, 45 }; 46 47 static void mtk_w32(struct mtk_pinctrl *pctl, u8 i, u32 reg, u32 val) 48 { 49 writel_relaxed(val, pctl->base[i] + reg); 50 } 51 52 static u32 mtk_r32(struct mtk_pinctrl *pctl, u8 i, u32 reg) 53 { 54 return readl_relaxed(pctl->base[i] + reg); 55 } 56 57 void mtk_rmw(struct mtk_pinctrl *pctl, u8 i, u32 reg, u32 mask, u32 set) 58 { 59 u32 val; 60 unsigned long flags; 61 62 spin_lock_irqsave(&pctl->lock, flags); 63 64 val = mtk_r32(pctl, i, reg); 65 val &= ~mask; 66 val |= set; 67 mtk_w32(pctl, i, reg, val); 68 69 spin_unlock_irqrestore(&pctl->lock, flags); 70 } 71 72 static int mtk_hw_pin_field_lookup(struct mtk_pinctrl *hw, 73 const struct mtk_pin_desc *desc, 74 int field, struct mtk_pin_field *pfd) 75 { 76 const struct mtk_pin_field_calc *c; 77 const struct mtk_pin_reg_calc *rc; 78 int start = 0, end, check; 79 bool found = false; 80 u32 bits; 81 82 if (hw->soc->reg_cal && hw->soc->reg_cal[field].range) { 83 rc = &hw->soc->reg_cal[field]; 84 } else { 85 dev_dbg(hw->dev, 86 "Not support field %d for this soc\n", field); 87 return -ENOTSUPP; 88 } 89 90 end = rc->nranges - 1; 91 92 while (start <= end) { 93 check = (start + end) >> 1; 94 if (desc->number >= rc->range[check].s_pin 95 && desc->number <= rc->range[check].e_pin) { 96 found = true; 97 break; 98 } else if (start == end) 99 break; 100 else if (desc->number < rc->range[check].s_pin) 101 end = check - 1; 102 else 103 start = check + 1; 104 } 105 106 if (!found) { 107 dev_dbg(hw->dev, "Not support field %d for pin = %d (%s)\n", 108 field, desc->number, desc->name); 109 return -ENOTSUPP; 110 } 111 112 c = rc->range + check; 113 114 if (c->i_base > hw->nbase - 1) { 115 dev_err(hw->dev, 116 "Invalid base for field %d for pin = %d (%s)\n", 117 field, desc->number, desc->name); 118 return -EINVAL; 119 } 120 121 /* Calculated bits as the overall offset the pin is located at, 122 * if c->fixed is held, that determines the all the pins in the 123 * range use the same field with the s_pin. 124 */ 125 bits = c->fixed ? c->s_bit : c->s_bit + 126 (desc->number - c->s_pin) * (c->x_bits); 127 128 /* Fill pfd from bits. For example 32-bit register applied is assumed 129 * when c->sz_reg is equal to 32. 130 */ 131 pfd->index = c->i_base; 132 pfd->offset = c->s_addr + c->x_addrs * (bits / c->sz_reg); 133 pfd->bitpos = bits % c->sz_reg; 134 pfd->mask = (1 << c->x_bits) - 1; 135 136 /* pfd->next is used for indicating that bit wrapping-around happens 137 * which requires the manipulation for bit 0 starting in the next 138 * register to form the complete field read/write. 139 */ 140 pfd->next = pfd->bitpos + c->x_bits > c->sz_reg ? c->x_addrs : 0; 141 142 return 0; 143 } 144 145 static int mtk_hw_pin_field_get(struct mtk_pinctrl *hw, 146 const struct mtk_pin_desc *desc, 147 int field, struct mtk_pin_field *pfd) 148 { 149 if (field < 0 || field >= PINCTRL_PIN_REG_MAX) { 150 dev_err(hw->dev, "Invalid Field %d\n", field); 151 return -EINVAL; 152 } 153 154 return mtk_hw_pin_field_lookup(hw, desc, field, pfd); 155 } 156 157 static void mtk_hw_bits_part(struct mtk_pin_field *pf, int *h, int *l) 158 { 159 *l = 32 - pf->bitpos; 160 *h = get_count_order(pf->mask) - *l; 161 } 162 163 static void mtk_hw_write_cross_field(struct mtk_pinctrl *hw, 164 struct mtk_pin_field *pf, int value) 165 { 166 int nbits_l, nbits_h; 167 168 mtk_hw_bits_part(pf, &nbits_h, &nbits_l); 169 170 mtk_rmw(hw, pf->index, pf->offset, pf->mask << pf->bitpos, 171 (value & pf->mask) << pf->bitpos); 172 173 mtk_rmw(hw, pf->index, pf->offset + pf->next, BIT(nbits_h) - 1, 174 (value & pf->mask) >> nbits_l); 175 } 176 177 static void mtk_hw_read_cross_field(struct mtk_pinctrl *hw, 178 struct mtk_pin_field *pf, int *value) 179 { 180 int nbits_l, nbits_h, h, l; 181 182 mtk_hw_bits_part(pf, &nbits_h, &nbits_l); 183 184 l = (mtk_r32(hw, pf->index, pf->offset) 185 >> pf->bitpos) & (BIT(nbits_l) - 1); 186 h = (mtk_r32(hw, pf->index, pf->offset + pf->next)) 187 & (BIT(nbits_h) - 1); 188 189 *value = (h << nbits_l) | l; 190 } 191 192 int mtk_hw_set_value(struct mtk_pinctrl *hw, const struct mtk_pin_desc *desc, 193 int field, int value) 194 { 195 struct mtk_pin_field pf; 196 int err; 197 198 err = mtk_hw_pin_field_get(hw, desc, field, &pf); 199 if (err) 200 return err; 201 202 if (value < 0 || value > pf.mask) 203 return -EINVAL; 204 205 if (!pf.next) 206 mtk_rmw(hw, pf.index, pf.offset, pf.mask << pf.bitpos, 207 (value & pf.mask) << pf.bitpos); 208 else 209 mtk_hw_write_cross_field(hw, &pf, value); 210 211 return 0; 212 } 213 EXPORT_SYMBOL_GPL(mtk_hw_set_value); 214 215 int mtk_hw_get_value(struct mtk_pinctrl *hw, const struct mtk_pin_desc *desc, 216 int field, int *value) 217 { 218 struct mtk_pin_field pf; 219 int err; 220 221 err = mtk_hw_pin_field_get(hw, desc, field, &pf); 222 if (err) 223 return err; 224 225 if (!pf.next) 226 *value = (mtk_r32(hw, pf.index, pf.offset) 227 >> pf.bitpos) & pf.mask; 228 else 229 mtk_hw_read_cross_field(hw, &pf, value); 230 231 return 0; 232 } 233 EXPORT_SYMBOL_GPL(mtk_hw_get_value); 234 235 static int mtk_xt_find_eint_num(struct mtk_pinctrl *hw, unsigned long eint_n) 236 { 237 const struct mtk_pin_desc *desc; 238 int i = 0; 239 240 desc = (const struct mtk_pin_desc *)hw->soc->pins; 241 242 while (i < hw->soc->npins) { 243 if (desc[i].eint.eint_n == eint_n) 244 return desc[i].number; 245 i++; 246 } 247 248 return EINT_NA; 249 } 250 251 /* 252 * Virtual GPIO only used inside SOC and not being exported to outside SOC. 253 * Some modules use virtual GPIO as eint (e.g. pmif or usb). 254 * In MTK platform, external interrupt (EINT) and GPIO is 1-1 mapping 255 * and we can set GPIO as eint. 256 * But some modules use specific eint which doesn't have real GPIO pin. 257 * So we use virtual GPIO to map it. 258 */ 259 260 bool mtk_is_virt_gpio(struct mtk_pinctrl *hw, unsigned int gpio_n) 261 { 262 const struct mtk_pin_desc *desc; 263 bool virt_gpio = false; 264 265 desc = (const struct mtk_pin_desc *)&hw->soc->pins[gpio_n]; 266 267 /* if the GPIO is not supported for eint mode */ 268 if (desc->eint.eint_m == NO_EINT_SUPPORT) 269 return virt_gpio; 270 271 if (desc->funcs && !desc->funcs[desc->eint.eint_m].name) 272 virt_gpio = true; 273 274 return virt_gpio; 275 } 276 EXPORT_SYMBOL_GPL(mtk_is_virt_gpio); 277 278 static int mtk_xt_get_gpio_n(void *data, unsigned long eint_n, 279 unsigned int *gpio_n, 280 struct gpio_chip **gpio_chip) 281 { 282 struct mtk_pinctrl *hw = (struct mtk_pinctrl *)data; 283 const struct mtk_pin_desc *desc; 284 285 desc = (const struct mtk_pin_desc *)hw->soc->pins; 286 *gpio_chip = &hw->chip; 287 288 /* 289 * Be greedy to guess first gpio_n is equal to eint_n. 290 * Only eint virtual eint number is greater than gpio number. 291 */ 292 if (hw->soc->npins > eint_n && 293 desc[eint_n].eint.eint_n == eint_n) 294 *gpio_n = eint_n; 295 else 296 *gpio_n = mtk_xt_find_eint_num(hw, eint_n); 297 298 return *gpio_n == EINT_NA ? -EINVAL : 0; 299 } 300 301 static int mtk_xt_get_gpio_state(void *data, unsigned long eint_n) 302 { 303 struct mtk_pinctrl *hw = (struct mtk_pinctrl *)data; 304 const struct mtk_pin_desc *desc; 305 struct gpio_chip *gpio_chip; 306 unsigned int gpio_n; 307 int value, err; 308 309 err = mtk_xt_get_gpio_n(hw, eint_n, &gpio_n, &gpio_chip); 310 if (err) 311 return err; 312 313 desc = (const struct mtk_pin_desc *)&hw->soc->pins[gpio_n]; 314 315 err = mtk_hw_get_value(hw, desc, PINCTRL_PIN_REG_DI, &value); 316 if (err) 317 return err; 318 319 return !!value; 320 } 321 322 static int mtk_xt_set_gpio_as_eint(void *data, unsigned long eint_n) 323 { 324 struct mtk_pinctrl *hw = (struct mtk_pinctrl *)data; 325 const struct mtk_pin_desc *desc; 326 struct gpio_chip *gpio_chip; 327 unsigned int gpio_n; 328 int err; 329 330 err = mtk_xt_get_gpio_n(hw, eint_n, &gpio_n, &gpio_chip); 331 if (err) 332 return err; 333 334 if (mtk_is_virt_gpio(hw, gpio_n)) 335 return 0; 336 337 desc = (const struct mtk_pin_desc *)&hw->soc->pins[gpio_n]; 338 339 err = mtk_hw_set_value(hw, desc, PINCTRL_PIN_REG_MODE, 340 desc->eint.eint_m); 341 if (err) 342 return err; 343 344 err = mtk_hw_set_value(hw, desc, PINCTRL_PIN_REG_DIR, MTK_INPUT); 345 if (err) 346 return err; 347 348 err = mtk_hw_set_value(hw, desc, PINCTRL_PIN_REG_SMT, MTK_ENABLE); 349 /* SMT is supposed to be supported by every real GPIO and doesn't 350 * support virtual GPIOs, so the extra condition err != -ENOTSUPP 351 * is just for adding EINT support to these virtual GPIOs. It should 352 * add an extra flag in the pin descriptor when more pins with 353 * distinctive characteristic come out. 354 */ 355 if (err && err != -ENOTSUPP) 356 return err; 357 358 return 0; 359 } 360 361 static const struct mtk_eint_xt mtk_eint_xt = { 362 .get_gpio_n = mtk_xt_get_gpio_n, 363 .get_gpio_state = mtk_xt_get_gpio_state, 364 .set_gpio_as_eint = mtk_xt_set_gpio_as_eint, 365 }; 366 367 int mtk_build_eint(struct mtk_pinctrl *hw, struct platform_device *pdev) 368 { 369 struct device_node *np = pdev->dev.of_node; 370 int ret; 371 372 if (!IS_ENABLED(CONFIG_EINT_MTK)) 373 return 0; 374 375 if (!of_property_read_bool(np, "interrupt-controller")) 376 return -ENODEV; 377 378 hw->eint = devm_kzalloc(hw->dev, sizeof(*hw->eint), GFP_KERNEL); 379 if (!hw->eint) 380 return -ENOMEM; 381 382 hw->eint->base = devm_platform_ioremap_resource_byname(pdev, "eint"); 383 if (IS_ERR(hw->eint->base)) { 384 ret = PTR_ERR(hw->eint->base); 385 goto err_free_eint; 386 } 387 388 hw->eint->irq = irq_of_parse_and_map(np, 0); 389 if (!hw->eint->irq) { 390 ret = -EINVAL; 391 goto err_free_eint; 392 } 393 394 if (!hw->soc->eint_hw) { 395 ret = -ENODEV; 396 goto err_free_eint; 397 } 398 399 hw->eint->dev = &pdev->dev; 400 hw->eint->hw = hw->soc->eint_hw; 401 hw->eint->pctl = hw; 402 hw->eint->gpio_xlate = &mtk_eint_xt; 403 404 return mtk_eint_do_init(hw->eint); 405 406 err_free_eint: 407 devm_kfree(hw->dev, hw->eint); 408 hw->eint = NULL; 409 return ret; 410 } 411 EXPORT_SYMBOL_GPL(mtk_build_eint); 412 413 /* Revision 0 */ 414 int mtk_pinconf_bias_disable_set(struct mtk_pinctrl *hw, 415 const struct mtk_pin_desc *desc) 416 { 417 int err; 418 419 err = mtk_hw_set_value(hw, desc, PINCTRL_PIN_REG_PU, 420 MTK_DISABLE); 421 if (err) 422 return err; 423 424 err = mtk_hw_set_value(hw, desc, PINCTRL_PIN_REG_PD, 425 MTK_DISABLE); 426 if (err) 427 return err; 428 429 return 0; 430 } 431 EXPORT_SYMBOL_GPL(mtk_pinconf_bias_disable_set); 432 433 int mtk_pinconf_bias_disable_get(struct mtk_pinctrl *hw, 434 const struct mtk_pin_desc *desc, int *res) 435 { 436 int v, v2; 437 int err; 438 439 err = mtk_hw_get_value(hw, desc, PINCTRL_PIN_REG_PU, &v); 440 if (err) 441 return err; 442 443 err = mtk_hw_get_value(hw, desc, PINCTRL_PIN_REG_PD, &v2); 444 if (err) 445 return err; 446 447 if (v == MTK_ENABLE || v2 == MTK_ENABLE) 448 return -EINVAL; 449 450 *res = 1; 451 452 return 0; 453 } 454 EXPORT_SYMBOL_GPL(mtk_pinconf_bias_disable_get); 455 456 int mtk_pinconf_bias_set(struct mtk_pinctrl *hw, 457 const struct mtk_pin_desc *desc, bool pullup) 458 { 459 int err, arg; 460 461 arg = pullup ? 1 : 2; 462 463 err = mtk_hw_set_value(hw, desc, PINCTRL_PIN_REG_PU, arg & 1); 464 if (err) 465 return err; 466 467 err = mtk_hw_set_value(hw, desc, PINCTRL_PIN_REG_PD, 468 !!(arg & 2)); 469 if (err) 470 return err; 471 472 return 0; 473 } 474 EXPORT_SYMBOL_GPL(mtk_pinconf_bias_set); 475 476 int mtk_pinconf_bias_get(struct mtk_pinctrl *hw, 477 const struct mtk_pin_desc *desc, bool pullup, int *res) 478 { 479 int reg, err, v; 480 481 reg = pullup ? PINCTRL_PIN_REG_PU : PINCTRL_PIN_REG_PD; 482 483 err = mtk_hw_get_value(hw, desc, reg, &v); 484 if (err) 485 return err; 486 487 if (!v) 488 return -EINVAL; 489 490 *res = 1; 491 492 return 0; 493 } 494 EXPORT_SYMBOL_GPL(mtk_pinconf_bias_get); 495 496 /* Revision 1 */ 497 int mtk_pinconf_bias_disable_set_rev1(struct mtk_pinctrl *hw, 498 const struct mtk_pin_desc *desc) 499 { 500 return mtk_hw_set_value(hw, desc, PINCTRL_PIN_REG_PULLEN, 501 MTK_DISABLE); 502 } 503 EXPORT_SYMBOL_GPL(mtk_pinconf_bias_disable_set_rev1); 504 505 int mtk_pinconf_bias_disable_get_rev1(struct mtk_pinctrl *hw, 506 const struct mtk_pin_desc *desc, int *res) 507 { 508 int v, err; 509 510 err = mtk_hw_get_value(hw, desc, PINCTRL_PIN_REG_PULLEN, &v); 511 if (err) 512 return err; 513 514 if (v == MTK_ENABLE) 515 return -EINVAL; 516 517 *res = 1; 518 519 return 0; 520 } 521 EXPORT_SYMBOL_GPL(mtk_pinconf_bias_disable_get_rev1); 522 523 int mtk_pinconf_bias_set_rev1(struct mtk_pinctrl *hw, 524 const struct mtk_pin_desc *desc, bool pullup) 525 { 526 int err, arg; 527 528 arg = pullup ? MTK_PULLUP : MTK_PULLDOWN; 529 530 err = mtk_hw_set_value(hw, desc, PINCTRL_PIN_REG_PULLEN, 531 MTK_ENABLE); 532 if (err) 533 return err; 534 535 err = mtk_hw_set_value(hw, desc, PINCTRL_PIN_REG_PULLSEL, arg); 536 if (err) 537 return err; 538 539 return 0; 540 } 541 EXPORT_SYMBOL_GPL(mtk_pinconf_bias_set_rev1); 542 543 int mtk_pinconf_bias_get_rev1(struct mtk_pinctrl *hw, 544 const struct mtk_pin_desc *desc, bool pullup, 545 int *res) 546 { 547 int err, v; 548 549 err = mtk_hw_get_value(hw, desc, PINCTRL_PIN_REG_PULLEN, &v); 550 if (err) 551 return err; 552 553 if (v == MTK_DISABLE) 554 return -EINVAL; 555 556 err = mtk_hw_get_value(hw, desc, PINCTRL_PIN_REG_PULLSEL, &v); 557 if (err) 558 return err; 559 560 if (pullup ^ (v == MTK_PULLUP)) 561 return -EINVAL; 562 563 *res = 1; 564 565 return 0; 566 } 567 EXPORT_SYMBOL_GPL(mtk_pinconf_bias_get_rev1); 568 569 /* Combo for the following pull register type: 570 * 1. PU + PD 571 * 2. PULLSEL + PULLEN 572 * 3. PUPD + R0 + R1 573 */ 574 static int mtk_pinconf_bias_set_pu_pd(struct mtk_pinctrl *hw, 575 const struct mtk_pin_desc *desc, 576 u32 pullup, u32 arg) 577 { 578 int err, pu, pd; 579 580 if (arg == MTK_DISABLE) { 581 pu = 0; 582 pd = 0; 583 } else if ((arg == MTK_ENABLE) && pullup) { 584 pu = 1; 585 pd = 0; 586 } else if ((arg == MTK_ENABLE) && !pullup) { 587 pu = 0; 588 pd = 1; 589 } else { 590 err = -EINVAL; 591 goto out; 592 } 593 594 err = mtk_hw_set_value(hw, desc, PINCTRL_PIN_REG_PU, pu); 595 if (err) 596 goto out; 597 598 err = mtk_hw_set_value(hw, desc, PINCTRL_PIN_REG_PD, pd); 599 600 out: 601 return err; 602 } 603 604 static int mtk_pinconf_bias_set_pullsel_pullen(struct mtk_pinctrl *hw, 605 const struct mtk_pin_desc *desc, 606 u32 pullup, u32 arg) 607 { 608 int err, enable; 609 610 if (arg == MTK_DISABLE) 611 enable = 0; 612 else if (arg == MTK_ENABLE) 613 enable = 1; 614 else { 615 err = -EINVAL; 616 goto out; 617 } 618 619 err = mtk_hw_set_value(hw, desc, PINCTRL_PIN_REG_PULLEN, enable); 620 if (err) 621 goto out; 622 623 err = mtk_hw_set_value(hw, desc, PINCTRL_PIN_REG_PULLSEL, pullup); 624 625 out: 626 return err; 627 } 628 629 static int mtk_pinconf_bias_set_pupd_r1_r0(struct mtk_pinctrl *hw, 630 const struct mtk_pin_desc *desc, 631 u32 pullup, u32 arg) 632 { 633 int err, r0, r1; 634 635 if ((arg == MTK_DISABLE) || (arg == MTK_PUPD_SET_R1R0_00)) { 636 pullup = 0; 637 r0 = 0; 638 r1 = 0; 639 } else if (arg == MTK_PUPD_SET_R1R0_01) { 640 r0 = 1; 641 r1 = 0; 642 } else if (arg == MTK_PUPD_SET_R1R0_10) { 643 r0 = 0; 644 r1 = 1; 645 } else if (arg == MTK_PUPD_SET_R1R0_11) { 646 r0 = 1; 647 r1 = 1; 648 } else { 649 err = -EINVAL; 650 goto out; 651 } 652 653 /* MTK HW PUPD bit: 1 for pull-down, 0 for pull-up */ 654 err = mtk_hw_set_value(hw, desc, PINCTRL_PIN_REG_PUPD, !pullup); 655 if (err) 656 goto out; 657 658 err = mtk_hw_set_value(hw, desc, PINCTRL_PIN_REG_R0, r0); 659 if (err) 660 goto out; 661 662 err = mtk_hw_set_value(hw, desc, PINCTRL_PIN_REG_R1, r1); 663 664 out: 665 return err; 666 } 667 668 static int mtk_hw_pin_rsel_lookup(struct mtk_pinctrl *hw, 669 const struct mtk_pin_desc *desc, 670 u32 pullup, u32 arg, u32 *rsel_val) 671 { 672 const struct mtk_pin_rsel *rsel; 673 int check; 674 bool found = false; 675 676 rsel = hw->soc->pin_rsel; 677 678 for (check = 0; check <= hw->soc->npin_rsel - 1; check++) { 679 if (desc->number >= rsel[check].s_pin && 680 desc->number <= rsel[check].e_pin) { 681 if (pullup) { 682 if (rsel[check].up_rsel == arg) { 683 found = true; 684 *rsel_val = rsel[check].rsel_index; 685 break; 686 } 687 } else { 688 if (rsel[check].down_rsel == arg) { 689 found = true; 690 *rsel_val = rsel[check].rsel_index; 691 break; 692 } 693 } 694 } 695 } 696 697 if (!found) { 698 dev_err(hw->dev, "Not support rsel value %d Ohm for pin = %d (%s)\n", 699 arg, desc->number, desc->name); 700 return -ENOTSUPP; 701 } 702 703 return 0; 704 } 705 706 static int mtk_pinconf_bias_set_rsel(struct mtk_pinctrl *hw, 707 const struct mtk_pin_desc *desc, 708 u32 pullup, u32 arg) 709 { 710 int err, rsel_val; 711 712 if (hw->rsel_si_unit) { 713 /* find pin rsel_index from pin_rsel array*/ 714 err = mtk_hw_pin_rsel_lookup(hw, desc, pullup, arg, &rsel_val); 715 if (err) 716 return err; 717 } else { 718 if (arg < MTK_PULL_SET_RSEL_000 || arg > MTK_PULL_SET_RSEL_111) 719 return -EINVAL; 720 721 rsel_val = arg - MTK_PULL_SET_RSEL_000; 722 } 723 724 return mtk_hw_set_value(hw, desc, PINCTRL_PIN_REG_RSEL, rsel_val); 725 } 726 727 static int mtk_pinconf_bias_set_pu_pd_rsel(struct mtk_pinctrl *hw, 728 const struct mtk_pin_desc *desc, 729 u32 pullup, u32 arg) 730 { 731 u32 enable = arg == MTK_DISABLE ? MTK_DISABLE : MTK_ENABLE; 732 int err; 733 734 if (arg != MTK_DISABLE) { 735 err = mtk_pinconf_bias_set_rsel(hw, desc, pullup, arg); 736 if (err) 737 return err; 738 } 739 740 return mtk_pinconf_bias_set_pu_pd(hw, desc, pullup, enable); 741 } 742 743 int mtk_pinconf_bias_set_combo(struct mtk_pinctrl *hw, 744 const struct mtk_pin_desc *desc, 745 u32 pullup, u32 arg) 746 { 747 int err = -ENOTSUPP; 748 u32 try_all_type; 749 750 if (hw->soc->pull_type) 751 try_all_type = hw->soc->pull_type[desc->number]; 752 else 753 try_all_type = MTK_PULL_TYPE_MASK; 754 755 if (try_all_type & MTK_PULL_RSEL_TYPE) { 756 err = mtk_pinconf_bias_set_pu_pd_rsel(hw, desc, pullup, arg); 757 if (!err) 758 return 0; 759 } 760 761 if (try_all_type & MTK_PULL_PU_PD_TYPE) { 762 err = mtk_pinconf_bias_set_pu_pd(hw, desc, pullup, arg); 763 if (!err) 764 return 0; 765 } 766 767 if (try_all_type & MTK_PULL_PULLSEL_TYPE) { 768 err = mtk_pinconf_bias_set_pullsel_pullen(hw, desc, 769 pullup, arg); 770 if (!err) 771 return 0; 772 } 773 774 if (try_all_type & MTK_PULL_PUPD_R1R0_TYPE) 775 err = mtk_pinconf_bias_set_pupd_r1_r0(hw, desc, pullup, arg); 776 777 if (err) 778 dev_err(hw->dev, "Invalid pull argument\n"); 779 780 return err; 781 } 782 EXPORT_SYMBOL_GPL(mtk_pinconf_bias_set_combo); 783 784 static int mtk_rsel_get_si_unit(struct mtk_pinctrl *hw, 785 const struct mtk_pin_desc *desc, 786 u32 pullup, u32 rsel_val, u32 *si_unit) 787 { 788 const struct mtk_pin_rsel *rsel; 789 int check; 790 791 rsel = hw->soc->pin_rsel; 792 793 for (check = 0; check <= hw->soc->npin_rsel - 1; check++) { 794 if (desc->number >= rsel[check].s_pin && 795 desc->number <= rsel[check].e_pin) { 796 if (rsel_val == rsel[check].rsel_index) { 797 if (pullup) 798 *si_unit = rsel[check].up_rsel; 799 else 800 *si_unit = rsel[check].down_rsel; 801 break; 802 } 803 } 804 } 805 806 return 0; 807 } 808 809 static int mtk_pinconf_bias_get_pu_pd_rsel(struct mtk_pinctrl *hw, 810 const struct mtk_pin_desc *desc, 811 u32 *pullup, u32 *enable) 812 { 813 int pu, pd, rsel, err; 814 815 err = mtk_hw_get_value(hw, desc, PINCTRL_PIN_REG_RSEL, &rsel); 816 if (err) 817 goto out; 818 819 err = mtk_hw_get_value(hw, desc, PINCTRL_PIN_REG_PU, &pu); 820 if (err) 821 goto out; 822 823 err = mtk_hw_get_value(hw, desc, PINCTRL_PIN_REG_PD, &pd); 824 if (err) 825 goto out; 826 827 if (pu == 0 && pd == 0) { 828 *pullup = 0; 829 *enable = MTK_DISABLE; 830 } else if (pu == 1 && pd == 0) { 831 *pullup = 1; 832 if (hw->rsel_si_unit) 833 mtk_rsel_get_si_unit(hw, desc, *pullup, rsel, enable); 834 else 835 *enable = rsel + MTK_PULL_SET_RSEL_000; 836 } else if (pu == 0 && pd == 1) { 837 *pullup = 0; 838 if (hw->rsel_si_unit) 839 mtk_rsel_get_si_unit(hw, desc, *pullup, rsel, enable); 840 else 841 *enable = rsel + MTK_PULL_SET_RSEL_000; 842 } else { 843 err = -EINVAL; 844 goto out; 845 } 846 847 out: 848 return err; 849 } 850 851 static int mtk_pinconf_bias_get_pu_pd(struct mtk_pinctrl *hw, 852 const struct mtk_pin_desc *desc, 853 u32 *pullup, u32 *enable) 854 { 855 int err, pu, pd; 856 857 err = mtk_hw_get_value(hw, desc, PINCTRL_PIN_REG_PU, &pu); 858 if (err) 859 goto out; 860 861 err = mtk_hw_get_value(hw, desc, PINCTRL_PIN_REG_PD, &pd); 862 if (err) 863 goto out; 864 865 if (pu == 0 && pd == 0) { 866 *pullup = 0; 867 *enable = MTK_DISABLE; 868 } else if (pu == 1 && pd == 0) { 869 *pullup = 1; 870 *enable = MTK_ENABLE; 871 } else if (pu == 0 && pd == 1) { 872 *pullup = 0; 873 *enable = MTK_ENABLE; 874 } else 875 err = -EINVAL; 876 877 out: 878 return err; 879 } 880 881 static int mtk_pinconf_bias_get_pullsel_pullen(struct mtk_pinctrl *hw, 882 const struct mtk_pin_desc *desc, 883 u32 *pullup, u32 *enable) 884 { 885 int err; 886 887 err = mtk_hw_get_value(hw, desc, PINCTRL_PIN_REG_PULLSEL, pullup); 888 if (err) 889 goto out; 890 891 err = mtk_hw_get_value(hw, desc, PINCTRL_PIN_REG_PULLEN, enable); 892 893 out: 894 return err; 895 } 896 897 static int mtk_pinconf_bias_get_pupd_r1_r0(struct mtk_pinctrl *hw, 898 const struct mtk_pin_desc *desc, 899 u32 *pullup, u32 *enable) 900 { 901 int err, r0, r1; 902 903 err = mtk_hw_get_value(hw, desc, PINCTRL_PIN_REG_PUPD, pullup); 904 if (err) 905 goto out; 906 /* MTK HW PUPD bit: 1 for pull-down, 0 for pull-up */ 907 *pullup = !(*pullup); 908 909 err = mtk_hw_get_value(hw, desc, PINCTRL_PIN_REG_R0, &r0); 910 if (err) 911 goto out; 912 913 err = mtk_hw_get_value(hw, desc, PINCTRL_PIN_REG_R1, &r1); 914 if (err) 915 goto out; 916 917 if ((r1 == 0) && (r0 == 0)) 918 *enable = MTK_PUPD_SET_R1R0_00; 919 else if ((r1 == 0) && (r0 == 1)) 920 *enable = MTK_PUPD_SET_R1R0_01; 921 else if ((r1 == 1) && (r0 == 0)) 922 *enable = MTK_PUPD_SET_R1R0_10; 923 else if ((r1 == 1) && (r0 == 1)) 924 *enable = MTK_PUPD_SET_R1R0_11; 925 else 926 err = -EINVAL; 927 928 out: 929 return err; 930 } 931 932 int mtk_pinconf_bias_get_combo(struct mtk_pinctrl *hw, 933 const struct mtk_pin_desc *desc, 934 u32 *pullup, u32 *enable) 935 { 936 int err = -ENOTSUPP; 937 u32 try_all_type; 938 939 if (hw->soc->pull_type) 940 try_all_type = hw->soc->pull_type[desc->number]; 941 else 942 try_all_type = MTK_PULL_TYPE_MASK; 943 944 if (try_all_type & MTK_PULL_RSEL_TYPE) { 945 err = mtk_pinconf_bias_get_pu_pd_rsel(hw, desc, pullup, enable); 946 if (!err) 947 return 0; 948 } 949 950 if (try_all_type & MTK_PULL_PU_PD_TYPE) { 951 err = mtk_pinconf_bias_get_pu_pd(hw, desc, pullup, enable); 952 if (!err) 953 return 0; 954 } 955 956 if (try_all_type & MTK_PULL_PULLSEL_TYPE) { 957 err = mtk_pinconf_bias_get_pullsel_pullen(hw, desc, 958 pullup, enable); 959 if (!err) 960 return 0; 961 } 962 963 if (try_all_type & MTK_PULL_PUPD_R1R0_TYPE) 964 err = mtk_pinconf_bias_get_pupd_r1_r0(hw, desc, pullup, enable); 965 966 return err; 967 } 968 EXPORT_SYMBOL_GPL(mtk_pinconf_bias_get_combo); 969 970 /* Revision 0 */ 971 int mtk_pinconf_drive_set(struct mtk_pinctrl *hw, 972 const struct mtk_pin_desc *desc, u32 arg) 973 { 974 const struct mtk_drive_desc *tb; 975 int err = -ENOTSUPP; 976 977 tb = &mtk_drive[desc->drv_n]; 978 /* 4mA when (e8, e4) = (0, 0) 979 * 8mA when (e8, e4) = (0, 1) 980 * 12mA when (e8, e4) = (1, 0) 981 * 16mA when (e8, e4) = (1, 1) 982 */ 983 if ((arg >= tb->min && arg <= tb->max) && !(arg % tb->step)) { 984 arg = (arg / tb->step - 1) * tb->scal; 985 err = mtk_hw_set_value(hw, desc, PINCTRL_PIN_REG_E4, 986 arg & 0x1); 987 if (err) 988 return err; 989 990 err = mtk_hw_set_value(hw, desc, PINCTRL_PIN_REG_E8, 991 (arg & 0x2) >> 1); 992 if (err) 993 return err; 994 } 995 996 return err; 997 } 998 EXPORT_SYMBOL_GPL(mtk_pinconf_drive_set); 999 1000 int mtk_pinconf_drive_get(struct mtk_pinctrl *hw, 1001 const struct mtk_pin_desc *desc, int *val) 1002 { 1003 const struct mtk_drive_desc *tb; 1004 int err, val1, val2; 1005 1006 tb = &mtk_drive[desc->drv_n]; 1007 1008 err = mtk_hw_get_value(hw, desc, PINCTRL_PIN_REG_E4, &val1); 1009 if (err) 1010 return err; 1011 1012 err = mtk_hw_get_value(hw, desc, PINCTRL_PIN_REG_E8, &val2); 1013 if (err) 1014 return err; 1015 1016 /* 4mA when (e8, e4) = (0, 0); 8mA when (e8, e4) = (0, 1) 1017 * 12mA when (e8, e4) = (1, 0); 16mA when (e8, e4) = (1, 1) 1018 */ 1019 *val = (((val2 << 1) + val1) / tb->scal + 1) * tb->step; 1020 1021 return 0; 1022 } 1023 EXPORT_SYMBOL_GPL(mtk_pinconf_drive_get); 1024 1025 /* Revision 1 */ 1026 int mtk_pinconf_drive_set_rev1(struct mtk_pinctrl *hw, 1027 const struct mtk_pin_desc *desc, u32 arg) 1028 { 1029 const struct mtk_drive_desc *tb; 1030 int err = -ENOTSUPP; 1031 1032 tb = &mtk_drive[desc->drv_n]; 1033 1034 if ((arg >= tb->min && arg <= tb->max) && !(arg % tb->step)) { 1035 arg = (arg / tb->step - 1) * tb->scal; 1036 1037 err = mtk_hw_set_value(hw, desc, PINCTRL_PIN_REG_DRV, 1038 arg); 1039 if (err) 1040 return err; 1041 } 1042 1043 return err; 1044 } 1045 EXPORT_SYMBOL_GPL(mtk_pinconf_drive_set_rev1); 1046 1047 int mtk_pinconf_drive_get_rev1(struct mtk_pinctrl *hw, 1048 const struct mtk_pin_desc *desc, int *val) 1049 { 1050 const struct mtk_drive_desc *tb; 1051 int err, val1; 1052 1053 tb = &mtk_drive[desc->drv_n]; 1054 1055 err = mtk_hw_get_value(hw, desc, PINCTRL_PIN_REG_DRV, &val1); 1056 if (err) 1057 return err; 1058 1059 *val = ((val1 & 0x7) / tb->scal + 1) * tb->step; 1060 1061 return 0; 1062 } 1063 EXPORT_SYMBOL_GPL(mtk_pinconf_drive_get_rev1); 1064 1065 int mtk_pinconf_drive_set_raw(struct mtk_pinctrl *hw, 1066 const struct mtk_pin_desc *desc, u32 arg) 1067 { 1068 return mtk_hw_set_value(hw, desc, PINCTRL_PIN_REG_DRV, arg); 1069 } 1070 EXPORT_SYMBOL_GPL(mtk_pinconf_drive_set_raw); 1071 1072 int mtk_pinconf_drive_get_raw(struct mtk_pinctrl *hw, 1073 const struct mtk_pin_desc *desc, int *val) 1074 { 1075 return mtk_hw_get_value(hw, desc, PINCTRL_PIN_REG_DRV, val); 1076 } 1077 EXPORT_SYMBOL_GPL(mtk_pinconf_drive_get_raw); 1078 1079 int mtk_pinconf_adv_pull_set(struct mtk_pinctrl *hw, 1080 const struct mtk_pin_desc *desc, bool pullup, 1081 u32 arg) 1082 { 1083 int err; 1084 1085 /* 10K off & 50K (75K) off, when (R0, R1) = (0, 0); 1086 * 10K off & 50K (75K) on, when (R0, R1) = (0, 1); 1087 * 10K on & 50K (75K) off, when (R0, R1) = (1, 0); 1088 * 10K on & 50K (75K) on, when (R0, R1) = (1, 1) 1089 */ 1090 err = mtk_hw_set_value(hw, desc, PINCTRL_PIN_REG_R0, arg & 1); 1091 if (err) 1092 return 0; 1093 1094 err = mtk_hw_set_value(hw, desc, PINCTRL_PIN_REG_R1, 1095 !!(arg & 2)); 1096 if (err) 1097 return 0; 1098 1099 arg = pullup ? 0 : 1; 1100 1101 err = mtk_hw_set_value(hw, desc, PINCTRL_PIN_REG_PUPD, arg); 1102 1103 /* If PUPD register is not supported for that pin, let's fallback to 1104 * general bias control. 1105 */ 1106 if (err == -ENOTSUPP) { 1107 if (hw->soc->bias_set) { 1108 err = hw->soc->bias_set(hw, desc, pullup); 1109 if (err) 1110 return err; 1111 } else { 1112 err = mtk_pinconf_bias_set_rev1(hw, desc, pullup); 1113 if (err) 1114 err = mtk_pinconf_bias_set(hw, desc, pullup); 1115 } 1116 } 1117 1118 return err; 1119 } 1120 EXPORT_SYMBOL_GPL(mtk_pinconf_adv_pull_set); 1121 1122 int mtk_pinconf_adv_pull_get(struct mtk_pinctrl *hw, 1123 const struct mtk_pin_desc *desc, bool pullup, 1124 u32 *val) 1125 { 1126 u32 t, t2; 1127 int err; 1128 1129 err = mtk_hw_get_value(hw, desc, PINCTRL_PIN_REG_PUPD, &t); 1130 1131 /* If PUPD register is not supported for that pin, let's fallback to 1132 * general bias control. 1133 */ 1134 if (err == -ENOTSUPP) { 1135 if (hw->soc->bias_get) { 1136 err = hw->soc->bias_get(hw, desc, pullup, val); 1137 if (err) 1138 return err; 1139 } else { 1140 return -ENOTSUPP; 1141 } 1142 } else { 1143 /* t == 0 supposes PULLUP for the customized PULL setup */ 1144 if (err) 1145 return err; 1146 1147 if (pullup ^ !t) 1148 return -EINVAL; 1149 } 1150 1151 err = mtk_hw_get_value(hw, desc, PINCTRL_PIN_REG_R0, &t); 1152 if (err) 1153 return err; 1154 1155 err = mtk_hw_get_value(hw, desc, PINCTRL_PIN_REG_R1, &t2); 1156 if (err) 1157 return err; 1158 1159 *val = (t | t2 << 1) & 0x7; 1160 1161 return 0; 1162 } 1163 EXPORT_SYMBOL_GPL(mtk_pinconf_adv_pull_get); 1164 1165 int mtk_pinconf_adv_drive_set(struct mtk_pinctrl *hw, 1166 const struct mtk_pin_desc *desc, u32 arg) 1167 { 1168 int err; 1169 int en = arg & 1; 1170 int e0 = !!(arg & 2); 1171 int e1 = !!(arg & 4); 1172 1173 err = mtk_hw_set_value(hw, desc, PINCTRL_PIN_REG_DRV_EN, en); 1174 if (err) 1175 return err; 1176 1177 if (!en) 1178 return err; 1179 1180 err = mtk_hw_set_value(hw, desc, PINCTRL_PIN_REG_DRV_E0, e0); 1181 if (err) 1182 return err; 1183 1184 err = mtk_hw_set_value(hw, desc, PINCTRL_PIN_REG_DRV_E1, e1); 1185 if (err) 1186 return err; 1187 1188 return err; 1189 } 1190 EXPORT_SYMBOL_GPL(mtk_pinconf_adv_drive_set); 1191 1192 int mtk_pinconf_adv_drive_get(struct mtk_pinctrl *hw, 1193 const struct mtk_pin_desc *desc, u32 *val) 1194 { 1195 u32 en, e0, e1; 1196 int err; 1197 1198 err = mtk_hw_get_value(hw, desc, PINCTRL_PIN_REG_DRV_EN, &en); 1199 if (err) 1200 return err; 1201 1202 err = mtk_hw_get_value(hw, desc, PINCTRL_PIN_REG_DRV_E0, &e0); 1203 if (err) 1204 return err; 1205 1206 err = mtk_hw_get_value(hw, desc, PINCTRL_PIN_REG_DRV_E1, &e1); 1207 if (err) 1208 return err; 1209 1210 *val = (en | e0 << 1 | e1 << 2) & 0x7; 1211 1212 return 0; 1213 } 1214 EXPORT_SYMBOL_GPL(mtk_pinconf_adv_drive_get); 1215 1216 int mtk_pinconf_adv_drive_set_raw(struct mtk_pinctrl *hw, 1217 const struct mtk_pin_desc *desc, u32 arg) 1218 { 1219 return mtk_hw_set_value(hw, desc, PINCTRL_PIN_REG_DRV_ADV, arg); 1220 } 1221 EXPORT_SYMBOL_GPL(mtk_pinconf_adv_drive_set_raw); 1222 1223 int mtk_pinconf_adv_drive_get_raw(struct mtk_pinctrl *hw, 1224 const struct mtk_pin_desc *desc, u32 *val) 1225 { 1226 return mtk_hw_get_value(hw, desc, PINCTRL_PIN_REG_DRV_ADV, val); 1227 } 1228 EXPORT_SYMBOL_GPL(mtk_pinconf_adv_drive_get_raw); 1229 1230 MODULE_LICENSE("GPL v2"); 1231 MODULE_AUTHOR("Sean Wang <sean.wang@mediatek.com>"); 1232 MODULE_DESCRIPTION("Pin configuration library module for mediatek SoCs"); 1233