diff options
| author | Ivan T. Ivanov <iivanov@mm-sol.com> | 2014-10-22 05:58:46 -0400 |
|---|---|---|
| committer | Linus Walleij <linus.walleij@linaro.org> | 2014-10-29 04:28:37 -0400 |
| commit | eadff3024472f8a7955fae7e5484d235ed407453 (patch) | |
| tree | f3fa17047fba6efcca794f8980bab982a17d95bd | |
| parent | 89a7117d56d405b49b7d1f8ed30e01188e9d5a05 (diff) | |
pinctrl: Qualcomm SPMI PMIC GPIO pin controller driver
This is the pinctrl, pinmux, pinconf and gpiolib driver for the
Qualcomm GPIO sub-function blocks found in the PMIC chips.
Signed-off-by: Ivan T. Ivanov <iivanov@mm-sol.com>
Acked-by: Bjorn Andersson <bjorn.andersson@sonymobile.com>
Signed-off-by: Linus Walleij <linus.walleij@linaro.org>
| -rw-r--r-- | drivers/pinctrl/qcom/Kconfig | 13 | ||||
| -rw-r--r-- | drivers/pinctrl/qcom/Makefile | 1 | ||||
| -rw-r--r-- | drivers/pinctrl/qcom/pinctrl-spmi-gpio.c | 933 |
3 files changed, 947 insertions, 0 deletions
diff --git a/drivers/pinctrl/qcom/Kconfig b/drivers/pinctrl/qcom/Kconfig index 81275af9638b..3cd243c26b7d 100644 --- a/drivers/pinctrl/qcom/Kconfig +++ b/drivers/pinctrl/qcom/Kconfig | |||
| @@ -47,4 +47,17 @@ config PINCTRL_MSM8X74 | |||
| 47 | This is the pinctrl, pinmux, pinconf and gpiolib driver for the | 47 | This is the pinctrl, pinmux, pinconf and gpiolib driver for the |
| 48 | Qualcomm TLMM block found in the Qualcomm 8974 platform. | 48 | Qualcomm TLMM block found in the Qualcomm 8974 platform. |
| 49 | 49 | ||
| 50 | config PINCTRL_QCOM_SPMI_PMIC | ||
| 51 | tristate "Qualcomm SPMI PMIC pin controller driver" | ||
| 52 | depends on GPIOLIB && OF && SPMI | ||
| 53 | select REGMAP_SPMI | ||
| 54 | select PINMUX | ||
| 55 | select PINCONF | ||
| 56 | select GENERIC_PINCONF | ||
| 57 | help | ||
| 58 | This is the pinctrl, pinmux, pinconf and gpiolib driver for the | ||
| 59 | Qualcomm GPIO and MPP blocks found in the Qualcomm PMIC's chips, | ||
| 60 | which are using SPMI for communication with SoC. Example PMIC's | ||
| 61 | devices are pm8841, pm8941 and pma8084. | ||
| 62 | |||
| 50 | endif | 63 | endif |
diff --git a/drivers/pinctrl/qcom/Makefile b/drivers/pinctrl/qcom/Makefile index ba8519fcd8d3..9b49c65a1cab 100644 --- a/drivers/pinctrl/qcom/Makefile +++ b/drivers/pinctrl/qcom/Makefile | |||
| @@ -5,3 +5,4 @@ obj-$(CONFIG_PINCTRL_APQ8084) += pinctrl-apq8084.o | |||
| 5 | obj-$(CONFIG_PINCTRL_IPQ8064) += pinctrl-ipq8064.o | 5 | obj-$(CONFIG_PINCTRL_IPQ8064) += pinctrl-ipq8064.o |
| 6 | obj-$(CONFIG_PINCTRL_MSM8960) += pinctrl-msm8960.o | 6 | obj-$(CONFIG_PINCTRL_MSM8960) += pinctrl-msm8960.o |
| 7 | obj-$(CONFIG_PINCTRL_MSM8X74) += pinctrl-msm8x74.o | 7 | obj-$(CONFIG_PINCTRL_MSM8X74) += pinctrl-msm8x74.o |
| 8 | obj-$(CONFIG_PINCTRL_QCOM_SPMI_PMIC) += pinctrl-spmi-gpio.o | ||
diff --git a/drivers/pinctrl/qcom/pinctrl-spmi-gpio.c b/drivers/pinctrl/qcom/pinctrl-spmi-gpio.c new file mode 100644 index 000000000000..b863b5080890 --- /dev/null +++ b/drivers/pinctrl/qcom/pinctrl-spmi-gpio.c | |||
| @@ -0,0 +1,933 @@ | |||
| 1 | /* | ||
| 2 | * Copyright (c) 2012-2014, The Linux Foundation. All rights reserved. | ||
| 3 | * | ||
| 4 | * This program is free software; you can redistribute it and/or modify | ||
| 5 | * it under the terms of the GNU General Public License version 2 and | ||
| 6 | * only version 2 as published by the Free Software Foundation. | ||
| 7 | * | ||
| 8 | * This program is distributed in the hope that it will be useful, | ||
| 9 | * but WITHOUT ANY WARRANTY; without even the implied warranty of | ||
| 10 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | ||
| 11 | * GNU General Public License for more details. | ||
| 12 | */ | ||
| 13 | |||
| 14 | #include <linux/gpio.h> | ||
| 15 | #include <linux/module.h> | ||
| 16 | #include <linux/of.h> | ||
| 17 | #include <linux/pinctrl/pinconf-generic.h> | ||
| 18 | #include <linux/pinctrl/pinconf.h> | ||
| 19 | #include <linux/pinctrl/pinmux.h> | ||
| 20 | #include <linux/platform_device.h> | ||
| 21 | #include <linux/regmap.h> | ||
| 22 | #include <linux/slab.h> | ||
| 23 | #include <linux/types.h> | ||
| 24 | |||
| 25 | #include <dt-bindings/pinctrl/qcom,pmic-gpio.h> | ||
| 26 | |||
| 27 | #include "../core.h" | ||
| 28 | #include "../pinctrl-utils.h" | ||
| 29 | |||
| 30 | #define PMIC_GPIO_ADDRESS_RANGE 0x100 | ||
| 31 | |||
| 32 | /* type and subtype registers base address offsets */ | ||
| 33 | #define PMIC_GPIO_REG_TYPE 0x4 | ||
| 34 | #define PMIC_GPIO_REG_SUBTYPE 0x5 | ||
| 35 | |||
| 36 | /* GPIO peripheral type and subtype out_values */ | ||
| 37 | #define PMIC_GPIO_TYPE 0x10 | ||
| 38 | #define PMIC_GPIO_SUBTYPE_GPIO_4CH 0x1 | ||
| 39 | #define PMIC_GPIO_SUBTYPE_GPIOC_4CH 0x5 | ||
| 40 | #define PMIC_GPIO_SUBTYPE_GPIO_8CH 0x9 | ||
| 41 | #define PMIC_GPIO_SUBTYPE_GPIOC_8CH 0xd | ||
| 42 | |||
| 43 | #define PMIC_MPP_REG_RT_STS 0x10 | ||
| 44 | #define PMIC_MPP_REG_RT_STS_VAL_MASK 0x1 | ||
| 45 | |||
| 46 | /* control register base address offsets */ | ||
| 47 | #define PMIC_GPIO_REG_MODE_CTL 0x40 | ||
| 48 | #define PMIC_GPIO_REG_DIG_VIN_CTL 0x41 | ||
| 49 | #define PMIC_GPIO_REG_DIG_PULL_CTL 0x42 | ||
| 50 | #define PMIC_GPIO_REG_DIG_OUT_CTL 0x45 | ||
| 51 | #define PMIC_GPIO_REG_EN_CTL 0x46 | ||
| 52 | |||
| 53 | /* PMIC_GPIO_REG_MODE_CTL */ | ||
| 54 | #define PMIC_GPIO_REG_MODE_VALUE_SHIFT 0x1 | ||
| 55 | #define PMIC_GPIO_REG_MODE_FUNCTION_SHIFT 1 | ||
| 56 | #define PMIC_GPIO_REG_MODE_FUNCTION_MASK 0x7 | ||
| 57 | #define PMIC_GPIO_REG_MODE_DIR_SHIFT 4 | ||
| 58 | #define PMIC_GPIO_REG_MODE_DIR_MASK 0x7 | ||
| 59 | |||
| 60 | /* PMIC_GPIO_REG_DIG_VIN_CTL */ | ||
| 61 | #define PMIC_GPIO_REG_VIN_SHIFT 0 | ||
| 62 | #define PMIC_GPIO_REG_VIN_MASK 0x7 | ||
| 63 | |||
| 64 | /* PMIC_GPIO_REG_DIG_PULL_CTL */ | ||
| 65 | #define PMIC_GPIO_REG_PULL_SHIFT 0 | ||
| 66 | #define PMIC_GPIO_REG_PULL_MASK 0x7 | ||
| 67 | |||
| 68 | #define PMIC_GPIO_PULL_DOWN 4 | ||
| 69 | #define PMIC_GPIO_PULL_DISABLE 5 | ||
| 70 | |||
| 71 | /* PMIC_GPIO_REG_DIG_OUT_CTL */ | ||
| 72 | #define PMIC_GPIO_REG_OUT_STRENGTH_SHIFT 0 | ||
| 73 | #define PMIC_GPIO_REG_OUT_STRENGTH_MASK 0x3 | ||
| 74 | #define PMIC_GPIO_REG_OUT_TYPE_SHIFT 4 | ||
| 75 | #define PMIC_GPIO_REG_OUT_TYPE_MASK 0x3 | ||
| 76 | |||
| 77 | /* | ||
| 78 | * Output type - indicates pin should be configured as push-pull, | ||
| 79 | * open drain or open source. | ||
| 80 | */ | ||
| 81 | #define PMIC_GPIO_OUT_BUF_CMOS 0 | ||
| 82 | #define PMIC_GPIO_OUT_BUF_OPEN_DRAIN_NMOS 1 | ||
| 83 | #define PMIC_GPIO_OUT_BUF_OPEN_DRAIN_PMOS 2 | ||
| 84 | |||
| 85 | /* PMIC_GPIO_REG_EN_CTL */ | ||
| 86 | #define PMIC_GPIO_REG_MASTER_EN_SHIFT 7 | ||
| 87 | |||
| 88 | #define PMIC_GPIO_PHYSICAL_OFFSET 1 | ||
| 89 | |||
| 90 | /* Qualcomm specific pin configurations */ | ||
| 91 | #define PMIC_GPIO_CONF_PULL_UP (PIN_CONFIG_END + 1) | ||
| 92 | #define PMIC_GPIO_CONF_STRENGTH (PIN_CONFIG_END + 2) | ||
| 93 | |||
| 94 | /** | ||
| 95 | * struct pmic_gpio_pad - keep current GPIO settings | ||
| 96 | * @base: Address base in SPMI device. | ||
| 97 | * @irq: IRQ number which this GPIO generate. | ||
| 98 | * @is_enabled: Set to false when GPIO should be put in high Z state. | ||
| 99 | * @out_value: Cached pin output value | ||
| 100 | * @have_buffer: Set to true if GPIO output could be configured in push-pull, | ||
| 101 | * open-drain or open-source mode. | ||
| 102 | * @output_enabled: Set to true if GPIO output logic is enabled. | ||
| 103 | * @input_enabled: Set to true if GPIO input buffer logic is enabled. | ||
| 104 | * @num_sources: Number of power-sources supported by this GPIO. | ||
| 105 | * @power_source: Current power-source used. | ||
| 106 | * @buffer_type: Push-pull, open-drain or open-source. | ||
| 107 | * @pullup: Constant current which flow trough GPIO output buffer. | ||
| 108 | * @strength: No, Low, Medium, High | ||
| 109 | * @function: See pmic_gpio_functions[] | ||
| 110 | */ | ||
| 111 | struct pmic_gpio_pad { | ||
| 112 | u16 base; | ||
| 113 | int irq; | ||
| 114 | bool is_enabled; | ||
| 115 | bool out_value; | ||
| 116 | bool have_buffer; | ||
| 117 | bool output_enabled; | ||
| 118 | bool input_enabled; | ||
| 119 | unsigned int num_sources; | ||
| 120 | unsigned int power_source; | ||
| 121 | unsigned int buffer_type; | ||
| 122 | unsigned int pullup; | ||
| 123 | unsigned int strength; | ||
| 124 | unsigned int function; | ||
| 125 | }; | ||
| 126 | |||
| 127 | struct pmic_gpio_state { | ||
| 128 | struct device *dev; | ||
| 129 | struct regmap *map; | ||
| 130 | struct pinctrl_dev *ctrl; | ||
| 131 | struct gpio_chip chip; | ||
| 132 | }; | ||
| 133 | |||
| 134 | struct pmic_gpio_bindings { | ||
| 135 | const char *property; | ||
| 136 | unsigned param; | ||
| 137 | }; | ||
| 138 | |||
| 139 | static struct pmic_gpio_bindings pmic_gpio_bindings[] = { | ||
| 140 | {"qcom,pull-up-strength", PMIC_GPIO_CONF_PULL_UP}, | ||
| 141 | {"qcom,drive-strength", PMIC_GPIO_CONF_STRENGTH}, | ||
| 142 | }; | ||
| 143 | |||
| 144 | static const char *const pmic_gpio_groups[] = { | ||
| 145 | "gpio1", "gpio2", "gpio3", "gpio4", "gpio5", "gpio6", "gpio7", "gpio8", | ||
| 146 | "gpio9", "gpio10", "gpio11", "gpio12", "gpio13", "gpio14", "gpio15", | ||
| 147 | "gpio16", "gpio17", "gpio18", "gpio19", "gpio20", "gpio21", "gpio22", | ||
| 148 | "gpio23", "gpio24", "gpio25", "gpio26", "gpio27", "gpio28", "gpio29", | ||
| 149 | "gpio30", "gpio31", "gpio32", "gpio33", "gpio34", "gpio35", "gpio36", | ||
| 150 | }; | ||
| 151 | |||
| 152 | static const char *const pmic_gpio_functions[] = { | ||
| 153 | PMIC_GPIO_FUNC_NORMAL, PMIC_GPIO_FUNC_PAIRED, | ||
