1*4882a593Smuzhiyun // SPDX-License-Identifier: GPL-2.0-or-later
2*4882a593Smuzhiyun /*
3*4882a593Smuzhiyun * wm8994-core.c -- Device access for Wolfson WM8994
4*4882a593Smuzhiyun *
5*4882a593Smuzhiyun * Copyright 2009 Wolfson Microelectronics PLC.
6*4882a593Smuzhiyun *
7*4882a593Smuzhiyun * Author: Mark Brown <broonie@opensource.wolfsonmicro.com>
8*4882a593Smuzhiyun */
9*4882a593Smuzhiyun
10*4882a593Smuzhiyun #include <linux/kernel.h>
11*4882a593Smuzhiyun #include <linux/module.h>
12*4882a593Smuzhiyun #include <linux/slab.h>
13*4882a593Smuzhiyun #include <linux/i2c.h>
14*4882a593Smuzhiyun #include <linux/err.h>
15*4882a593Smuzhiyun #include <linux/delay.h>
16*4882a593Smuzhiyun #include <linux/mfd/core.h>
17*4882a593Smuzhiyun #include <linux/of.h>
18*4882a593Smuzhiyun #include <linux/of_device.h>
19*4882a593Smuzhiyun #include <linux/pm_runtime.h>
20*4882a593Smuzhiyun #include <linux/regmap.h>
21*4882a593Smuzhiyun #include <linux/regulator/consumer.h>
22*4882a593Smuzhiyun #include <linux/regulator/machine.h>
23*4882a593Smuzhiyun
24*4882a593Smuzhiyun #include <linux/mfd/wm8994/core.h>
25*4882a593Smuzhiyun #include <linux/mfd/wm8994/pdata.h>
26*4882a593Smuzhiyun #include <linux/mfd/wm8994/registers.h>
27*4882a593Smuzhiyun
28*4882a593Smuzhiyun #include "wm8994.h"
29*4882a593Smuzhiyun
30*4882a593Smuzhiyun static const struct mfd_cell wm8994_regulator_devs[] = {
31*4882a593Smuzhiyun {
32*4882a593Smuzhiyun .name = "wm8994-ldo",
33*4882a593Smuzhiyun .id = 0,
34*4882a593Smuzhiyun .pm_runtime_no_callbacks = true,
35*4882a593Smuzhiyun },
36*4882a593Smuzhiyun {
37*4882a593Smuzhiyun .name = "wm8994-ldo",
38*4882a593Smuzhiyun .id = 1,
39*4882a593Smuzhiyun .pm_runtime_no_callbacks = true,
40*4882a593Smuzhiyun },
41*4882a593Smuzhiyun };
42*4882a593Smuzhiyun
43*4882a593Smuzhiyun static struct resource wm8994_codec_resources[] = {
44*4882a593Smuzhiyun {
45*4882a593Smuzhiyun .start = WM8994_IRQ_TEMP_SHUT,
46*4882a593Smuzhiyun .end = WM8994_IRQ_TEMP_WARN,
47*4882a593Smuzhiyun .flags = IORESOURCE_IRQ,
48*4882a593Smuzhiyun },
49*4882a593Smuzhiyun };
50*4882a593Smuzhiyun
51*4882a593Smuzhiyun static struct resource wm8994_gpio_resources[] = {
52*4882a593Smuzhiyun {
53*4882a593Smuzhiyun .start = WM8994_IRQ_GPIO(1),
54*4882a593Smuzhiyun .end = WM8994_IRQ_GPIO(11),
55*4882a593Smuzhiyun .flags = IORESOURCE_IRQ,
56*4882a593Smuzhiyun },
57*4882a593Smuzhiyun };
58*4882a593Smuzhiyun
59*4882a593Smuzhiyun static const struct mfd_cell wm8994_devs[] = {
60*4882a593Smuzhiyun {
61*4882a593Smuzhiyun .name = "wm8994-codec",
62*4882a593Smuzhiyun .num_resources = ARRAY_SIZE(wm8994_codec_resources),
63*4882a593Smuzhiyun .resources = wm8994_codec_resources,
64*4882a593Smuzhiyun },
65*4882a593Smuzhiyun
66*4882a593Smuzhiyun {
67*4882a593Smuzhiyun .name = "wm8994-gpio",
68*4882a593Smuzhiyun .num_resources = ARRAY_SIZE(wm8994_gpio_resources),
69*4882a593Smuzhiyun .resources = wm8994_gpio_resources,
70*4882a593Smuzhiyun .pm_runtime_no_callbacks = true,
71*4882a593Smuzhiyun },
72*4882a593Smuzhiyun };
73*4882a593Smuzhiyun
74*4882a593Smuzhiyun /*
75*4882a593Smuzhiyun * Supplies for the main bulk of CODEC; the LDO supplies are ignored
76*4882a593Smuzhiyun * and should be handled via the standard regulator API supply
77*4882a593Smuzhiyun * management.
78*4882a593Smuzhiyun */
79*4882a593Smuzhiyun static const char *wm1811_main_supplies[] = {
80*4882a593Smuzhiyun "DBVDD1",
81*4882a593Smuzhiyun "DBVDD2",
82*4882a593Smuzhiyun "DBVDD3",
83*4882a593Smuzhiyun "DCVDD",
84*4882a593Smuzhiyun "AVDD1",
85*4882a593Smuzhiyun "AVDD2",
86*4882a593Smuzhiyun "CPVDD",
87*4882a593Smuzhiyun "SPKVDD1",
88*4882a593Smuzhiyun "SPKVDD2",
89*4882a593Smuzhiyun };
90*4882a593Smuzhiyun
91*4882a593Smuzhiyun static const char *wm8994_main_supplies[] = {
92*4882a593Smuzhiyun "DBVDD",
93*4882a593Smuzhiyun "DCVDD",
94*4882a593Smuzhiyun "AVDD1",
95*4882a593Smuzhiyun "AVDD2",
96*4882a593Smuzhiyun "CPVDD",
97*4882a593Smuzhiyun "SPKVDD1",
98*4882a593Smuzhiyun "SPKVDD2",
99*4882a593Smuzhiyun };
100*4882a593Smuzhiyun
101*4882a593Smuzhiyun static const char *wm8958_main_supplies[] = {
102*4882a593Smuzhiyun "DBVDD1",
103*4882a593Smuzhiyun "DBVDD2",
104*4882a593Smuzhiyun "DBVDD3",
105*4882a593Smuzhiyun "DCVDD",
106*4882a593Smuzhiyun "AVDD1",
107*4882a593Smuzhiyun "AVDD2",
108*4882a593Smuzhiyun "CPVDD",
109*4882a593Smuzhiyun "SPKVDD1",
110*4882a593Smuzhiyun "SPKVDD2",
111*4882a593Smuzhiyun };
112*4882a593Smuzhiyun
113*4882a593Smuzhiyun #ifdef CONFIG_PM
wm8994_suspend(struct device * dev)114*4882a593Smuzhiyun static int wm8994_suspend(struct device *dev)
115*4882a593Smuzhiyun {
116*4882a593Smuzhiyun struct wm8994 *wm8994 = dev_get_drvdata(dev);
117*4882a593Smuzhiyun int ret;
118*4882a593Smuzhiyun
119*4882a593Smuzhiyun /* Don't actually go through with the suspend if the CODEC is
120*4882a593Smuzhiyun * still active for accessory detect. */
121*4882a593Smuzhiyun switch (wm8994->type) {
122*4882a593Smuzhiyun case WM8958:
123*4882a593Smuzhiyun case WM1811:
124*4882a593Smuzhiyun ret = wm8994_reg_read(wm8994, WM8958_MIC_DETECT_1);
125*4882a593Smuzhiyun if (ret < 0) {
126*4882a593Smuzhiyun dev_err(dev, "Failed to read power status: %d\n", ret);
127*4882a593Smuzhiyun } else if (ret & WM8958_MICD_ENA) {
128*4882a593Smuzhiyun dev_dbg(dev, "CODEC still active, ignoring suspend\n");
129*4882a593Smuzhiyun return 0;
130*4882a593Smuzhiyun }
131*4882a593Smuzhiyun break;
132*4882a593Smuzhiyun default:
133*4882a593Smuzhiyun break;
134*4882a593Smuzhiyun }
135*4882a593Smuzhiyun
136*4882a593Smuzhiyun /* Disable LDO pulldowns while the device is suspended if we
137*4882a593Smuzhiyun * don't know that something will be driving them. */
138*4882a593Smuzhiyun if (!wm8994->ldo_ena_always_driven)
139*4882a593Smuzhiyun wm8994_set_bits(wm8994, WM8994_PULL_CONTROL_2,
140*4882a593Smuzhiyun WM8994_LDO1ENA_PD | WM8994_LDO2ENA_PD,
141*4882a593Smuzhiyun WM8994_LDO1ENA_PD | WM8994_LDO2ENA_PD);
142*4882a593Smuzhiyun
143*4882a593Smuzhiyun /* Explicitly put the device into reset in case regulators
144*4882a593Smuzhiyun * don't get disabled in order to ensure consistent restart.
145*4882a593Smuzhiyun */
146*4882a593Smuzhiyun wm8994_reg_write(wm8994, WM8994_SOFTWARE_RESET,
147*4882a593Smuzhiyun wm8994_reg_read(wm8994, WM8994_SOFTWARE_RESET));
148*4882a593Smuzhiyun
149*4882a593Smuzhiyun regcache_mark_dirty(wm8994->regmap);
150*4882a593Smuzhiyun
151*4882a593Smuzhiyun /* Restore GPIO registers to prevent problems with mismatched
152*4882a593Smuzhiyun * pin configurations.
153*4882a593Smuzhiyun */
154*4882a593Smuzhiyun ret = regcache_sync_region(wm8994->regmap, WM8994_GPIO_1,
155*4882a593Smuzhiyun WM8994_GPIO_11);
156*4882a593Smuzhiyun if (ret != 0)
157*4882a593Smuzhiyun dev_err(dev, "Failed to restore GPIO registers: %d\n", ret);
158*4882a593Smuzhiyun
159*4882a593Smuzhiyun /* In case one of the GPIOs is used as a wake input. */
160*4882a593Smuzhiyun ret = regcache_sync_region(wm8994->regmap,
161*4882a593Smuzhiyun WM8994_INTERRUPT_STATUS_1_MASK,
162*4882a593Smuzhiyun WM8994_INTERRUPT_STATUS_1_MASK);
163*4882a593Smuzhiyun if (ret != 0)
164*4882a593Smuzhiyun dev_err(dev, "Failed to restore interrupt mask: %d\n", ret);
165*4882a593Smuzhiyun
166*4882a593Smuzhiyun regcache_cache_only(wm8994->regmap, true);
167*4882a593Smuzhiyun wm8994->suspended = true;
168*4882a593Smuzhiyun
169*4882a593Smuzhiyun ret = regulator_bulk_disable(wm8994->num_supplies,
170*4882a593Smuzhiyun wm8994->supplies);
171*4882a593Smuzhiyun if (ret != 0) {
172*4882a593Smuzhiyun dev_err(dev, "Failed to disable supplies: %d\n", ret);
173*4882a593Smuzhiyun return ret;
174*4882a593Smuzhiyun }
175*4882a593Smuzhiyun
176*4882a593Smuzhiyun return 0;
177*4882a593Smuzhiyun }
178*4882a593Smuzhiyun
wm8994_resume(struct device * dev)179*4882a593Smuzhiyun static int wm8994_resume(struct device *dev)
180*4882a593Smuzhiyun {
181*4882a593Smuzhiyun struct wm8994 *wm8994 = dev_get_drvdata(dev);
182*4882a593Smuzhiyun int ret;
183*4882a593Smuzhiyun
184*4882a593Smuzhiyun /* We may have lied to the PM core about suspending */
185*4882a593Smuzhiyun if (!wm8994->suspended)
186*4882a593Smuzhiyun return 0;
187*4882a593Smuzhiyun
188*4882a593Smuzhiyun ret = regulator_bulk_enable(wm8994->num_supplies,
189*4882a593Smuzhiyun wm8994->supplies);
190*4882a593Smuzhiyun if (ret != 0) {
191*4882a593Smuzhiyun dev_err(dev, "Failed to enable supplies: %d\n", ret);
192*4882a593Smuzhiyun return ret;
193*4882a593Smuzhiyun }
194*4882a593Smuzhiyun
195*4882a593Smuzhiyun regcache_cache_only(wm8994->regmap, false);
196*4882a593Smuzhiyun ret = regcache_sync(wm8994->regmap);
197*4882a593Smuzhiyun if (ret != 0) {
198*4882a593Smuzhiyun dev_err(dev, "Failed to restore register map: %d\n", ret);
199*4882a593Smuzhiyun goto err_enable;
200*4882a593Smuzhiyun }
201*4882a593Smuzhiyun
202*4882a593Smuzhiyun /* Disable LDO pulldowns while the device is active */
203*4882a593Smuzhiyun wm8994_set_bits(wm8994, WM8994_PULL_CONTROL_2,
204*4882a593Smuzhiyun WM8994_LDO1ENA_PD | WM8994_LDO2ENA_PD,
205*4882a593Smuzhiyun 0);
206*4882a593Smuzhiyun
207*4882a593Smuzhiyun wm8994->suspended = false;
208*4882a593Smuzhiyun
209*4882a593Smuzhiyun return 0;
210*4882a593Smuzhiyun
211*4882a593Smuzhiyun err_enable:
212*4882a593Smuzhiyun regulator_bulk_disable(wm8994->num_supplies, wm8994->supplies);
213*4882a593Smuzhiyun
214*4882a593Smuzhiyun return ret;
215*4882a593Smuzhiyun }
216*4882a593Smuzhiyun #endif
217*4882a593Smuzhiyun
218*4882a593Smuzhiyun #ifdef CONFIG_REGULATOR
wm8994_ldo_in_use(struct wm8994_pdata * pdata,int ldo)219*4882a593Smuzhiyun static int wm8994_ldo_in_use(struct wm8994_pdata *pdata, int ldo)
220*4882a593Smuzhiyun {
221*4882a593Smuzhiyun struct wm8994_ldo_pdata *ldo_pdata;
222*4882a593Smuzhiyun
223*4882a593Smuzhiyun if (!pdata)
224*4882a593Smuzhiyun return 0;
225*4882a593Smuzhiyun
226*4882a593Smuzhiyun ldo_pdata = &pdata->ldo[ldo];
227*4882a593Smuzhiyun
228*4882a593Smuzhiyun if (!ldo_pdata->init_data)
229*4882a593Smuzhiyun return 0;
230*4882a593Smuzhiyun
231*4882a593Smuzhiyun return ldo_pdata->init_data->num_consumer_supplies != 0;
232*4882a593Smuzhiyun }
233*4882a593Smuzhiyun #else
wm8994_ldo_in_use(struct wm8994_pdata * pdata,int ldo)234*4882a593Smuzhiyun static int wm8994_ldo_in_use(struct wm8994_pdata *pdata, int ldo)
235*4882a593Smuzhiyun {
236*4882a593Smuzhiyun return 0;
237*4882a593Smuzhiyun }
238*4882a593Smuzhiyun #endif
239*4882a593Smuzhiyun
240*4882a593Smuzhiyun static const struct reg_sequence wm8994_revc_patch[] = {
241*4882a593Smuzhiyun { 0x102, 0x3 },
242*4882a593Smuzhiyun { 0x56, 0x3 },
243*4882a593Smuzhiyun { 0x817, 0x0 },
244*4882a593Smuzhiyun { 0x102, 0x0 },
245*4882a593Smuzhiyun };
246*4882a593Smuzhiyun
247*4882a593Smuzhiyun static const struct reg_sequence wm8958_reva_patch[] = {
248*4882a593Smuzhiyun { 0x102, 0x3 },
249*4882a593Smuzhiyun { 0xcb, 0x81 },
250*4882a593Smuzhiyun { 0x817, 0x0 },
251*4882a593Smuzhiyun { 0x102, 0x0 },
252*4882a593Smuzhiyun };
253*4882a593Smuzhiyun
254*4882a593Smuzhiyun static const struct reg_sequence wm1811_reva_patch[] = {
255*4882a593Smuzhiyun { 0x102, 0x3 },
256*4882a593Smuzhiyun { 0x56, 0xc07 },
257*4882a593Smuzhiyun { 0x5d, 0x7e },
258*4882a593Smuzhiyun { 0x5e, 0x0 },
259*4882a593Smuzhiyun { 0x102, 0x0 },
260*4882a593Smuzhiyun };
261*4882a593Smuzhiyun
262*4882a593Smuzhiyun #ifdef CONFIG_OF
wm8994_set_pdata_from_of(struct wm8994 * wm8994)263*4882a593Smuzhiyun static int wm8994_set_pdata_from_of(struct wm8994 *wm8994)
264*4882a593Smuzhiyun {
265*4882a593Smuzhiyun struct device_node *np = wm8994->dev->of_node;
266*4882a593Smuzhiyun struct wm8994_pdata *pdata = &wm8994->pdata;
267*4882a593Smuzhiyun int i;
268*4882a593Smuzhiyun
269*4882a593Smuzhiyun if (!np)
270*4882a593Smuzhiyun return 0;
271*4882a593Smuzhiyun
272*4882a593Smuzhiyun if (of_property_read_u32_array(np, "wlf,gpio-cfg", pdata->gpio_defaults,
273*4882a593Smuzhiyun ARRAY_SIZE(pdata->gpio_defaults)) >= 0) {
274*4882a593Smuzhiyun for (i = 0; i < ARRAY_SIZE(pdata->gpio_defaults); i++) {
275*4882a593Smuzhiyun if (wm8994->pdata.gpio_defaults[i] == 0)
276*4882a593Smuzhiyun pdata->gpio_defaults[i]
277*4882a593Smuzhiyun = WM8994_CONFIGURE_GPIO;
278*4882a593Smuzhiyun }
279*4882a593Smuzhiyun }
280*4882a593Smuzhiyun
281*4882a593Smuzhiyun of_property_read_u32_array(np, "wlf,micbias-cfg", pdata->micbias,
282*4882a593Smuzhiyun ARRAY_SIZE(pdata->micbias));
283*4882a593Smuzhiyun
284*4882a593Smuzhiyun pdata->lineout1_diff = true;
285*4882a593Smuzhiyun pdata->lineout2_diff = true;
286*4882a593Smuzhiyun if (of_find_property(np, "wlf,lineout1-se", NULL))
287*4882a593Smuzhiyun pdata->lineout1_diff = false;
288*4882a593Smuzhiyun if (of_find_property(np, "wlf,lineout2-se", NULL))
289*4882a593Smuzhiyun pdata->lineout2_diff = false;
290*4882a593Smuzhiyun
291*4882a593Smuzhiyun if (of_find_property(np, "wlf,lineout1-feedback", NULL))
292*4882a593Smuzhiyun pdata->lineout1fb = true;
293*4882a593Smuzhiyun if (of_find_property(np, "wlf,lineout2-feedback", NULL))
294*4882a593Smuzhiyun pdata->lineout2fb = true;
295*4882a593Smuzhiyun
296*4882a593Smuzhiyun if (of_find_property(np, "wlf,ldoena-always-driven", NULL))
297*4882a593Smuzhiyun pdata->lineout2fb = true;
298*4882a593Smuzhiyun
299*4882a593Smuzhiyun pdata->spkmode_pu = of_property_read_bool(np, "wlf,spkmode-pu");
300*4882a593Smuzhiyun
301*4882a593Smuzhiyun pdata->csnaddr_pd = of_property_read_bool(np, "wlf,csnaddr-pd");
302*4882a593Smuzhiyun
303*4882a593Smuzhiyun return 0;
304*4882a593Smuzhiyun }
305*4882a593Smuzhiyun #else
wm8994_set_pdata_from_of(struct wm8994 * wm8994)306*4882a593Smuzhiyun static int wm8994_set_pdata_from_of(struct wm8994 *wm8994)
307*4882a593Smuzhiyun {
308*4882a593Smuzhiyun return 0;
309*4882a593Smuzhiyun }
310*4882a593Smuzhiyun #endif
311*4882a593Smuzhiyun
312*4882a593Smuzhiyun /*
313*4882a593Smuzhiyun * Instantiate the generic non-control parts of the device.
314*4882a593Smuzhiyun */
wm8994_device_init(struct wm8994 * wm8994,int irq)315*4882a593Smuzhiyun static int wm8994_device_init(struct wm8994 *wm8994, int irq)
316*4882a593Smuzhiyun {
317*4882a593Smuzhiyun struct wm8994_pdata *pdata;
318*4882a593Smuzhiyun struct regmap_config *regmap_config;
319*4882a593Smuzhiyun const struct reg_sequence *regmap_patch = NULL;
320*4882a593Smuzhiyun const char *devname;
321*4882a593Smuzhiyun int ret, i, patch_regs = 0;
322*4882a593Smuzhiyun int pulls = 0;
323*4882a593Smuzhiyun
324*4882a593Smuzhiyun if (dev_get_platdata(wm8994->dev)) {
325*4882a593Smuzhiyun pdata = dev_get_platdata(wm8994->dev);
326*4882a593Smuzhiyun wm8994->pdata = *pdata;
327*4882a593Smuzhiyun }
328*4882a593Smuzhiyun pdata = &wm8994->pdata;
329*4882a593Smuzhiyun
330*4882a593Smuzhiyun ret = wm8994_set_pdata_from_of(wm8994);
331*4882a593Smuzhiyun if (ret != 0)
332*4882a593Smuzhiyun return ret;
333*4882a593Smuzhiyun
334*4882a593Smuzhiyun dev_set_drvdata(wm8994->dev, wm8994);
335*4882a593Smuzhiyun
336*4882a593Smuzhiyun /* Add the on-chip regulators first for bootstrapping */
337*4882a593Smuzhiyun ret = mfd_add_devices(wm8994->dev, 0,
338*4882a593Smuzhiyun wm8994_regulator_devs,
339*4882a593Smuzhiyun ARRAY_SIZE(wm8994_regulator_devs),
340*4882a593Smuzhiyun NULL, 0, NULL);
341*4882a593Smuzhiyun if (ret != 0) {
342*4882a593Smuzhiyun dev_err(wm8994->dev, "Failed to add children: %d\n", ret);
343*4882a593Smuzhiyun goto err;
344*4882a593Smuzhiyun }
345*4882a593Smuzhiyun
346*4882a593Smuzhiyun switch (wm8994->type) {
347*4882a593Smuzhiyun case WM1811:
348*4882a593Smuzhiyun wm8994->num_supplies = ARRAY_SIZE(wm1811_main_supplies);
349*4882a593Smuzhiyun break;
350*4882a593Smuzhiyun case WM8994:
351*4882a593Smuzhiyun wm8994->num_supplies = ARRAY_SIZE(wm8994_main_supplies);
352*4882a593Smuzhiyun break;
353*4882a593Smuzhiyun case WM8958:
354*4882a593Smuzhiyun wm8994->num_supplies = ARRAY_SIZE(wm8958_main_supplies);
355*4882a593Smuzhiyun break;
356*4882a593Smuzhiyun default:
357*4882a593Smuzhiyun BUG();
358*4882a593Smuzhiyun goto err;
359*4882a593Smuzhiyun }
360*4882a593Smuzhiyun
361*4882a593Smuzhiyun wm8994->supplies = devm_kcalloc(wm8994->dev,
362*4882a593Smuzhiyun wm8994->num_supplies,
363*4882a593Smuzhiyun sizeof(struct regulator_bulk_data),
364*4882a593Smuzhiyun GFP_KERNEL);
365*4882a593Smuzhiyun if (!wm8994->supplies) {
366*4882a593Smuzhiyun ret = -ENOMEM;
367*4882a593Smuzhiyun goto err;
368*4882a593Smuzhiyun }
369*4882a593Smuzhiyun
370*4882a593Smuzhiyun switch (wm8994->type) {
371*4882a593Smuzhiyun case WM1811:
372*4882a593Smuzhiyun for (i = 0; i < ARRAY_SIZE(wm1811_main_supplies); i++)
373*4882a593Smuzhiyun wm8994->supplies[i].supply = wm1811_main_supplies[i];
374*4882a593Smuzhiyun break;
375*4882a593Smuzhiyun case WM8994:
376*4882a593Smuzhiyun for (i = 0; i < ARRAY_SIZE(wm8994_main_supplies); i++)
377*4882a593Smuzhiyun wm8994->supplies[i].supply = wm8994_main_supplies[i];
378*4882a593Smuzhiyun break;
379*4882a593Smuzhiyun case WM8958:
380*4882a593Smuzhiyun for (i = 0; i < ARRAY_SIZE(wm8958_main_supplies); i++)
381*4882a593Smuzhiyun wm8994->supplies[i].supply = wm8958_main_supplies[i];
382*4882a593Smuzhiyun break;
383*4882a593Smuzhiyun default:
384*4882a593Smuzhiyun BUG();
385*4882a593Smuzhiyun goto err;
386*4882a593Smuzhiyun }
387*4882a593Smuzhiyun
388*4882a593Smuzhiyun /*
389*4882a593Smuzhiyun * Can't use devres helper here as some of the supplies are provided by
390*4882a593Smuzhiyun * wm8994->dev's children (regulators) and those regulators are
391*4882a593Smuzhiyun * unregistered by the devres core before the supplies are freed.
392*4882a593Smuzhiyun */
393*4882a593Smuzhiyun ret = regulator_bulk_get(wm8994->dev, wm8994->num_supplies,
394*4882a593Smuzhiyun wm8994->supplies);
395*4882a593Smuzhiyun if (ret != 0) {
396*4882a593Smuzhiyun if (ret != -EPROBE_DEFER)
397*4882a593Smuzhiyun dev_err(wm8994->dev, "Failed to get supplies: %d\n",
398*4882a593Smuzhiyun ret);
399*4882a593Smuzhiyun goto err;
400*4882a593Smuzhiyun }
401*4882a593Smuzhiyun
402*4882a593Smuzhiyun ret = regulator_bulk_enable(wm8994->num_supplies, wm8994->supplies);
403*4882a593Smuzhiyun if (ret != 0) {
404*4882a593Smuzhiyun dev_err(wm8994->dev, "Failed to enable supplies: %d\n", ret);
405*4882a593Smuzhiyun goto err_regulator_free;
406*4882a593Smuzhiyun }
407*4882a593Smuzhiyun
408*4882a593Smuzhiyun ret = wm8994_reg_read(wm8994, WM8994_SOFTWARE_RESET);
409*4882a593Smuzhiyun if (ret < 0) {
410*4882a593Smuzhiyun dev_err(wm8994->dev, "Failed to read ID register\n");
411*4882a593Smuzhiyun goto err_enable;
412*4882a593Smuzhiyun }
413*4882a593Smuzhiyun switch (ret) {
414*4882a593Smuzhiyun case 0x1811:
415*4882a593Smuzhiyun devname = "WM1811";
416*4882a593Smuzhiyun if (wm8994->type != WM1811)
417*4882a593Smuzhiyun dev_warn(wm8994->dev, "Device registered as type %d\n",
418*4882a593Smuzhiyun wm8994->type);
419*4882a593Smuzhiyun wm8994->type = WM1811;
420*4882a593Smuzhiyun break;
421*4882a593Smuzhiyun case 0x8994:
422*4882a593Smuzhiyun devname = "WM8994";
423*4882a593Smuzhiyun if (wm8994->type != WM8994)
424*4882a593Smuzhiyun dev_warn(wm8994->dev, "Device registered as type %d\n",
425*4882a593Smuzhiyun wm8994->type);
426*4882a593Smuzhiyun wm8994->type = WM8994;
427*4882a593Smuzhiyun break;
428*4882a593Smuzhiyun case 0x8958:
429*4882a593Smuzhiyun devname = "WM8958";
430*4882a593Smuzhiyun if (wm8994->type != WM8958)
431*4882a593Smuzhiyun dev_warn(wm8994->dev, "Device registered as type %d\n",
432*4882a593Smuzhiyun wm8994->type);
433*4882a593Smuzhiyun wm8994->type = WM8958;
434*4882a593Smuzhiyun break;
435*4882a593Smuzhiyun default:
436*4882a593Smuzhiyun dev_err(wm8994->dev, "Device is not a WM8994, ID is %x\n",
437*4882a593Smuzhiyun ret);
438*4882a593Smuzhiyun ret = -EINVAL;
439*4882a593Smuzhiyun goto err_enable;
440*4882a593Smuzhiyun }
441*4882a593Smuzhiyun
442*4882a593Smuzhiyun ret = wm8994_reg_read(wm8994, WM8994_CHIP_REVISION);
443*4882a593Smuzhiyun if (ret < 0) {
444*4882a593Smuzhiyun dev_err(wm8994->dev, "Failed to read revision register: %d\n",
445*4882a593Smuzhiyun ret);
446*4882a593Smuzhiyun goto err_enable;
447*4882a593Smuzhiyun }
448*4882a593Smuzhiyun wm8994->revision = ret & WM8994_CHIP_REV_MASK;
449*4882a593Smuzhiyun wm8994->cust_id = (ret & WM8994_CUST_ID_MASK) >> WM8994_CUST_ID_SHIFT;
450*4882a593Smuzhiyun
451*4882a593Smuzhiyun switch (wm8994->type) {
452*4882a593Smuzhiyun case WM8994:
453*4882a593Smuzhiyun switch (wm8994->revision) {
454*4882a593Smuzhiyun case 0:
455*4882a593Smuzhiyun case 1:
456*4882a593Smuzhiyun dev_warn(wm8994->dev,
457*4882a593Smuzhiyun "revision %c not fully supported\n",
458*4882a593Smuzhiyun 'A' + wm8994->revision);
459*4882a593Smuzhiyun break;
460*4882a593Smuzhiyun case 2:
461*4882a593Smuzhiyun case 3:
462*4882a593Smuzhiyun default:
463*4882a593Smuzhiyun regmap_patch = wm8994_revc_patch;
464*4882a593Smuzhiyun patch_regs = ARRAY_SIZE(wm8994_revc_patch);
465*4882a593Smuzhiyun break;
466*4882a593Smuzhiyun }
467*4882a593Smuzhiyun break;
468*4882a593Smuzhiyun
469*4882a593Smuzhiyun case WM8958:
470*4882a593Smuzhiyun switch (wm8994->revision) {
471*4882a593Smuzhiyun case 0:
472*4882a593Smuzhiyun regmap_patch = wm8958_reva_patch;
473*4882a593Smuzhiyun patch_regs = ARRAY_SIZE(wm8958_reva_patch);
474*4882a593Smuzhiyun break;
475*4882a593Smuzhiyun default:
476*4882a593Smuzhiyun break;
477*4882a593Smuzhiyun }
478*4882a593Smuzhiyun break;
479*4882a593Smuzhiyun
480*4882a593Smuzhiyun case WM1811:
481*4882a593Smuzhiyun /* Revision C did not change the relevant layer */
482*4882a593Smuzhiyun if (wm8994->revision > 1)
483*4882a593Smuzhiyun wm8994->revision++;
484*4882a593Smuzhiyun
485*4882a593Smuzhiyun regmap_patch = wm1811_reva_patch;
486*4882a593Smuzhiyun patch_regs = ARRAY_SIZE(wm1811_reva_patch);
487*4882a593Smuzhiyun break;
488*4882a593Smuzhiyun
489*4882a593Smuzhiyun default:
490*4882a593Smuzhiyun break;
491*4882a593Smuzhiyun }
492*4882a593Smuzhiyun
493*4882a593Smuzhiyun dev_info(wm8994->dev, "%s revision %c CUST_ID %02x\n", devname,
494*4882a593Smuzhiyun 'A' + wm8994->revision, wm8994->cust_id);
495*4882a593Smuzhiyun
496*4882a593Smuzhiyun switch (wm8994->type) {
497*4882a593Smuzhiyun case WM1811:
498*4882a593Smuzhiyun regmap_config = &wm1811_regmap_config;
499*4882a593Smuzhiyun break;
500*4882a593Smuzhiyun case WM8994:
501*4882a593Smuzhiyun regmap_config = &wm8994_regmap_config;
502*4882a593Smuzhiyun break;
503*4882a593Smuzhiyun case WM8958:
504*4882a593Smuzhiyun regmap_config = &wm8958_regmap_config;
505*4882a593Smuzhiyun break;
506*4882a593Smuzhiyun default:
507*4882a593Smuzhiyun dev_err(wm8994->dev, "Unknown device type %d\n", wm8994->type);
508*4882a593Smuzhiyun ret = -EINVAL;
509*4882a593Smuzhiyun goto err_enable;
510*4882a593Smuzhiyun }
511*4882a593Smuzhiyun
512*4882a593Smuzhiyun ret = regmap_reinit_cache(wm8994->regmap, regmap_config);
513*4882a593Smuzhiyun if (ret != 0) {
514*4882a593Smuzhiyun dev_err(wm8994->dev, "Failed to reinit register cache: %d\n",
515*4882a593Smuzhiyun ret);
516*4882a593Smuzhiyun goto err_enable;
517*4882a593Smuzhiyun }
518*4882a593Smuzhiyun
519*4882a593Smuzhiyun /* Explicitly put the device into reset in case regulators
520*4882a593Smuzhiyun * don't get disabled in order to ensure we know the device
521*4882a593Smuzhiyun * state.
522*4882a593Smuzhiyun */
523*4882a593Smuzhiyun ret = wm8994_reg_write(wm8994, WM8994_SOFTWARE_RESET,
524*4882a593Smuzhiyun wm8994_reg_read(wm8994, WM8994_SOFTWARE_RESET));
525*4882a593Smuzhiyun if (ret != 0) {
526*4882a593Smuzhiyun dev_err(wm8994->dev, "Failed to reset device: %d\n", ret);
527*4882a593Smuzhiyun goto err_enable;
528*4882a593Smuzhiyun }
529*4882a593Smuzhiyun
530*4882a593Smuzhiyun if (regmap_patch) {
531*4882a593Smuzhiyun ret = regmap_register_patch(wm8994->regmap, regmap_patch,
532*4882a593Smuzhiyun patch_regs);
533*4882a593Smuzhiyun if (ret != 0) {
534*4882a593Smuzhiyun dev_err(wm8994->dev, "Failed to register patch: %d\n",
535*4882a593Smuzhiyun ret);
536*4882a593Smuzhiyun goto err_enable;
537*4882a593Smuzhiyun }
538*4882a593Smuzhiyun }
539*4882a593Smuzhiyun
540*4882a593Smuzhiyun wm8994->irq_base = pdata->irq_base;
541*4882a593Smuzhiyun wm8994->gpio_base = pdata->gpio_base;
542*4882a593Smuzhiyun
543*4882a593Smuzhiyun /* GPIO configuration is only applied if it's non-zero */
544*4882a593Smuzhiyun for (i = 0; i < ARRAY_SIZE(pdata->gpio_defaults); i++) {
545*4882a593Smuzhiyun if (pdata->gpio_defaults[i]) {
546*4882a593Smuzhiyun wm8994_set_bits(wm8994, WM8994_GPIO_1 + i,
547*4882a593Smuzhiyun 0xffff, pdata->gpio_defaults[i]);
548*4882a593Smuzhiyun }
549*4882a593Smuzhiyun }
550*4882a593Smuzhiyun
551*4882a593Smuzhiyun wm8994->ldo_ena_always_driven = pdata->ldo_ena_always_driven;
552*4882a593Smuzhiyun
553*4882a593Smuzhiyun if (pdata->spkmode_pu)
554*4882a593Smuzhiyun pulls |= WM8994_SPKMODE_PU;
555*4882a593Smuzhiyun if (pdata->csnaddr_pd)
556*4882a593Smuzhiyun pulls |= WM8994_CSNADDR_PD;
557*4882a593Smuzhiyun
558*4882a593Smuzhiyun /* Disable unneeded pulls */
559*4882a593Smuzhiyun wm8994_set_bits(wm8994, WM8994_PULL_CONTROL_2,
560*4882a593Smuzhiyun WM8994_LDO1ENA_PD | WM8994_LDO2ENA_PD |
561*4882a593Smuzhiyun WM8994_SPKMODE_PU | WM8994_CSNADDR_PD,
562*4882a593Smuzhiyun pulls);
563*4882a593Smuzhiyun
564*4882a593Smuzhiyun /* In some system designs where the regulators are not in use,
565*4882a593Smuzhiyun * we can achieve a small reduction in leakage currents by
566*4882a593Smuzhiyun * floating LDO outputs. This bit makes no difference if the
567*4882a593Smuzhiyun * LDOs are enabled, it only affects cases where the LDOs were
568*4882a593Smuzhiyun * in operation and are then disabled.
569*4882a593Smuzhiyun */
570*4882a593Smuzhiyun for (i = 0; i < WM8994_NUM_LDO_REGS; i++) {
571*4882a593Smuzhiyun if (wm8994_ldo_in_use(pdata, i))
572*4882a593Smuzhiyun wm8994_set_bits(wm8994, WM8994_LDO_1 + i,
573*4882a593Smuzhiyun WM8994_LDO1_DISCH, WM8994_LDO1_DISCH);
574*4882a593Smuzhiyun else
575*4882a593Smuzhiyun wm8994_set_bits(wm8994, WM8994_LDO_1 + i,
576*4882a593Smuzhiyun WM8994_LDO1_DISCH, 0);
577*4882a593Smuzhiyun }
578*4882a593Smuzhiyun
579*4882a593Smuzhiyun wm8994_irq_init(wm8994);
580*4882a593Smuzhiyun
581*4882a593Smuzhiyun ret = mfd_add_devices(wm8994->dev, -1,
582*4882a593Smuzhiyun wm8994_devs, ARRAY_SIZE(wm8994_devs),
583*4882a593Smuzhiyun NULL, 0, NULL);
584*4882a593Smuzhiyun if (ret != 0) {
585*4882a593Smuzhiyun dev_err(wm8994->dev, "Failed to add children: %d\n", ret);
586*4882a593Smuzhiyun goto err_irq;
587*4882a593Smuzhiyun }
588*4882a593Smuzhiyun
589*4882a593Smuzhiyun pm_runtime_set_active(wm8994->dev);
590*4882a593Smuzhiyun pm_runtime_enable(wm8994->dev);
591*4882a593Smuzhiyun pm_runtime_idle(wm8994->dev);
592*4882a593Smuzhiyun
593*4882a593Smuzhiyun return 0;
594*4882a593Smuzhiyun
595*4882a593Smuzhiyun err_irq:
596*4882a593Smuzhiyun wm8994_irq_exit(wm8994);
597*4882a593Smuzhiyun err_enable:
598*4882a593Smuzhiyun regulator_bulk_disable(wm8994->num_supplies,
599*4882a593Smuzhiyun wm8994->supplies);
600*4882a593Smuzhiyun err_regulator_free:
601*4882a593Smuzhiyun regulator_bulk_free(wm8994->num_supplies, wm8994->supplies);
602*4882a593Smuzhiyun err:
603*4882a593Smuzhiyun mfd_remove_devices(wm8994->dev);
604*4882a593Smuzhiyun return ret;
605*4882a593Smuzhiyun }
606*4882a593Smuzhiyun
wm8994_device_exit(struct wm8994 * wm8994)607*4882a593Smuzhiyun static void wm8994_device_exit(struct wm8994 *wm8994)
608*4882a593Smuzhiyun {
609*4882a593Smuzhiyun pm_runtime_get_sync(wm8994->dev);
610*4882a593Smuzhiyun pm_runtime_disable(wm8994->dev);
611*4882a593Smuzhiyun pm_runtime_put_noidle(wm8994->dev);
612*4882a593Smuzhiyun wm8994_irq_exit(wm8994);
613*4882a593Smuzhiyun regulator_bulk_disable(wm8994->num_supplies, wm8994->supplies);
614*4882a593Smuzhiyun regulator_bulk_free(wm8994->num_supplies, wm8994->supplies);
615*4882a593Smuzhiyun mfd_remove_devices(wm8994->dev);
616*4882a593Smuzhiyun }
617*4882a593Smuzhiyun
618*4882a593Smuzhiyun static const struct of_device_id wm8994_of_match[] = {
619*4882a593Smuzhiyun { .compatible = "wlf,wm1811", .data = (void *)WM1811 },
620*4882a593Smuzhiyun { .compatible = "wlf,wm8994", .data = (void *)WM8994 },
621*4882a593Smuzhiyun { .compatible = "wlf,wm8958", .data = (void *)WM8958 },
622*4882a593Smuzhiyun { }
623*4882a593Smuzhiyun };
624*4882a593Smuzhiyun MODULE_DEVICE_TABLE(of, wm8994_of_match);
625*4882a593Smuzhiyun
wm8994_i2c_probe(struct i2c_client * i2c,const struct i2c_device_id * id)626*4882a593Smuzhiyun static int wm8994_i2c_probe(struct i2c_client *i2c,
627*4882a593Smuzhiyun const struct i2c_device_id *id)
628*4882a593Smuzhiyun {
629*4882a593Smuzhiyun const struct of_device_id *of_id;
630*4882a593Smuzhiyun struct wm8994 *wm8994;
631*4882a593Smuzhiyun int ret;
632*4882a593Smuzhiyun
633*4882a593Smuzhiyun wm8994 = devm_kzalloc(&i2c->dev, sizeof(struct wm8994), GFP_KERNEL);
634*4882a593Smuzhiyun if (wm8994 == NULL)
635*4882a593Smuzhiyun return -ENOMEM;
636*4882a593Smuzhiyun
637*4882a593Smuzhiyun i2c_set_clientdata(i2c, wm8994);
638*4882a593Smuzhiyun wm8994->dev = &i2c->dev;
639*4882a593Smuzhiyun wm8994->irq = i2c->irq;
640*4882a593Smuzhiyun
641*4882a593Smuzhiyun if (i2c->dev.of_node) {
642*4882a593Smuzhiyun of_id = of_match_device(wm8994_of_match, &i2c->dev);
643*4882a593Smuzhiyun if (of_id)
644*4882a593Smuzhiyun wm8994->type = (enum wm8994_type)of_id->data;
645*4882a593Smuzhiyun } else {
646*4882a593Smuzhiyun wm8994->type = id->driver_data;
647*4882a593Smuzhiyun }
648*4882a593Smuzhiyun
649*4882a593Smuzhiyun wm8994->regmap = devm_regmap_init_i2c(i2c, &wm8994_base_regmap_config);
650*4882a593Smuzhiyun if (IS_ERR(wm8994->regmap)) {
651*4882a593Smuzhiyun ret = PTR_ERR(wm8994->regmap);
652*4882a593Smuzhiyun dev_err(wm8994->dev, "Failed to allocate register map: %d\n",
653*4882a593Smuzhiyun ret);
654*4882a593Smuzhiyun return ret;
655*4882a593Smuzhiyun }
656*4882a593Smuzhiyun
657*4882a593Smuzhiyun return wm8994_device_init(wm8994, i2c->irq);
658*4882a593Smuzhiyun }
659*4882a593Smuzhiyun
wm8994_i2c_remove(struct i2c_client * i2c)660*4882a593Smuzhiyun static int wm8994_i2c_remove(struct i2c_client *i2c)
661*4882a593Smuzhiyun {
662*4882a593Smuzhiyun struct wm8994 *wm8994 = i2c_get_clientdata(i2c);
663*4882a593Smuzhiyun
664*4882a593Smuzhiyun wm8994_device_exit(wm8994);
665*4882a593Smuzhiyun
666*4882a593Smuzhiyun return 0;
667*4882a593Smuzhiyun }
668*4882a593Smuzhiyun
669*4882a593Smuzhiyun static const struct i2c_device_id wm8994_i2c_id[] = {
670*4882a593Smuzhiyun { "wm1811", WM1811 },
671*4882a593Smuzhiyun { "wm1811a", WM1811 },
672*4882a593Smuzhiyun { "wm8994", WM8994 },
673*4882a593Smuzhiyun { "wm8958", WM8958 },
674*4882a593Smuzhiyun { }
675*4882a593Smuzhiyun };
676*4882a593Smuzhiyun MODULE_DEVICE_TABLE(i2c, wm8994_i2c_id);
677*4882a593Smuzhiyun
678*4882a593Smuzhiyun static const struct dev_pm_ops wm8994_pm_ops = {
679*4882a593Smuzhiyun SET_RUNTIME_PM_OPS(wm8994_suspend, wm8994_resume, NULL)
680*4882a593Smuzhiyun };
681*4882a593Smuzhiyun
682*4882a593Smuzhiyun static struct i2c_driver wm8994_i2c_driver = {
683*4882a593Smuzhiyun .driver = {
684*4882a593Smuzhiyun .name = "wm8994",
685*4882a593Smuzhiyun .pm = &wm8994_pm_ops,
686*4882a593Smuzhiyun .of_match_table = of_match_ptr(wm8994_of_match),
687*4882a593Smuzhiyun },
688*4882a593Smuzhiyun .probe = wm8994_i2c_probe,
689*4882a593Smuzhiyun .remove = wm8994_i2c_remove,
690*4882a593Smuzhiyun .id_table = wm8994_i2c_id,
691*4882a593Smuzhiyun };
692*4882a593Smuzhiyun
693*4882a593Smuzhiyun module_i2c_driver(wm8994_i2c_driver);
694*4882a593Smuzhiyun
695*4882a593Smuzhiyun MODULE_DESCRIPTION("Core support for the WM8994 audio CODEC");
696*4882a593Smuzhiyun MODULE_LICENSE("GPL");
697*4882a593Smuzhiyun MODULE_AUTHOR("Mark Brown <broonie@opensource.wolfsonmicro.com>");
698*4882a593Smuzhiyun MODULE_SOFTDEP("pre: wm8994_regulator");
699