aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorMark Brown <broonie@opensource.wolfsonmicro.com>2012-01-21 10:41:48 -0500
committerMark Brown <broonie@opensource.wolfsonmicro.com>2012-01-21 16:15:42 -0500
commit411a3450c9539043c794a5f4a6bdb03bb040670a (patch)
treeff409f1904d280c7d84d0a01b1a20f15c6eff9f1
parent9f8cbae4163ab132cd7a56385341efdd41fcd429 (diff)
ASoC: wm8985: Convert to direct regmap API usage
Signed-off-by: Mark Brown <broonie@opensource.wolfsonmicro.com>
-rw-r--r--sound/soc/codecs/wm8985.c253
1 files changed, 177 insertions, 76 deletions
diff --git a/sound/soc/codecs/wm8985.c b/sound/soc/codecs/wm8985.c
index bbe19b2ae516..14f666398d0c 100644
--- a/sound/soc/codecs/wm8985.c
+++ b/sound/soc/codecs/wm8985.c
@@ -19,6 +19,7 @@
19#include <linux/delay.h> 19#include <linux/delay.h>
20#include <linux/pm.h> 20#include <linux/pm.h>
21#include <linux/i2c.h> 21#include <linux/i2c.h>
22#include <linux/regmap.h>
22#include <linux/regulator/consumer.h> 23#include <linux/regulator/consumer.h>
23#include <linux/spi/spi.h> 24#include <linux/spi/spi.h>
24#include <linux/slab.h> 25#include <linux/slab.h>
@@ -39,73 +40,127 @@ static const char *wm8985_supply_names[WM8985_NUM_SUPPLIES] = {
39 "AVDD2" 40 "AVDD2"
40}; 41};
41 42
42static const u16 wm8985_reg_defs[] = { 43static const struct reg_default wm8985_reg_defaults[] = {
43 0x0000, /* R0 - Software Reset */ 44 { 1, 0x0000 }, /* R1 - Power management 1 */
44 0x0000, /* R1 - Power management 1 */ 45 { 2, 0x0000 }, /* R2 - Power management 2 */
45 0x0000, /* R2 - Power management 2 */ 46 { 3, 0x0000 }, /* R3 - Power management 3 */
46 0x0000, /* R3 - Power management 3 */ 47 { 4, 0x0050 }, /* R4 - Audio Interface */
47 0x0050, /* R4 - Audio Interface */ 48 { 5, 0x0000 }, /* R5 - Companding control */
48 0x0000, /* R5 - Companding control */ 49 { 6, 0x0140 }, /* R6 - Clock Gen control */
49 0x0140, /* R6 - Clock Gen control */ 50 { 7, 0x0000 }, /* R7 - Additional control */
50 0x0000, /* R7 - Additional control */ 51 { 8, 0x0000 }, /* R8 - GPIO Control */
51 0x0000, /* R8 - GPIO Control */ 52 { 9, 0x0000 }, /* R9 - Jack Detect Control 1 */
52 0x0000, /* R9 - Jack Detect Control 1 */ 53 { 10, 0x0000 }, /* R10 - DAC Control */
53 0x0000, /* R10 - DAC Control */ 54 { 11, 0x00FF }, /* R11 - Left DAC digital Vol */
54 0x00FF, /* R11 - Left DAC digital Vol */ 55 { 12, 0x00FF }, /* R12 - Right DAC digital vol */
55 0x00FF, /* R12 - Right DAC digital vol */ 56 { 13, 0x0000 }, /* R13 - Jack Detect Control 2 */
56 0x0000, /* R13 - Jack Detect Control 2 */ 57 { 14, 0x0100 }, /* R14 - ADC Control */
57 0x0100, /* R14 - ADC Control */ 58 { 15, 0x00FF }, /* R15 - Left ADC Digital Vol */
58 0x00FF, /* R15 - Left ADC Digital Vol */ 59 { 16, 0x00FF }, /* R16 - Right ADC Digital Vol */
59 0x00FF, /* R16 - Right ADC Digital Vol */ 60 { 18, 0x012C }, /* R18 - EQ1 - low shelf */
60 0x0000, /* R17 */ 61 { 19, 0x002C }, /* R19 - EQ2 - peak 1 */
61 0x012C, /* R18 - EQ1 - low shelf */ 62 { 20, 0x002C }, /* R20 - EQ3 - peak 2 */
62 0x002C, /* R19 - EQ2 - peak 1 */ 63 { 21, 0x002C }, /* R21 - EQ4 - peak 3 */
63 0x002C, /* R20 - EQ3 - peak 2 */ 64 { 22, 0x002C }, /* R22 - EQ5 - high shelf */
64 0x002C, /* R21 - EQ4 - peak 3 */ 65 { 24, 0x0032 }, /* R24 - DAC Limiter 1 */
65 0x002C, /* R22 - EQ5 - high shelf */ 66 { 25, 0x0000 }, /* R25 - DAC Limiter 2 */
66 0x0000, /* R23 */ 67 { 27, 0x0000 }, /* R27 - Notch Filter 1 */
67 0x0032, /* R24 - DAC Limiter 1 */ 68 { 28, 0x0000 }, /* R28 - Notch Filter 2 */
68 0x0000, /* R25 - DAC Limiter 2 */ 69 { 29, 0x0000 }, /* R29 - Notch Filter 3 */
69 0x0000, /* R26 */ 70 { 30, 0x0000 }, /* R30 - Notch Filter 4 */
70 0x0000, /* R27 - Notch Filter 1 */ 71 { 32, 0x0038 }, /* R32 - ALC control 1 */
71 0x0000, /* R28 - Notch Filter 2 */ 72 { 33, 0x000B }, /* R33 - ALC control 2 */
72 0x0000, /* R29 - Notch Filter 3 */ 73 { 34, 0x0032 }, /* R34 - ALC control 3 */
73 0x0000, /* R30 - Notch Filter 4 */ 74 { 35, 0x0000 }, /* R35 - Noise Gate */
74 0x0000, /* R31 */ 75 { 36, 0x0008 }, /* R36 - PLL N */
75 0x0038, /* R32 - ALC control 1 */ 76 { 37, 0x000C }, /* R37 - PLL K 1 */
76 0x000B, /* R33 - ALC control 2 */ 77 { 38, 0x0093 }, /* R38 - PLL K 2 */
77 0x0032, /* R34 - ALC control 3 */ 78 { 39, 0x00E9 }, /* R39 - PLL K 3 */
78 0x0000, /* R35 - Noise Gate */ 79 { 41, 0x0000 }, /* R41 - 3D control */
79 0x0008, /* R36 - PLL N */ 80 { 42, 0x0000 }, /* R42 - OUT4 to ADC */
80 0x000C, /* R37 - PLL K 1 */ 81 { 43, 0x0000 }, /* R43 - Beep control */
81 0x0093, /* R38 - PLL K 2 */ 82 { 44, 0x0033 }, /* R44 - Input ctrl */
82 0x00E9, /* R39 - PLL K 3 */ 83 { 45, 0x0010 }, /* R45 - Left INP PGA gain ctrl */
83 0x0000, /* R40 */ 84 { 46, 0x0010 }, /* R46 - Right INP PGA gain ctrl */
84 0x0000, /* R41 - 3D control */ 85 { 47, 0x0100 }, /* R47 - Left ADC BOOST ctrl */
85 0x0000, /* R42 - OUT4 to ADC */ 86 { 48, 0x0100 }, /* R48 - Right ADC BOOST ctrl */
86 0x0000, /* R43 - Beep control */ 87 { 49, 0x0002 }, /* R49 - Output ctrl */
87 0x0033, /* R44 - Input ctrl */ 88 { 50, 0x0001 }, /* R50 - Left mixer ctrl */
88 0x0010, /* R45 - Left INP PGA gain ctrl */ 89 { 51, 0x0001 }, /* R51 - Right mixer ctrl */
89 0x0010, /* R46 - Right INP PGA gain ctrl */ 90 { 52, 0x0039 }, /* R52 - LOUT1 (HP) volume ctrl */
90 0x0100, /* R47 - Left ADC BOOST ctrl */ 91 { 53, 0x0039 }, /* R53 - ROUT1 (HP) volume ctrl */
91 0x0100, /* R48 - Right ADC BOOST ctrl */ 92 { 54, 0x0039 }, /* R54 - LOUT2 (SPK) volume ctrl */
92 0x0002, /* R49 - Output ctrl */ 93 { 55, 0x0039 }, /* R55 - ROUT2 (SPK) volume ctrl */
93 0x0001, /* R50 - Left mixer ctrl */ 94 { 56, 0x0001 }, /* R56 - OUT3 mixer ctrl */
94 0x0001, /* R51 - Right mixer ctrl */ 95 { 57, 0x0001 }, /* R57 - OUT4 (MONO) mix ctrl */
95 0x0039, /* R52 - LOUT1 (HP) volume ctrl */ 96 { 60, 0x0004 }, /* R60 - OUTPUT ctrl */
96 0x0039, /* R53 - ROUT1 (HP) volume ctrl */ 97 { 61, 0x0000 }, /* R61 - BIAS CTRL */
97 0x0039, /* R54 - LOUT2 (SPK) volume ctrl */
98 0x0039, /* R55 - ROUT2 (SPK) volume ctrl */
99 0x0001, /* R56 - OUT3 mixer ctrl */
100 0x0001, /* R57 - OUT4 (MONO) mix ctrl */
101 0x0001, /* R58 */
102 0x0000, /* R59 */
103 0x0004, /* R60 - OUTPUT ctrl */
104 0x0000, /* R61 - BIAS CTRL */
105 0x0180, /* R62 */
106 0x0000 /* R63 */
107}; 98};
108 99
100static bool wm8985_writeable(struct device *dev, unsigned int reg)
101{
102 switch (reg) {
103 case WM8985_SOFTWARE_RESET:
104 case WM8985_POWER_MANAGEMENT_1:
105 case WM8985_POWER_MANAGEMENT_2:
106 case WM8985_POWER_MANAGEMENT_3:
107 case WM8985_AUDIO_INTERFACE:
108 case WM8985_COMPANDING_CONTROL:
109 case WM8985_CLOCK_GEN_CONTROL:
110 case WM8985_ADDITIONAL_CONTROL:
111 case WM8985_GPIO_CONTROL:
112 case WM8985_JACK_DETECT_CONTROL_1:
113 case WM8985_DAC_CONTROL:
114 case WM8985_LEFT_DAC_DIGITAL_VOL:
115 case WM8985_RIGHT_DAC_DIGITAL_VOL:
116 case WM8985_JACK_DETECT_CONTROL_2:
117 case WM8985_ADC_CONTROL:
118 case WM8985_LEFT_ADC_DIGITAL_VOL:
119 case WM8985_RIGHT_ADC_DIGITAL_VOL:
120 case WM8985_EQ1_LOW_SHELF:
121 case WM8985_EQ2_PEAK_1:
122 case WM8985_EQ3_PEAK_2:
123 case WM8985_EQ4_PEAK_3:
124 case WM8985_EQ5_HIGH_SHELF:
125 case WM8985_DAC_LIMITER_1:
126 case WM8985_DAC_LIMITER_2:
127 case WM8985_NOTCH_FILTER_1:
128 case WM8985_NOTCH_FILTER_2:
129 case WM8985_NOTCH_FILTER_3:
130 case WM8985_NOTCH_FILTER_4:
131 case WM8985_ALC_CONTROL_1:
132 case WM8985_ALC_CONTROL_2:
133 case WM8985_ALC_CONTROL_3:
134 case WM8985_NOISE_GATE:
135 case WM8985_PLL_N:
136 case WM8985_PLL_K_1:
137 case WM8985_PLL_K_2:
138 case WM8985_PLL_K_3:
139 case WM8985_3D_CONTROL:
140 case WM8985_OUT4_TO_ADC:
141 case WM8985_BEEP_CONTROL:
142 case WM8985_INPUT_CTRL:
143 case WM8985_LEFT_INP_PGA_GAIN_CTRL:
144 case WM8985_RIGHT_INP_PGA_GAIN_CTRL:
145 case WM8985_LEFT_ADC_BOOST_CTRL:
146 case WM8985_RIGHT_ADC_BOOST_CTRL:
147 case WM8985_OUTPUT_CTRL0:
148 case WM8985_LEFT_MIXER_CTRL:
149 case WM8985_RIGHT_MIXER_CTRL:
150 case WM8985_LOUT1_HP_VOLUME_CTRL:
151 case WM8985_ROUT1_HP_VOLUME_CTRL:
152 case WM8985_LOUT2_SPK_VOLUME_CTRL:
153 case WM8985_ROUT2_SPK_VOLUME_CTRL:
154 case WM8985_OUT3_MIXER_CTRL:
155 case WM8985_OUT4_MONO_MIX_CTRL:
156 case WM8985_OUTPUT_CTRL1:
157 case WM8985_BIAS_CTRL:
158 return true;
159 default:
160 return false;
161 }
162}
163
109/* 164/*
110 * latch bit 8 of these registers to ensure instant 165 * latch bit 8 of these registers to ensure instant
111 * volume updates 166 * volume updates
@@ -124,7 +179,7 @@ static const int volume_update_regs[] = {
124}; 179};
125 180
126struct wm8985_priv { 181struct wm8985_priv {
127 enum snd_soc_control_type control_type; 182 struct regmap *regmap;
128 struct regulator_bulk_data supplies[WM8985_NUM_SUPPLIES]; 183 struct regulator_bulk_data supplies[WM8985_NUM_SUPPLIES];
129 unsigned int sysclk; 184 unsigned int sysclk;
130 unsigned int bclk; 185 unsigned int bclk;
@@ -860,7 +915,7 @@ static int wm8985_set_bias_level(struct snd_soc_codec *codec,
860 return ret; 915 return ret;
861 } 916 }
862 917
863 snd_soc_cache_sync(codec); 918 regcache_sync(wm8985->regmap);
864 919
865 /* enable anti-pop features */ 920 /* enable anti-pop features */
866 snd_soc_update_bits(codec, WM8985_OUT4_TO_ADC, 921 snd_soc_update_bits(codec, WM8985_OUT4_TO_ADC,
@@ -903,7 +958,7 @@ static int wm8985_set_bias_level(struct snd_soc_codec *codec,
903 snd_soc_write(codec, WM8985_POWER_MANAGEMENT_2, 0); 958 snd_soc_write(codec, WM8985_POWER_MANAGEMENT_2, 0);
904 snd_soc_write(codec, WM8985_POWER_MANAGEMENT_3, 0); 959 snd_soc_write(codec, WM8985_POWER_MANAGEMENT_3, 0);
905 960
906 codec->cache_sync = 1; 961 regcache_mark_dirty(wm8985->regmap);
907 962
908 regulator_bulk_disable(ARRAY_SIZE(wm8985->supplies), 963 regulator_bulk_disable(ARRAY_SIZE(wm8985->supplies),
909 wm8985->supplies); 964 wm8985->supplies);
@@ -948,8 +1003,9 @@ static int wm8985_probe(struct snd_soc_codec *codec)
948 int ret; 1003 int ret;
949 1004
950 wm8985 = snd_soc_codec_get_drvdata(codec); 1005 wm8985 = snd_soc_codec_get_drvdata(codec);
1006 codec->control_data = wm8985->regmap;
951 1007
952 ret = snd_soc_codec_set_cache_io(codec, 7, 9, wm8985->control_type); 1008 ret = snd_soc_codec_set_cache_io(codec, 7, 9, SND_SOC_REGMAP);
953 if (ret < 0) { 1009 if (ret < 0) {
954 dev_err(codec->dev, "Failed to set cache i/o: %d\n", ret); 1010 dev_err(codec->dev, "Failed to set cache i/o: %d\n", ret);
955 return ret; 1011 return ret;
@@ -1037,14 +1093,23 @@ static struct snd_soc_codec_driver soc_codec_dev_wm8985 = {
1037 .controls = wm8985_snd_controls, 1093 .controls = wm8985_snd_controls,
1038 .num_controls = ARRAY_SIZE(wm8985_snd_controls), 1094 .num_controls = ARRAY_SIZE(wm8985_snd_controls),
1039 .dapm_widgets = wm8985_dapm_widgets, 1095 .dapm_widgets = wm8985_dapm_widgets,
1040 .reg_cache_size = ARRAY_SIZE(wm8985_reg_defs),
1041 .reg_word_size = sizeof(u16),
1042 .reg_cache_default = wm8985_reg_defs
1043 .num_dapm_widgets = ARRAY_SIZE(wm8985_dapm_widgets), 1096 .num_dapm_widgets = ARRAY_SIZE(wm8985_dapm_widgets),
1044 .dapm_routes = wm8985_dapm_routes, 1097 .dapm_routes = wm8985_dapm_routes,
1045 .num_dapm_routes = ARRAY_SIZE(wm8985_dapm_routes), 1098 .num_dapm_routes = ARRAY_SIZE(wm8985_dapm_routes),
1046}; 1099};
1047 1100
1101static const struct regmap_config wm8985_regmap = {
1102 .reg_bits = 7,
1103 .val_bits = 9,
1104
1105 .max_register = WM8985_MAX_REGISTER,
1106 .writeable_reg = wm8985_writeable,
1107
1108 .cache_type = REGCACHE_RBTREE,
1109 .reg_defaults = wm8985_reg_defaults,
1110 .num_reg_defaults = ARRAY_SIZE(wm8985_reg_defaults),
1111};
1112
1048#if defined(CONFIG_SPI_MASTER) 1113#if defined(CONFIG_SPI_MASTER)
1049static int __devinit wm8985_spi_probe(struct spi_device *spi) 1114static int __devinit wm8985_spi_probe(struct spi_device *spi)
1050{ 1115{
@@ -1055,17 +1120,35 @@ static int __devinit wm8985_spi_probe(struct spi_device *spi)
1055 if (!wm8985) 1120 if (!wm8985)
1056 return -ENOMEM; 1121 return -ENOMEM;
1057 1122
1058 wm8985->control_type = SND_SOC_SPI;
1059 spi_set_drvdata(spi, wm8985); 1123 spi_set_drvdata(spi, wm8985);
1060 1124
1125 wm8985->regmap = regmap_init_spi(spi, &wm8985_regmap);
1126 if (IS_ERR(wm8985->regmap)) {
1127 ret = PTR_ERR(wm8985->regmap);
1128 dev_err(&spi->dev, "Failed to allocate register map: %d\n",
1129 ret);
1130 goto err;
1131 }
1132
1061 ret = snd_soc_register_codec(&spi->dev, 1133 ret = snd_soc_register_codec(&spi->dev,
1062 &soc_codec_dev_wm8985, &wm8985_dai, 1); 1134 &soc_codec_dev_wm8985, &wm8985_dai, 1);
1135 if (ret != 0)
1136 goto err;
1137
1138 return 0;
1139
1140err:
1141 regmap_exit(wm8985->regmap);
1063 return ret; 1142 return ret;
1064} 1143}
1065 1144
1066static int __devexit wm8985_spi_remove(struct spi_device *spi) 1145static int __devexit wm8985_spi_remove(struct spi_device *spi)
1067{ 1146{
1147 struct wm8985_priv *wm8985 = spi_get_drvdata(spi);
1148
1068 snd_soc_unregister_codec(&spi->dev); 1149 snd_soc_unregister_codec(&spi->dev);
1150 regmap_exit(wm8985->regmap);
1151
1069 return 0; 1152 return 0;
1070} 1153}
1071 1154
@@ -1090,17 +1173,35 @@ static __devinit int wm8985_i2c_probe(struct i2c_client *i2c,
1090 if (!wm8985) 1173 if (!wm8985)
1091 return -ENOMEM; 1174 return -ENOMEM;
1092 1175
1093 wm8985->control_type = SND_SOC_I2C;
1094 i2c_set_clientdata(i2c, wm8985); 1176 i2c_set_clientdata(i2c, wm8985);
1095 1177
1178 wm8985->regmap = regmap_init_i2c(i2c, &wm8985_regmap);
1179 if (IS_ERR(wm8985->regmap)) {
1180 ret = PTR_ERR(wm8985->regmap);
1181 dev_err(&i2c->dev, "Failed to allocate register map: %d\n",
1182 ret);
1183 goto err;
1184 }
1185
1096 ret = snd_soc_register_codec(&i2c->dev, 1186 ret = snd_soc_register_codec(&i2c->dev,
1097 &soc_codec_dev_wm8985, &wm8985_dai, 1); 1187 &soc_codec_dev_wm8985, &wm8985_dai, 1);
1188 if (ret != 0)
1189 goto err;
1190
1191 return 0;
1192
1193err:
1194 regmap_exit(wm8985->regmap);
1098 return ret; 1195 return ret;
1099} 1196}
1100 1197
1101static __devexit int wm8985_i2c_remove(struct i2c_client *client) 1198static __devexit int wm8985_i2c_remove(struct i2c_client *i2c)
1102{ 1199{
1103 snd_soc_unregister_codec(&client->dev); 1200 struct wm8985_priv *wm8985 = i2c_get_clientdata(i2c);
1201
1202 snd_soc_unregister_codec(&i2c->dev);
1203 regmap_exit(wm8985->regmap);
1204
1104 return 0; 1205 return 0;
1105} 1206}
1106 1207