| .. | .. |
|---|
| 1 | | -/* |
|---|
| 2 | | - * wm8994-regulator.c -- Regulator driver for the WM8994 |
|---|
| 3 | | - * |
|---|
| 4 | | - * Copyright 2009 Wolfson Microelectronics PLC. |
|---|
| 5 | | - * |
|---|
| 6 | | - * Author: Mark Brown <broonie@opensource.wolfsonmicro.com> |
|---|
| 7 | | - * |
|---|
| 8 | | - * This program is free software; you can redistribute it and/or modify it |
|---|
| 9 | | - * under the terms of the GNU General Public License as published by the |
|---|
| 10 | | - * Free Software Foundation; either version 2 of the License, or (at your |
|---|
| 11 | | - * option) any later version. |
|---|
| 12 | | - */ |
|---|
| 1 | +// SPDX-License-Identifier: GPL-2.0+ |
|---|
| 2 | +// |
|---|
| 3 | +// wm8994-regulator.c -- Regulator driver for the WM8994 |
|---|
| 4 | +// |
|---|
| 5 | +// Copyright 2009 Wolfson Microelectronics PLC. |
|---|
| 6 | +// |
|---|
| 7 | +// Author: Mark Brown <broonie@opensource.wolfsonmicro.com> |
|---|
| 13 | 8 | |
|---|
| 14 | 9 | #include <linux/module.h> |
|---|
| 15 | 10 | #include <linux/moduleparam.h> |
|---|
| .. | .. |
|---|
| 19 | 14 | #include <linux/platform_device.h> |
|---|
| 20 | 15 | #include <linux/regulator/driver.h> |
|---|
| 21 | 16 | #include <linux/regulator/machine.h> |
|---|
| 22 | | -#include <linux/gpio.h> |
|---|
| 17 | +#include <linux/gpio/consumer.h> |
|---|
| 23 | 18 | #include <linux/slab.h> |
|---|
| 24 | 19 | |
|---|
| 25 | 20 | #include <linux/mfd/wm8994/core.h> |
|---|
| .. | .. |
|---|
| 87 | 82 | .min_uV = 2400000, |
|---|
| 88 | 83 | .uV_step = 100000, |
|---|
| 89 | 84 | .enable_time = 3000, |
|---|
| 85 | + .off_on_delay = 36000, |
|---|
| 86 | + .owner = THIS_MODULE, |
|---|
| 87 | + }, |
|---|
| 88 | + { |
|---|
| 89 | + .name = "LDO2", |
|---|
| 90 | + .id = 2, |
|---|
| 91 | + .type = REGULATOR_VOLTAGE, |
|---|
| 92 | + .n_voltages = WM8994_LDO2_MAX_SELECTOR + 1, |
|---|
| 93 | + .vsel_reg = WM8994_LDO_2, |
|---|
| 94 | + .vsel_mask = WM8994_LDO2_VSEL_MASK, |
|---|
| 95 | + .ops = &wm8994_ldo2_ops, |
|---|
| 96 | + .enable_time = 3000, |
|---|
| 97 | + .off_on_delay = 36000, |
|---|
| 98 | + .owner = THIS_MODULE, |
|---|
| 99 | + }, |
|---|
| 100 | +}; |
|---|
| 101 | + |
|---|
| 102 | +static const struct regulator_desc wm8958_ldo_desc[] = { |
|---|
| 103 | + { |
|---|
| 104 | + .name = "LDO1", |
|---|
| 105 | + .id = 1, |
|---|
| 106 | + .type = REGULATOR_VOLTAGE, |
|---|
| 107 | + .n_voltages = WM8994_LDO1_MAX_SELECTOR + 1, |
|---|
| 108 | + .vsel_reg = WM8994_LDO_1, |
|---|
| 109 | + .vsel_mask = WM8994_LDO1_VSEL_MASK, |
|---|
| 110 | + .ops = &wm8994_ldo1_ops, |
|---|
| 111 | + .min_uV = 2400000, |
|---|
| 112 | + .uV_step = 100000, |
|---|
| 113 | + .enable_time = 3000, |
|---|
| 90 | 114 | .owner = THIS_MODULE, |
|---|
| 91 | 115 | }, |
|---|
| 92 | 116 | { |
|---|
| .. | .. |
|---|
| 129 | 153 | int id = pdev->id % ARRAY_SIZE(pdata->ldo); |
|---|
| 130 | 154 | struct regulator_config config = { }; |
|---|
| 131 | 155 | struct wm8994_ldo *ldo; |
|---|
| 156 | + struct gpio_desc *gpiod; |
|---|
| 132 | 157 | int ret; |
|---|
| 133 | 158 | |
|---|
| 134 | 159 | dev_dbg(&pdev->dev, "Probing LDO%d\n", id + 1); |
|---|
| .. | .. |
|---|
| 145 | 170 | config.driver_data = ldo; |
|---|
| 146 | 171 | config.regmap = wm8994->regmap; |
|---|
| 147 | 172 | config.init_data = &ldo->init_data; |
|---|
| 148 | | - if (pdata) { |
|---|
| 149 | | - config.ena_gpio = pdata->ldo[id].enable; |
|---|
| 150 | | - } else if (wm8994->dev->of_node) { |
|---|
| 151 | | - config.ena_gpio = wm8994->pdata.ldo[id].enable; |
|---|
| 152 | | - config.ena_gpio_initialized = true; |
|---|
| 153 | | - } |
|---|
| 173 | + |
|---|
| 174 | + /* |
|---|
| 175 | + * Look up LDO enable GPIO from the parent device node, we don't |
|---|
| 176 | + * use devm because the regulator core will free the GPIO |
|---|
| 177 | + */ |
|---|
| 178 | + gpiod = gpiod_get_optional(pdev->dev.parent, |
|---|
| 179 | + id ? "wlf,ldo2ena" : "wlf,ldo1ena", |
|---|
| 180 | + GPIOD_OUT_LOW | |
|---|
| 181 | + GPIOD_FLAGS_BIT_NONEXCLUSIVE); |
|---|
| 182 | + if (IS_ERR(gpiod)) |
|---|
| 183 | + return PTR_ERR(gpiod); |
|---|
| 184 | + config.ena_gpiod = gpiod; |
|---|
| 154 | 185 | |
|---|
| 155 | 186 | /* Use default constraints if none set up */ |
|---|
| 156 | 187 | if (!pdata || !pdata->ldo[id].init_data || wm8994->dev->of_node) { |
|---|
| .. | .. |
|---|
| 159 | 190 | |
|---|
| 160 | 191 | ldo->init_data = wm8994_ldo_default[id]; |
|---|
| 161 | 192 | ldo->init_data.consumer_supplies = &ldo->supply; |
|---|
| 162 | | - if (!config.ena_gpio) |
|---|
| 193 | + if (!gpiod) |
|---|
| 163 | 194 | ldo->init_data.constraints.valid_ops_mask = 0; |
|---|
| 164 | 195 | } else { |
|---|
| 165 | 196 | ldo->init_data = *pdata->ldo[id].init_data; |
|---|
| 166 | 197 | } |
|---|
| 167 | 198 | |
|---|
| 168 | | - ldo->regulator = devm_regulator_register(&pdev->dev, |
|---|
| 169 | | - &wm8994_ldo_desc[id], |
|---|
| 170 | | - &config); |
|---|
| 199 | + /* |
|---|
| 200 | + * At this point the GPIO descriptor is handled over to the |
|---|
| 201 | + * regulator core and we need not worry about it on the |
|---|
| 202 | + * error path. |
|---|
| 203 | + */ |
|---|
| 204 | + if (ldo->wm8994->type == WM8994) { |
|---|
| 205 | + ldo->regulator = devm_regulator_register(&pdev->dev, |
|---|
| 206 | + &wm8994_ldo_desc[id], |
|---|
| 207 | + &config); |
|---|
| 208 | + } else { |
|---|
| 209 | + ldo->regulator = devm_regulator_register(&pdev->dev, |
|---|
| 210 | + &wm8958_ldo_desc[id], |
|---|
| 211 | + &config); |
|---|
| 212 | + } |
|---|
| 213 | + |
|---|
| 171 | 214 | if (IS_ERR(ldo->regulator)) { |
|---|
| 172 | 215 | ret = PTR_ERR(ldo->regulator); |
|---|
| 173 | 216 | dev_err(wm8994->dev, "Failed to register LDO%d: %d\n", |
|---|
| 174 | 217 | id + 1, ret); |
|---|
| 175 | | - goto err; |
|---|
| 218 | + return ret; |
|---|
| 176 | 219 | } |
|---|
| 177 | 220 | |
|---|
| 178 | 221 | platform_set_drvdata(pdev, ldo); |
|---|
| 179 | 222 | |
|---|
| 180 | 223 | return 0; |
|---|
| 181 | | - |
|---|
| 182 | | -err: |
|---|
| 183 | | - return ret; |
|---|
| 184 | 224 | } |
|---|
| 185 | 225 | |
|---|
| 186 | 226 | static struct platform_driver wm8994_ldo_driver = { |
|---|