Lines Matching +full:tb10x +full:- +full:gpio
1 // SPDX-License-Identifier: GPL-2.0-only
3 * Abilis Systems TB10x pin control driver
22 #include "pinctrl-utils.h"
37 (((1 << PCFG_PORT_BITWIDTH) - 1) << (PCFG_PORT_BITWIDTH * (PORT)))
442 DEFPINFUNCGRP(gpiob, -1, 0, 1),
443 DEFPINFUNCGRP(gpiod, -1, 0, 1),
444 DEFPINFUNCGRP(gpiof, -1, 0, 1),
445 DEFPINFUNCGRP(gpioh, -1, 0, 1),
446 DEFPINFUNCGRP(gpioi, -1, 0, 1),
458 * struct tb10x_port - state of an I/O port
469 * struct tb10x_pinctrl - TB10x pin controller internal state
477 * @gpios: Indicates if a given pin is currently used as GPIO (1) or not (0).
497 if (state->ports[port].count) in tb10x_pinctrl_set_config()
500 state->ports[port].mode = mode; in tb10x_pinctrl_set_config()
502 pcfg = ioread32(state->base) & ~(PCFG_PORT_MASK(port)); in tb10x_pinctrl_set_config()
504 iowrite32(pcfg, state->base); in tb10x_pinctrl_set_config()
511 return (ioread32(state->base) & PCFG_PORT_MASK(port)) in tb10x_pinctrl_get_config()
518 return state->pinfuncgrpcnt; in tb10x_get_groups_count()
524 return state->pingroups[n].name; in tb10x_get_group_name()
533 *pins = state->pingroups[n].pins; in tb10x_get_group_pins()
534 *num_pins = state->pingroups[n].pincnt; in tb10x_get_group_pins()
550 return -EINVAL; in tb10x_dt_node_to_map()
562 num_maps, string, np_config->name); in tb10x_dt_node_to_map()
579 return state->pinfuncnt; in tb10x_get_functions_count()
586 return state->pinfuncs[n].name; in tb10x_get_function_name()
595 *groups = &state->pinfuncs[n].group; in tb10x_get_function_groups()
606 int muxport = -1; in tb10x_gpio_request_enable()
607 int muxmode = -1; in tb10x_gpio_request_enable()
610 mutex_lock(&state->mutex); in tb10x_gpio_request_enable()
613 * Figure out to which port the requested GPIO belongs and how to in tb10x_gpio_request_enable()
618 for (i = 0; i < state->pinfuncgrpcnt; i++) { in tb10x_gpio_request_enable()
619 const struct tb10x_pinfuncgrp *pfg = &state->pingroups[i]; in tb10x_gpio_request_enable()
620 unsigned int mode = pfg->mode; in tb10x_gpio_request_enable()
621 int j, port = pfg->port; in tb10x_gpio_request_enable()
630 for (j = 0; j < pfg->pincnt; j++) { in tb10x_gpio_request_enable()
631 if (pin == pfg->pins[j]) { in tb10x_gpio_request_enable()
632 if (pfg->isgpio) { in tb10x_gpio_request_enable()
634 * Remember the GPIO-only setting of in tb10x_gpio_request_enable()
639 } else if (state->ports[port].count in tb10x_gpio_request_enable()
640 && (state->ports[port].mode == mode)) { in tb10x_gpio_request_enable()
645 mutex_unlock(&state->mutex); in tb10x_gpio_request_enable()
646 return -EBUSY; in tb10x_gpio_request_enable()
654 * If we haven't returned an error at this point, the GPIO pin is not in tb10x_gpio_request_enable()
655 * used by another function and the GPIO request can be granted: in tb10x_gpio_request_enable()
656 * Register pin as being used as GPIO so we don't allocate it to in tb10x_gpio_request_enable()
659 set_bit(pin, state->gpios); in tb10x_gpio_request_enable()
664 * Right Thing, either configure the port in GPIO only mode or leave in tb10x_gpio_request_enable()
665 * another mode compatible with this GPIO request untouched. in tb10x_gpio_request_enable()
670 mutex_unlock(&state->mutex); in tb10x_gpio_request_enable()
681 mutex_lock(&state->mutex); in tb10x_gpio_disable_free()
683 clear_bit(pin, state->gpios); in tb10x_gpio_disable_free()
685 mutex_unlock(&state->mutex); in tb10x_gpio_disable_free()
692 const struct tb10x_pinfuncgrp *grp = &state->pingroups[group_selector]; in tb10x_pctl_set_mux()
695 if (grp->port < 0) in tb10x_pctl_set_mux()
698 mutex_lock(&state->mutex); in tb10x_pctl_set_mux()
704 if (state->ports[grp->port].count in tb10x_pctl_set_mux()
705 && (state->ports[grp->port].mode != grp->mode)) { in tb10x_pctl_set_mux()
706 mutex_unlock(&state->mutex); in tb10x_pctl_set_mux()
707 return -EBUSY; in tb10x_pctl_set_mux()
714 for (i = 0; i < grp->pincnt; i++) in tb10x_pctl_set_mux()
715 if (test_bit(grp->pins[i], state->gpios)) { in tb10x_pctl_set_mux()
716 mutex_unlock(&state->mutex); in tb10x_pctl_set_mux()
717 return -EBUSY; in tb10x_pctl_set_mux()
720 tb10x_pinctrl_set_config(state, grp->port, grp->mode); in tb10x_pctl_set_mux()
722 state->ports[grp->port].count++; in tb10x_pctl_set_mux()
724 mutex_unlock(&state->mutex); in tb10x_pctl_set_mux()
739 .name = "TB10x",
749 int ret = -EINVAL; in tb10x_pinctrl_probe()
750 struct device *dev = &pdev->dev; in tb10x_pinctrl_probe()
751 struct device_node *of_node = dev->of_node; in tb10x_pinctrl_probe()
758 return -EINVAL; in tb10x_pinctrl_probe()
765 return -ENOMEM; in tb10x_pinctrl_probe()
768 mutex_init(&state->mutex); in tb10x_pinctrl_probe()
770 state->base = devm_platform_ioremap_resource(pdev, 0); in tb10x_pinctrl_probe()
771 if (IS_ERR(state->base)) { in tb10x_pinctrl_probe()
772 ret = PTR_ERR(state->base); in tb10x_pinctrl_probe()
776 state->pingroups = tb10x_pingroups; in tb10x_pinctrl_probe()
777 state->pinfuncgrpcnt = ARRAY_SIZE(tb10x_pingroups); in tb10x_pinctrl_probe()
780 state->ports[i].mode = tb10x_pinctrl_get_config(state, i); in tb10x_pinctrl_probe()
787 state->pinfuncs[state->pinfuncnt].name = child->name; in tb10x_pinctrl_probe()
788 state->pinfuncs[state->pinfuncnt].group = name; in tb10x_pinctrl_probe()
789 state->pinfuncnt++; in tb10x_pinctrl_probe()
793 state->pctl = devm_pinctrl_register(dev, &tb10x_pindesc, state); in tb10x_pinctrl_probe()
794 if (IS_ERR(state->pctl)) { in tb10x_pinctrl_probe()
795 dev_err(dev, "could not register TB10x pin driver\n"); in tb10x_pinctrl_probe()
796 ret = PTR_ERR(state->pctl); in tb10x_pinctrl_probe()
803 mutex_destroy(&state->mutex); in tb10x_pinctrl_probe()
811 mutex_destroy(&state->mutex); in tb10x_pinctrl_remove()
816 { .compatible = "abilis,tb10x-iomux" },
833 MODULE_DESCRIPTION("Abilis Systems TB10x pinctrl driver");