^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1) // SPDX-License-Identifier: GPL-2.0-only
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3) * Pinctrl driver for the Wondermedia SoC's
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5) * Copyright (c) 2013 Tony Prisk <linux@prisktech.co.nz>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 6) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 7)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 8) #include <linux/err.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 9) #include <linux/gpio/driver.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 10) #include <linux/interrupt.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 11) #include <linux/io.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 12) #include <linux/irq.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 13) #include <linux/of.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 14) #include <linux/of_irq.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 15) #include <linux/pinctrl/consumer.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 16) #include <linux/pinctrl/machine.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 17) #include <linux/pinctrl/pinconf.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 18) #include <linux/pinctrl/pinconf-generic.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 19) #include <linux/pinctrl/pinctrl.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 20) #include <linux/pinctrl/pinmux.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 21) #include <linux/platform_device.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 22) #include <linux/slab.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 23)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 24) #include "pinctrl-wmt.h"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 25)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 26) static inline void wmt_setbits(struct wmt_pinctrl_data *data, u32 reg,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 27) u32 mask)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 28) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 29) u32 val;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 30)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 31) val = readl_relaxed(data->base + reg);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 32) val |= mask;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 33) writel_relaxed(val, data->base + reg);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 34) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 35)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 36) static inline void wmt_clearbits(struct wmt_pinctrl_data *data, u32 reg,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 37) u32 mask)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 38) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 39) u32 val;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 40)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 41) val = readl_relaxed(data->base + reg);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 42) val &= ~mask;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 43) writel_relaxed(val, data->base + reg);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 44) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 45)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 46) enum wmt_func_sel {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 47) WMT_FSEL_GPIO_IN = 0,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 48) WMT_FSEL_GPIO_OUT = 1,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 49) WMT_FSEL_ALT = 2,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 50) WMT_FSEL_COUNT = 3,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 51) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 52)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 53) static const char * const wmt_functions[WMT_FSEL_COUNT] = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 54) [WMT_FSEL_GPIO_IN] = "gpio_in",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 55) [WMT_FSEL_GPIO_OUT] = "gpio_out",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 56) [WMT_FSEL_ALT] = "alt",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 57) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 58)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 59) static int wmt_pmx_get_functions_count(struct pinctrl_dev *pctldev)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 60) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 61) return WMT_FSEL_COUNT;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 62) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 63)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 64) static const char *wmt_pmx_get_function_name(struct pinctrl_dev *pctldev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 65) unsigned selector)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 66) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 67) return wmt_functions[selector];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 68) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 69)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 70) static int wmt_pmx_get_function_groups(struct pinctrl_dev *pctldev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 71) unsigned selector,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 72) const char * const **groups,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 73) unsigned * const num_groups)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 74) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 75) struct wmt_pinctrl_data *data = pinctrl_dev_get_drvdata(pctldev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 76)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 77) /* every pin does every function */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 78) *groups = data->groups;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 79) *num_groups = data->ngroups;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 80)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 81) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 82) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 83)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 84) static int wmt_set_pinmux(struct wmt_pinctrl_data *data, unsigned func,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 85) unsigned pin)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 86) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 87) u32 bank = WMT_BANK_FROM_PIN(pin);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 88) u32 bit = WMT_BIT_FROM_PIN(pin);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 89) u32 reg_en = data->banks[bank].reg_en;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 90) u32 reg_dir = data->banks[bank].reg_dir;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 91)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 92) if (reg_dir == NO_REG) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 93) dev_err(data->dev, "pin:%d no direction register defined\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 94) pin);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 95) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 96) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 97)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 98) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 99) * If reg_en == NO_REG, we assume it is a dedicated GPIO and cannot be
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 100) * disabled (as on VT8500) and that no alternate function is available.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 101) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 102) switch (func) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 103) case WMT_FSEL_GPIO_IN:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 104) if (reg_en != NO_REG)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 105) wmt_setbits(data, reg_en, BIT(bit));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 106) wmt_clearbits(data, reg_dir, BIT(bit));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 107) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 108) case WMT_FSEL_GPIO_OUT:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 109) if (reg_en != NO_REG)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 110) wmt_setbits(data, reg_en, BIT(bit));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 111) wmt_setbits(data, reg_dir, BIT(bit));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 112) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 113) case WMT_FSEL_ALT:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 114) if (reg_en == NO_REG) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 115) dev_err(data->dev, "pin:%d no alt function available\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 116) pin);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 117) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 118) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 119) wmt_clearbits(data, reg_en, BIT(bit));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 120) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 121)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 122) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 123) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 124)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 125) static int wmt_pmx_set_mux(struct pinctrl_dev *pctldev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 126) unsigned func_selector,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 127) unsigned group_selector)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 128) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 129) struct wmt_pinctrl_data *data = pinctrl_dev_get_drvdata(pctldev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 130) u32 pinnum = data->pins[group_selector].number;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 131)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 132) return wmt_set_pinmux(data, func_selector, pinnum);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 133) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 134)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 135) static void wmt_pmx_gpio_disable_free(struct pinctrl_dev *pctldev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 136) struct pinctrl_gpio_range *range,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 137) unsigned offset)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 138) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 139) struct wmt_pinctrl_data *data = pinctrl_dev_get_drvdata(pctldev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 140)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 141) /* disable by setting GPIO_IN */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 142) wmt_set_pinmux(data, WMT_FSEL_GPIO_IN, offset);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 143) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 144)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 145) static int wmt_pmx_gpio_set_direction(struct pinctrl_dev *pctldev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 146) struct pinctrl_gpio_range *range,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 147) unsigned offset,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 148) bool input)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 149) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 150) struct wmt_pinctrl_data *data = pinctrl_dev_get_drvdata(pctldev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 151)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 152) wmt_set_pinmux(data, (input ? WMT_FSEL_GPIO_IN : WMT_FSEL_GPIO_OUT),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 153) offset);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 154)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 155) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 156) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 157)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 158) static const struct pinmux_ops wmt_pinmux_ops = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 159) .get_functions_count = wmt_pmx_get_functions_count,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 160) .get_function_name = wmt_pmx_get_function_name,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 161) .get_function_groups = wmt_pmx_get_function_groups,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 162) .set_mux = wmt_pmx_set_mux,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 163) .gpio_disable_free = wmt_pmx_gpio_disable_free,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 164) .gpio_set_direction = wmt_pmx_gpio_set_direction,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 165) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 166)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 167) static int wmt_get_groups_count(struct pinctrl_dev *pctldev)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 168) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 169) struct wmt_pinctrl_data *data = pinctrl_dev_get_drvdata(pctldev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 170)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 171) return data->ngroups;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 172) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 173)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 174) static const char *wmt_get_group_name(struct pinctrl_dev *pctldev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 175) unsigned selector)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 176) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 177) struct wmt_pinctrl_data *data = pinctrl_dev_get_drvdata(pctldev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 178)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 179) return data->groups[selector];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 180) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 181)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 182) static int wmt_get_group_pins(struct pinctrl_dev *pctldev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 183) unsigned selector,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 184) const unsigned **pins,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 185) unsigned *num_pins)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 186) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 187) struct wmt_pinctrl_data *data = pinctrl_dev_get_drvdata(pctldev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 188)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 189) *pins = &data->pins[selector].number;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 190) *num_pins = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 191)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 192) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 193) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 194)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 195) static int wmt_pctl_find_group_by_pin(struct wmt_pinctrl_data *data, u32 pin)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 196) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 197) int i;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 198)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 199) for (i = 0; i < data->npins; i++) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 200) if (data->pins[i].number == pin)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 201) return i;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 202) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 203)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 204) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 205) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 206)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 207) static int wmt_pctl_dt_node_to_map_func(struct wmt_pinctrl_data *data,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 208) struct device_node *np,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 209) u32 pin, u32 fnum,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 210) struct pinctrl_map **maps)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 211) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 212) int group;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 213) struct pinctrl_map *map = *maps;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 214)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 215) if (fnum >= ARRAY_SIZE(wmt_functions)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 216) dev_err(data->dev, "invalid wm,function %d\n", fnum);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 217) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 218) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 219)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 220) group = wmt_pctl_find_group_by_pin(data, pin);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 221) if (group < 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 222) dev_err(data->dev, "unable to match pin %d to group\n", pin);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 223) return group;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 224) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 225)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 226) map->type = PIN_MAP_TYPE_MUX_GROUP;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 227) map->data.mux.group = data->groups[group];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 228) map->data.mux.function = wmt_functions[fnum];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 229) (*maps)++;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 230)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 231) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 232) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 233)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 234) static int wmt_pctl_dt_node_to_map_pull(struct wmt_pinctrl_data *data,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 235) struct device_node *np,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 236) u32 pin, u32 pull,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 237) struct pinctrl_map **maps)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 238) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 239) int group;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 240) unsigned long *configs;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 241) struct pinctrl_map *map = *maps;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 242)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 243) if (pull > 2) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 244) dev_err(data->dev, "invalid wm,pull %d\n", pull);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 245) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 246) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 247)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 248) group = wmt_pctl_find_group_by_pin(data, pin);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 249) if (group < 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 250) dev_err(data->dev, "unable to match pin %d to group\n", pin);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 251) return group;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 252) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 253)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 254) configs = kzalloc(sizeof(*configs), GFP_KERNEL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 255) if (!configs)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 256) return -ENOMEM;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 257)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 258) switch (pull) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 259) case 0:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 260) configs[0] = PIN_CONFIG_BIAS_DISABLE;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 261) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 262) case 1:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 263) configs[0] = PIN_CONFIG_BIAS_PULL_DOWN;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 264) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 265) case 2:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 266) configs[0] = PIN_CONFIG_BIAS_PULL_UP;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 267) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 268) default:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 269) configs[0] = PIN_CONFIG_BIAS_DISABLE;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 270) dev_err(data->dev, "invalid pull state %d - disabling\n", pull);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 271) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 272)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 273) map->type = PIN_MAP_TYPE_CONFIGS_PIN;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 274) map->data.configs.group_or_pin = data->groups[group];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 275) map->data.configs.configs = configs;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 276) map->data.configs.num_configs = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 277) (*maps)++;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 278)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 279) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 280) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 281)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 282) static void wmt_pctl_dt_free_map(struct pinctrl_dev *pctldev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 283) struct pinctrl_map *maps,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 284) unsigned num_maps)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 285) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 286) int i;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 287)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 288) for (i = 0; i < num_maps; i++)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 289) if (maps[i].type == PIN_MAP_TYPE_CONFIGS_PIN)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 290) kfree(maps[i].data.configs.configs);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 291)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 292) kfree(maps);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 293) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 294)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 295) static int wmt_pctl_dt_node_to_map(struct pinctrl_dev *pctldev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 296) struct device_node *np,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 297) struct pinctrl_map **map,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 298) unsigned *num_maps)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 299) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 300) struct pinctrl_map *maps, *cur_map;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 301) struct property *pins, *funcs, *pulls;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 302) u32 pin, func, pull;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 303) int num_pins, num_funcs, num_pulls, maps_per_pin;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 304) int i, err;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 305) struct wmt_pinctrl_data *data = pinctrl_dev_get_drvdata(pctldev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 306)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 307) pins = of_find_property(np, "wm,pins", NULL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 308) if (!pins) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 309) dev_err(data->dev, "missing wmt,pins property\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 310) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 311) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 312)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 313) funcs = of_find_property(np, "wm,function", NULL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 314) pulls = of_find_property(np, "wm,pull", NULL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 315)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 316) if (!funcs && !pulls) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 317) dev_err(data->dev, "neither wm,function nor wm,pull specified\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 318) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 319) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 320)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 321) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 322) * The following lines calculate how many values are defined for each
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 323) * of the properties.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 324) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 325) num_pins = pins->length / sizeof(u32);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 326) num_funcs = funcs ? (funcs->length / sizeof(u32)) : 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 327) num_pulls = pulls ? (pulls->length / sizeof(u32)) : 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 328)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 329) if (num_funcs > 1 && num_funcs != num_pins) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 330) dev_err(data->dev, "wm,function must have 1 or %d entries\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 331) num_pins);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 332) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 333) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 334)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 335) if (num_pulls > 1 && num_pulls != num_pins) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 336) dev_err(data->dev, "wm,pull must have 1 or %d entries\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 337) num_pins);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 338) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 339) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 340)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 341) maps_per_pin = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 342) if (num_funcs)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 343) maps_per_pin++;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 344) if (num_pulls)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 345) maps_per_pin++;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 346)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 347) cur_map = maps = kcalloc(num_pins * maps_per_pin, sizeof(*maps),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 348) GFP_KERNEL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 349) if (!maps)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 350) return -ENOMEM;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 351)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 352) for (i = 0; i < num_pins; i++) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 353) err = of_property_read_u32_index(np, "wm,pins", i, &pin);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 354) if (err)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 355) goto fail;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 356)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 357) if (pin >= (data->nbanks * 32)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 358) dev_err(data->dev, "invalid wm,pins value\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 359) err = -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 360) goto fail;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 361) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 362)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 363) if (num_funcs) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 364) err = of_property_read_u32_index(np, "wm,function",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 365) (num_funcs > 1 ? i : 0), &func);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 366) if (err)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 367) goto fail;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 368)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 369) err = wmt_pctl_dt_node_to_map_func(data, np, pin, func,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 370) &cur_map);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 371) if (err)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 372) goto fail;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 373) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 374)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 375) if (num_pulls) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 376) err = of_property_read_u32_index(np, "wm,pull",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 377) (num_pulls > 1 ? i : 0), &pull);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 378) if (err)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 379) goto fail;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 380)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 381) err = wmt_pctl_dt_node_to_map_pull(data, np, pin, pull,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 382) &cur_map);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 383) if (err)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 384) goto fail;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 385) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 386) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 387) *map = maps;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 388) *num_maps = num_pins * maps_per_pin;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 389) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 390)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 391) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 392) * The fail path removes any maps that have been allocated. The fail path is
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 393) * only called from code after maps has been kzalloc'd. It is also safe to
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 394) * pass 'num_pins * maps_per_pin' as the map count even though we probably
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 395) * failed before all the mappings were read as all maps are allocated at once,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 396) * and configs are only allocated for .type = PIN_MAP_TYPE_CONFIGS_PIN - there
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 397) * is no failpath where a config can be allocated without .type being set.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 398) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 399) fail:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 400) wmt_pctl_dt_free_map(pctldev, maps, num_pins * maps_per_pin);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 401) return err;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 402) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 403)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 404) static const struct pinctrl_ops wmt_pctl_ops = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 405) .get_groups_count = wmt_get_groups_count,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 406) .get_group_name = wmt_get_group_name,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 407) .get_group_pins = wmt_get_group_pins,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 408) .dt_node_to_map = wmt_pctl_dt_node_to_map,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 409) .dt_free_map = wmt_pctl_dt_free_map,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 410) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 411)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 412) static int wmt_pinconf_get(struct pinctrl_dev *pctldev, unsigned pin,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 413) unsigned long *config)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 414) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 415) return -ENOTSUPP;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 416) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 417)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 418) static int wmt_pinconf_set(struct pinctrl_dev *pctldev, unsigned pin,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 419) unsigned long *configs, unsigned num_configs)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 420) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 421) struct wmt_pinctrl_data *data = pinctrl_dev_get_drvdata(pctldev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 422) enum pin_config_param param;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 423) u32 arg;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 424) u32 bank = WMT_BANK_FROM_PIN(pin);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 425) u32 bit = WMT_BIT_FROM_PIN(pin);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 426) u32 reg_pull_en = data->banks[bank].reg_pull_en;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 427) u32 reg_pull_cfg = data->banks[bank].reg_pull_cfg;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 428) int i;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 429)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 430) if ((reg_pull_en == NO_REG) || (reg_pull_cfg == NO_REG)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 431) dev_err(data->dev, "bias functions not supported on pin %d\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 432) pin);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 433) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 434) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 435)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 436) for (i = 0; i < num_configs; i++) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 437) param = pinconf_to_config_param(configs[i]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 438) arg = pinconf_to_config_argument(configs[i]);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 439)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 440) if ((param == PIN_CONFIG_BIAS_PULL_DOWN) ||
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 441) (param == PIN_CONFIG_BIAS_PULL_UP)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 442) if (arg == 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 443) param = PIN_CONFIG_BIAS_DISABLE;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 444) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 445)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 446) switch (param) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 447) case PIN_CONFIG_BIAS_DISABLE:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 448) wmt_clearbits(data, reg_pull_en, BIT(bit));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 449) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 450) case PIN_CONFIG_BIAS_PULL_DOWN:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 451) wmt_clearbits(data, reg_pull_cfg, BIT(bit));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 452) wmt_setbits(data, reg_pull_en, BIT(bit));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 453) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 454) case PIN_CONFIG_BIAS_PULL_UP:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 455) wmt_setbits(data, reg_pull_cfg, BIT(bit));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 456) wmt_setbits(data, reg_pull_en, BIT(bit));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 457) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 458) default:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 459) dev_err(data->dev, "unknown pinconf param\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 460) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 461) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 462) } /* for each config */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 463)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 464) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 465) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 466)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 467) static const struct pinconf_ops wmt_pinconf_ops = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 468) .pin_config_get = wmt_pinconf_get,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 469) .pin_config_set = wmt_pinconf_set,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 470) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 471)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 472) static struct pinctrl_desc wmt_desc = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 473) .owner = THIS_MODULE,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 474) .name = "pinctrl-wmt",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 475) .pctlops = &wmt_pctl_ops,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 476) .pmxops = &wmt_pinmux_ops,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 477) .confops = &wmt_pinconf_ops,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 478) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 479)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 480) static int wmt_gpio_get_direction(struct gpio_chip *chip, unsigned offset)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 481) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 482) struct wmt_pinctrl_data *data = gpiochip_get_data(chip);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 483) u32 bank = WMT_BANK_FROM_PIN(offset);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 484) u32 bit = WMT_BIT_FROM_PIN(offset);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 485) u32 reg_dir = data->banks[bank].reg_dir;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 486) u32 val;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 487)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 488) val = readl_relaxed(data->base + reg_dir);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 489) if (val & BIT(bit))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 490) return GPIO_LINE_DIRECTION_OUT;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 491)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 492) return GPIO_LINE_DIRECTION_IN;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 493) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 494)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 495) static int wmt_gpio_get_value(struct gpio_chip *chip, unsigned offset)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 496) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 497) struct wmt_pinctrl_data *data = gpiochip_get_data(chip);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 498) u32 bank = WMT_BANK_FROM_PIN(offset);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 499) u32 bit = WMT_BIT_FROM_PIN(offset);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 500) u32 reg_data_in = data->banks[bank].reg_data_in;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 501)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 502) if (reg_data_in == NO_REG) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 503) dev_err(data->dev, "no data in register defined\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 504) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 505) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 506)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 507) return !!(readl_relaxed(data->base + reg_data_in) & BIT(bit));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 508) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 509)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 510) static void wmt_gpio_set_value(struct gpio_chip *chip, unsigned offset,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 511) int val)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 512) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 513) struct wmt_pinctrl_data *data = gpiochip_get_data(chip);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 514) u32 bank = WMT_BANK_FROM_PIN(offset);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 515) u32 bit = WMT_BIT_FROM_PIN(offset);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 516) u32 reg_data_out = data->banks[bank].reg_data_out;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 517)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 518) if (reg_data_out == NO_REG) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 519) dev_err(data->dev, "no data out register defined\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 520) return;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 521) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 522)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 523) if (val)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 524) wmt_setbits(data, reg_data_out, BIT(bit));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 525) else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 526) wmt_clearbits(data, reg_data_out, BIT(bit));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 527) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 528)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 529) static int wmt_gpio_direction_input(struct gpio_chip *chip, unsigned offset)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 530) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 531) return pinctrl_gpio_direction_input(chip->base + offset);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 532) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 533)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 534) static int wmt_gpio_direction_output(struct gpio_chip *chip, unsigned offset,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 535) int value)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 536) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 537) wmt_gpio_set_value(chip, offset, value);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 538) return pinctrl_gpio_direction_output(chip->base + offset);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 539) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 540)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 541) static const struct gpio_chip wmt_gpio_chip = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 542) .label = "gpio-wmt",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 543) .owner = THIS_MODULE,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 544) .request = gpiochip_generic_request,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 545) .free = gpiochip_generic_free,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 546) .get_direction = wmt_gpio_get_direction,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 547) .direction_input = wmt_gpio_direction_input,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 548) .direction_output = wmt_gpio_direction_output,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 549) .get = wmt_gpio_get_value,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 550) .set = wmt_gpio_set_value,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 551) .can_sleep = false,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 552) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 553)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 554) int wmt_pinctrl_probe(struct platform_device *pdev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 555) struct wmt_pinctrl_data *data)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 556) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 557) int err;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 558)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 559) data->base = devm_platform_ioremap_resource(pdev, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 560) if (IS_ERR(data->base))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 561) return PTR_ERR(data->base);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 562)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 563) wmt_desc.pins = data->pins;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 564) wmt_desc.npins = data->npins;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 565)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 566) data->gpio_chip = wmt_gpio_chip;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 567) data->gpio_chip.parent = &pdev->dev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 568) data->gpio_chip.of_node = pdev->dev.of_node;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 569) data->gpio_chip.ngpio = data->nbanks * 32;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 570)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 571) platform_set_drvdata(pdev, data);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 572)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 573) data->dev = &pdev->dev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 574)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 575) data->pctl_dev = devm_pinctrl_register(&pdev->dev, &wmt_desc, data);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 576) if (IS_ERR(data->pctl_dev)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 577) dev_err(&pdev->dev, "Failed to register pinctrl\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 578) return PTR_ERR(data->pctl_dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 579) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 580)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 581) err = gpiochip_add_data(&data->gpio_chip, data);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 582) if (err) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 583) dev_err(&pdev->dev, "could not add GPIO chip\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 584) return err;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 585) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 586)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 587) err = gpiochip_add_pin_range(&data->gpio_chip, dev_name(data->dev),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 588) 0, 0, data->nbanks * 32);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 589) if (err)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 590) goto fail_range;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 591)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 592) dev_info(&pdev->dev, "Pin controller initialized\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 593)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 594) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 595)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 596) fail_range:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 597) gpiochip_remove(&data->gpio_chip);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 598) return err;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 599) }