aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorMark Brown <broonie@opensource.wolfsonmicro.com>2010-02-03 06:51:42 -0500
committerMark Brown <broonie@opensource.wolfsonmicro.com>2010-02-04 05:41:09 -0500
commitb37e399bfc7fcb5b523e3e2e74686c8cc95c0cba (patch)
treeac502e0469dbd048699cf71e0e07a7dad3bd902b
parent3bf6e4217e3c69438f6dc41a009664107eb27ab1 (diff)
ASoC: Initial WM8993 regulator API hookup
At the minute the regulators are simply enabled for the entire lifetime of the device. Signed-off-by: Mark Brown <broonie@opensource.wolfsonmicro.com> Acked-by: Liam Girdwood <lrg@slimlogic.co.uk>
-rw-r--r--sound/soc/codecs/wm8993.c41
1 files changed, 38 insertions, 3 deletions
diff --git a/sound/soc/codecs/wm8993.c b/sound/soc/codecs/wm8993.c
index 3c9336cd4eeb..e97b3f45b24b 100644
--- a/sound/soc/codecs/wm8993.c
+++ b/sound/soc/codecs/wm8993.c
@@ -16,6 +16,7 @@
16#include <linux/delay.h> 16#include <linux/delay.h>
17#include <linux/pm.h> 17#include <linux/pm.h>
18#include <linux/i2c.h> 18#include <linux/i2c.h>
19#include <linux/regulator/consumer.h>
19#include <linux/spi/spi.h> 20#include <linux/spi/spi.h>
20#include <sound/core.h> 21#include <sound/core.h>
21#include <sound/pcm.h> 22#include <sound/pcm.h>
@@ -29,6 +30,16 @@
29#include "wm8993.h" 30#include "wm8993.h"
30#include "wm_hubs.h" 31#include "wm_hubs.h"
31 32
33#define WM8993_NUM_SUPPLIES 6
34static const char *wm8993_supply_names[WM8993_NUM_SUPPLIES] = {
35 "DCVDD",
36 "DBVDD",
37 "AVDD1",
38 "AVDD2",
39 "CPVDD",
40 "SPKVDD",
41};
42
32static u16 wm8993_reg_defaults[WM8993_REGISTER_COUNT] = { 43static u16 wm8993_reg_defaults[WM8993_REGISTER_COUNT] = {
33 0x8993, /* R0 - Software Reset */ 44 0x8993, /* R0 - Software Reset */
34 0x0000, /* R1 - Power Management (1) */ 45 0x0000, /* R1 - Power Management (1) */
@@ -215,6 +226,7 @@ static struct {
215struct wm8993_priv { 226struct wm8993_priv {
216 struct wm_hubs_data hubs_data; 227 struct wm_hubs_data hubs_data;
217 u16 reg_cache[WM8993_REGISTER_COUNT]; 228 u16 reg_cache[WM8993_REGISTER_COUNT];
229 struct regulator_bulk_data supplies[WM8993_NUM_SUPPLIES];
218 struct wm8993_platform_data pdata; 230 struct wm8993_platform_data pdata;
219 struct snd_soc_codec codec; 231 struct snd_soc_codec codec;
220 int master; 232 int master;
@@ -1496,6 +1508,7 @@ static int wm8993_i2c_probe(struct i2c_client *i2c,
1496 struct snd_soc_codec *codec; 1508 struct snd_soc_codec *codec;
1497 unsigned int val; 1509 unsigned int val;
1498 int ret; 1510 int ret;
1511 int i;
1499 1512
1500 if (wm8993_codec) { 1513 if (wm8993_codec) {
1501 dev_err(&i2c->dev, "A WM8993 is already registered\n"); 1514 dev_err(&i2c->dev, "A WM8993 is already registered\n");
@@ -1543,16 +1556,33 @@ static int wm8993_i2c_probe(struct i2c_client *i2c,
1543 1556
1544 codec->dev = &i2c->dev; 1557 codec->dev = &i2c->dev;
1545 1558
1559 for (i = 0; i < ARRAY_SIZE(wm8993->supplies); i++)
1560 wm8993->supplies[i].supply = wm8993_supply_names[i];
1561
1562 ret = regulator_bulk_get(codec->dev, ARRAY_SIZE(wm8993->supplies),
1563 wm8993->supplies);
1564 if (ret != 0) {
1565 dev_err(codec->dev, "Failed to request supplies: %d\n", ret);
1566 goto err;
1567 }
1568
1569 ret = regulator_bulk_enable(ARRAY_SIZE(wm8993->supplies),
1570 wm8993->supplies);
1571 if (ret != 0) {
1572 dev_err(codec->dev, "Failed to enable supplies: %d\n", ret);
1573 goto err_get;
1574 }
1575
1546 val = snd_soc_read(codec, WM8993_SOFTWARE_RESET); 1576 val = snd_soc_read(codec, WM8993_SOFTWARE_RESET);
1547 if (val != wm8993_reg_defaults[WM8993_SOFTWARE_RESET]) { 1577 if (val != wm8993_reg_defaults[WM8993_SOFTWARE_RESET]) {
1548 dev_err(codec->dev, "Invalid ID register value %x\n", val); 1578 dev_err(codec->dev, "Invalid ID register value %x\n", val);
1549 ret = -EINVAL; 1579 ret = -EINVAL;
1550 goto err; 1580 goto err_enable;
1551 } 1581 }
1552 1582
1553 ret = snd_soc_write(codec, WM8993_SOFTWARE_RESET, 0xffff); 1583 ret = snd_soc_write(codec, WM8993_SOFTWARE_RESET, 0xffff);
1554 if (ret != 0) 1584 if (ret != 0)
1555 goto err; 1585 goto err_enable;
1556 1586
1557 /* By default we're using the output mixers */ 1587 /* By default we're using the output mixers */
1558 wm8993->class_w_users = 2; 1588 wm8993->class_w_users = 2;
@@ -1582,7 +1612,7 @@ static int wm8993_i2c_probe(struct i2c_client *i2c,
1582 1612
1583 ret = wm8993_set_bias_level(codec, SND_SOC_BIAS_STANDBY); 1613 ret = wm8993_set_bias_level(codec, SND_SOC_BIAS_STANDBY);
1584 if (ret != 0) 1614 if (ret != 0)
1585 goto err; 1615 goto err_enable;
1586 1616
1587 wm8993_dai.dev = codec->dev; 1617 wm8993_dai.dev = codec->dev;
1588 1618
@@ -1596,6 +1626,10 @@ static int wm8993_i2c_probe(struct i2c_client *i2c,
1596 1626
1597err_bias: 1627err_bias:
1598 wm8993_set_bias_level(codec, SND_SOC_BIAS_OFF); 1628 wm8993_set_bias_level(codec, SND_SOC_BIAS_OFF);
1629err_enable:
1630 regulator_bulk_disable(ARRAY_SIZE(wm8993->supplies), wm8993->supplies);
1631err_get:
1632 regulator_bulk_free(ARRAY_SIZE(wm8993->supplies), wm8993->supplies);
1599err: 1633err:
1600 wm8993_codec = NULL; 1634 wm8993_codec = NULL;
1601 kfree(wm8993); 1635 kfree(wm8993);
@@ -1610,6 +1644,7 @@ static int wm8993_i2c_remove(struct i2c_client *client)
1610 snd_soc_unregister_dai(&wm8993_dai); 1644 snd_soc_unregister_dai(&wm8993_dai);
1611 1645
1612 wm8993_set_bias_level(&wm8993->codec, SND_SOC_BIAS_OFF); 1646 wm8993_set_bias_level(&wm8993->codec, SND_SOC_BIAS_OFF);
1647 regulator_bulk_free(ARRAY_SIZE(wm8993->supplies), wm8993->supplies);
1613 kfree(wm8993); 1648 kfree(wm8993);
1614 1649
1615 return 0; 1650 return 0;