aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorLars-Peter Clausen <lars@metafoo.de>2013-08-31 14:31:15 -0400
committerMark Brown <broonie@linaro.org>2013-09-16 19:37:03 -0400
commitf90fb3f778042b0b9f9aa1fd48cb76047a25eac0 (patch)
tree6db437fce4c7168668d568f8ae110cdadd3b6458
parenta94ed23436fb28bdcdd66e7fcf68ca5f7967e456 (diff)
ASoC: Remove infrastructure for supporting multiple cache types
The only cache type left is the flat cache and new other cache types won't be added since new drivers are supposed to use regmap directly for IO and caching. This patch removes the snd_soc_cache_ops indirection that was added to support multiple cache types and modifies the code to always use the flat cache directly. Signed-off-by: Lars-Peter Clausen <lars@metafoo.de> Signed-off-by: Mark Brown <broonie@linaro.org>
-rw-r--r--include/sound/soc.h27
-rw-r--r--sound/soc/soc-cache.c195
-rw-r--r--sound/soc/soc-core.c27
3 files changed, 58 insertions, 191 deletions
diff --git a/include/sound/soc.h b/include/sound/soc.h
index 577212629d0f..a72af6327987 100644
--- a/include/sound/soc.h
+++ b/include/sound/soc.h
@@ -330,7 +330,6 @@ struct soc_enum;
330struct snd_soc_jack; 330struct snd_soc_jack;
331struct snd_soc_jack_zone; 331struct snd_soc_jack_zone;
332struct snd_soc_jack_pin; 332struct snd_soc_jack_pin;
333struct snd_soc_cache_ops;
334#include <sound/soc-dapm.h> 333#include <sound/soc-dapm.h>
335#include <sound/soc-dpcm.h> 334#include <sound/soc-dpcm.h>
336 335
@@ -348,10 +347,6 @@ enum snd_soc_control_type {
348 SND_SOC_REGMAP, 347 SND_SOC_REGMAP,
349}; 348};
350 349
351enum snd_soc_compress_type {
352 SND_SOC_FLAT_COMPRESSION = 1,
353};
354
355enum snd_soc_pcm_subclass { 350enum snd_soc_pcm_subclass {
356 SND_SOC_PCM_CLASS_PCM = 0, 351 SND_SOC_PCM_CLASS_PCM = 0,
357 SND_SOC_PCM_CLASS_BE = 1, 352 SND_SOC_PCM_CLASS_BE = 1,
@@ -635,19 +630,6 @@ struct snd_soc_compr_ops {
635 int (*trigger)(struct snd_compr_stream *); 630 int (*trigger)(struct snd_compr_stream *);
636}; 631};
637 632
638/* SoC cache ops */
639struct snd_soc_cache_ops {
640 const char *name;
641 enum snd_soc_compress_type id;
642 int (*init)(struct snd_soc_codec *codec);
643 int (*exit)(struct snd_soc_codec *codec);
644 int (*read)(struct snd_soc_codec *codec, unsigned int reg,
645 unsigned int *value);
646 int (*write)(struct snd_soc_codec *codec, unsigned int reg,
647 unsigned int value);
648 int (*sync)(struct snd_soc_codec *codec);
649};
650
651/* SoC Audio Codec device */ 633/* SoC Audio Codec device */
652struct snd_soc_codec { 634struct snd_soc_codec {
653 const char *name; 635 const char *name;
@@ -661,7 +643,6 @@ struct snd_soc_codec {
661 struct list_head list; 643 struct list_head list;
662 struct list_head card_list; 644 struct list_head card_list;
663 int num_dai; 645 int num_dai;
664 enum snd_soc_compress_type compress_type;
665 int (*volatile_register)(struct snd_soc_codec *, unsigned int); 646 int (*volatile_register)(struct snd_soc_codec *, unsigned int);
666 int (*readable_register)(struct snd_soc_codec *, unsigned int); 647 int (*readable_register)(struct snd_soc_codec *, unsigned int);
667 int (*writable_register)(struct snd_soc_codec *, unsigned int); 648 int (*writable_register)(struct snd_soc_codec *, unsigned int);
@@ -686,7 +667,6 @@ struct snd_soc_codec {
686 unsigned int (*read)(struct snd_soc_codec *, unsigned int); 667 unsigned int (*read)(struct snd_soc_codec *, unsigned int);
687 int (*write)(struct snd_soc_codec *, unsigned int, unsigned int); 668 int (*write)(struct snd_soc_codec *, unsigned int, unsigned int);
688 void *reg_cache; 669 void *reg_cache;
689 const struct snd_soc_cache_ops *cache_ops;
690 struct mutex cache_rw_mutex; 670 struct mutex cache_rw_mutex;
691 int val_bytes; 671 int val_bytes;
692 672
@@ -735,7 +715,6 @@ struct snd_soc_codec_driver {
735 short reg_cache_step; 715 short reg_cache_step;
736 short reg_word_size; 716 short reg_word_size;
737 const void *reg_cache_default; 717 const void *reg_cache_default;
738 enum snd_soc_compress_type compress_type;
739 718
740 /* codec bias level */ 719 /* codec bias level */
741 int (*set_bias_level)(struct snd_soc_codec *, 720 int (*set_bias_level)(struct snd_soc_codec *,
@@ -917,12 +896,6 @@ struct snd_soc_codec_conf {
917 * associated per device 896 * associated per device
918 */ 897 */
919 const char *name_prefix; 898 const char *name_prefix;
920
921 /*
922 * set this to the desired compression type if you want to
923 * override the one supplied in codec->driver->compress_type
924 */
925 enum snd_soc_compress_type compress_type;
926}; 899};
927 900
928struct snd_soc_aux_dev { 901struct snd_soc_aux_dev {
diff --git a/sound/soc/soc-cache.c b/sound/soc/soc-cache.c
index 9542c83d2295..1b6663f45b34 100644
--- a/sound/soc/soc-cache.c
+++ b/sound/soc/soc-cache.c
@@ -11,12 +11,9 @@
11 * option) any later version. 11 * option) any later version.
12 */ 12 */
13 13
14#include <linux/i2c.h>
15#include <linux/spi/spi.h>
16#include <sound/soc.h> 14#include <sound/soc.h>
17#include <linux/bitmap.h>
18#include <linux/rbtree.h>
19#include <linux/export.h> 15#include <linux/export.h>
16#include <linux/slab.h>
20 17
21#include <trace/events/asoc.h> 18#include <trace/events/asoc.h>
22 19
@@ -66,66 +63,18 @@ static unsigned int snd_soc_get_cache_val(const void *base, unsigned int idx,
66 return -1; 63 return -1;
67} 64}
68 65
69static int snd_soc_flat_cache_sync(struct snd_soc_codec *codec) 66int snd_soc_cache_init(struct snd_soc_codec *codec)
70{
71 int i;
72 int ret;
73 const struct snd_soc_codec_driver *codec_drv;
74 unsigned int val;
75
76 codec_drv = codec->driver;
77 for (i = 0; i < codec_drv->reg_cache_size; ++i) {
78 ret = snd_soc_cache_read(codec, i, &val);
79 if (ret)
80 return ret;
81 if (codec_drv->reg_cache_default)
82 if (snd_soc_get_cache_val(codec_drv->reg_cache_default,
83 i, codec_drv->reg_word_size) == val)
84 continue;
85
86 WARN_ON(!snd_soc_codec_writable_register(codec, i));
87
88 ret = snd_soc_write(codec, i, val);
89 if (ret)
90 return ret;
91 dev_dbg(codec->dev, "ASoC: Synced register %#x, value = %#x\n",
92 i, val);
93 }
94 return 0;
95}
96
97static int snd_soc_flat_cache_write(struct snd_soc_codec *codec,
98 unsigned int reg, unsigned int value)
99{
100 snd_soc_set_cache_val(codec->reg_cache, reg, value,
101 codec->driver->reg_word_size);
102 return 0;
103}
104
105static int snd_soc_flat_cache_read(struct snd_soc_codec *codec,
106 unsigned int reg, unsigned int *value)
107{
108 *value = snd_soc_get_cache_val(codec->reg_cache, reg,
109 codec->driver->reg_word_size);
110 return 0;
111}
112
113static int snd_soc_flat_cache_exit(struct snd_soc_codec *codec)
114{
115 if (!codec->reg_cache)
116 return 0;
117 kfree(codec->reg_cache);
118 codec->reg_cache = NULL;
119 return 0;
120}
121
122static int snd_soc_flat_cache_init(struct snd_soc_codec *codec)
123{ 67{
124 const struct snd_soc_codec_driver *codec_drv = codec->driver; 68 const struct snd_soc_codec_driver *codec_drv = codec->driver;
125 size_t reg_size; 69 size_t reg_size;
126 70
127 reg_size = codec_drv->reg_cache_size * codec_drv->reg_word_size; 71 reg_size = codec_drv->reg_cache_size * codec_drv->reg_word_size;
128 72
73 mutex_init(&codec->cache_rw_mutex);
74
75 dev_dbg(codec->dev, "ASoC: Initializing cache for %s codec\n",
76 codec->name);
77
129 if (codec_drv->reg_cache_default) 78 if (codec_drv->reg_cache_default)
130 codec->reg_cache = kmemdup(codec_drv->reg_cache_default, 79 codec->reg_cache = kmemdup(codec_drv->reg_cache_default,
131 reg_size, GFP_KERNEL); 80 reg_size, GFP_KERNEL);
@@ -137,60 +86,19 @@ static int snd_soc_flat_cache_init(struct snd_soc_codec *codec)
137 return 0; 86 return 0;
138} 87}
139 88
140/* an array of all supported compression types */
141static const struct snd_soc_cache_ops cache_types[] = {
142 /* Flat *must* be the first entry for fallback */
143 {
144 .id = SND_SOC_FLAT_COMPRESSION,
145 .name = "flat",
146 .init = snd_soc_flat_cache_init,
147 .exit = snd_soc_flat_cache_exit,
148 .read = snd_soc_flat_cache_read,
149 .write = snd_soc_flat_cache_write,
150 .sync = snd_soc_flat_cache_sync
151 },
152};
153
154int snd_soc_cache_init(struct snd_soc_codec *codec)
155{
156 int i;
157
158 for (i = 0; i < ARRAY_SIZE(cache_types); ++i)
159 if (cache_types[i].id == codec->compress_type)
160 break;
161
162 /* Fall back to flat compression */
163 if (i == ARRAY_SIZE(cache_types)) {
164 dev_warn(codec->dev, "ASoC: Could not match compress type: %d\n",
165 codec->compress_type);
166 i = 0;
167 }
168
169 mutex_init(&codec->cache_rw_mutex);
170 codec->cache_ops = &cache_types[i];
171
172 if (codec->cache_ops->init) {
173 if (codec->cache_ops->name)
174 dev_dbg(codec->dev, "ASoC: Initializing %s cache for %s codec\n",
175 codec->cache_ops->name, codec->name);
176 return codec->cache_ops->init(codec);
177 }
178 return -ENOSYS;
179}
180
181/* 89/*
182 * NOTE: keep in mind that this function might be called 90 * NOTE: keep in mind that this function might be called
183 * multiple times. 91 * multiple times.
184 */ 92 */
185int snd_soc_cache_exit(struct snd_soc_codec *codec) 93int snd_soc_cache_exit(struct snd_soc_codec *codec)
186{ 94{
187 if (codec->cache_ops && codec->cache_ops->exit) { 95 dev_dbg(codec->dev, "ASoC: Destroying cache for %s codec\n",
188 if (codec->cache_ops->name) 96 codec->name);
189 dev_dbg(codec->dev, "ASoC: Destroying %s cache for %s codec\n", 97 if (!codec->reg_cache)
190 codec->cache_ops->name, codec->name); 98 return 0;
191 return codec->cache_ops->exit(codec); 99 kfree(codec->reg_cache);
192 } 100 codec->reg_cache = NULL;
193 return -ENOSYS; 101 return 0;
194} 102}
195 103
196/** 104/**
@@ -203,18 +111,15 @@ int snd_soc_cache_exit(struct snd_soc_codec *codec)
203int snd_soc_cache_read(struct snd_soc_codec *codec, 111int snd_soc_cache_read(struct snd_soc_codec *codec,
204 unsigned int reg, unsigned int *value) 112 unsigned int reg, unsigned int *value)
205{ 113{
206 int ret; 114 if (!value)
115 return -EINVAL;
207 116
208 mutex_lock(&codec->cache_rw_mutex); 117 mutex_lock(&codec->cache_rw_mutex);
209 118 *value = snd_soc_get_cache_val(codec->reg_cache, reg,
210 if (value && codec->cache_ops && codec->cache_ops->read) { 119 codec->driver->reg_word_size);
211 ret = codec->cache_ops->read(codec, reg, value);
212 mutex_unlock(&codec->cache_rw_mutex);
213 return ret;
214 }
215
216 mutex_unlock(&codec->cache_rw_mutex); 120 mutex_unlock(&codec->cache_rw_mutex);
217 return -ENOSYS; 121
122 return 0;
218} 123}
219EXPORT_SYMBOL_GPL(snd_soc_cache_read); 124EXPORT_SYMBOL_GPL(snd_soc_cache_read);
220 125
@@ -228,20 +133,42 @@ EXPORT_SYMBOL_GPL(snd_soc_cache_read);
228int snd_soc_cache_write(struct snd_soc_codec *codec, 133int snd_soc_cache_write(struct snd_soc_codec *codec,
229 unsigned int reg, unsigned int value) 134 unsigned int reg, unsigned int value)
230{ 135{
136 mutex_lock(&codec->cache_rw_mutex);
137 snd_soc_set_cache_val(codec->reg_cache, reg, value,
138 codec->driver->reg_word_size);
139 mutex_unlock(&codec->cache_rw_mutex);
140
141 return 0;
142}
143EXPORT_SYMBOL_GPL(snd_soc_cache_write);
144
145static int snd_soc_flat_cache_sync(struct snd_soc_codec *codec)
146{
147 int i;
231 int ret; 148 int ret;
149 const struct snd_soc_codec_driver *codec_drv;
150 unsigned int val;
232 151
233 mutex_lock(&codec->cache_rw_mutex); 152 codec_drv = codec->driver;
153 for (i = 0; i < codec_drv->reg_cache_size; ++i) {
154 ret = snd_soc_cache_read(codec, i, &val);
155 if (ret)
156 return ret;
157 if (codec_drv->reg_cache_default)
158 if (snd_soc_get_cache_val(codec_drv->reg_cache_default,
159 i, codec_drv->reg_word_size) == val)
160 continue;
234 161
235 if (codec->cache_ops && codec->cache_ops->write) { 162 WARN_ON(!snd_soc_codec_writable_register(codec, i));
236 ret = codec->cache_ops->write(codec, reg, value);
237 mutex_unlock(&codec->cache_rw_mutex);
238 return ret;
239 }
240 163
241 mutex_unlock(&codec->cache_rw_mutex); 164 ret = snd_soc_write(codec, i, val);
242 return -ENOSYS; 165 if (ret)
166 return ret;
167 dev_dbg(codec->dev, "ASoC: Synced register %#x, value = %#x\n",
168 i, val);
169 }
170 return 0;
243} 171}
244EXPORT_SYMBOL_GPL(snd_soc_cache_write);
245 172
246/** 173/**
247 * snd_soc_cache_sync: Sync the register cache with the hardware. 174 * snd_soc_cache_sync: Sync the register cache with the hardware.
@@ -254,26 +181,16 @@ EXPORT_SYMBOL_GPL(snd_soc_cache_write);
254 */ 181 */
255int snd_soc_cache_sync(struct snd_soc_codec *codec) 182int snd_soc_cache_sync(struct snd_soc_codec *codec)
256{ 183{
184 const char *name = "flat";
257 int ret; 185 int ret;
258 const char *name;
259 186
260 if (!codec->cache_sync) { 187 if (!codec->cache_sync)
261 return 0; 188 return 0;
262 }
263
264 if (!codec->cache_ops || !codec->cache_ops->sync)
265 return -ENOSYS;
266
267 if (codec->cache_ops->name)
268 name = codec->cache_ops->name;
269 else
270 name = "unknown";
271 189
272 if (codec->cache_ops->name) 190 dev_dbg(codec->dev, "ASoC: Syncing cache for %s codec\n",
273 dev_dbg(codec->dev, "ASoC: Syncing %s cache for %s codec\n", 191 codec->name);
274 codec->cache_ops->name, codec->name);
275 trace_snd_soc_cache_sync(codec, name, "start"); 192 trace_snd_soc_cache_sync(codec, name, "start");
276 ret = codec->cache_ops->sync(codec); 193 ret = snd_soc_flat_cache_sync(codec);
277 if (!ret) 194 if (!ret)
278 codec->cache_sync = 0; 195 codec->cache_sync = 0;
279 trace_snd_soc_cache_sync(codec, name, "end"); 196 trace_snd_soc_cache_sync(codec, name, "end");
diff --git a/sound/soc/soc-core.c b/sound/soc/soc-core.c
index af9648426f4f..16a3930c6375 100644
--- a/sound/soc/soc-core.c
+++ b/sound/soc/soc-core.c
@@ -1590,17 +1590,13 @@ static void soc_remove_aux_dev(struct snd_soc_card *card, int num)
1590 soc_remove_codec(codec); 1590 soc_remove_codec(codec);
1591} 1591}
1592 1592
1593static int snd_soc_init_codec_cache(struct snd_soc_codec *codec, 1593static int snd_soc_init_codec_cache(struct snd_soc_codec *codec)
1594 enum snd_soc_compress_type compress_type)
1595{ 1594{
1596 int ret; 1595 int ret;
1597 1596
1598 if (codec->cache_init) 1597 if (codec->cache_init)
1599 return 0; 1598 return 0;
1600 1599
1601 /* override the compress_type if necessary */
1602 if (compress_type && codec->compress_type != compress_type)
1603 codec->compress_type = compress_type;
1604 ret = snd_soc_cache_init(codec); 1600 ret = snd_soc_cache_init(codec);
1605 if (ret < 0) { 1601 if (ret < 0) {
1606 dev_err(codec->dev, 1602 dev_err(codec->dev,
@@ -1615,8 +1611,6 @@ static int snd_soc_init_codec_cache(struct snd_soc_codec *codec,
1615static int snd_soc_instantiate_card(struct snd_soc_card *card) 1611static int snd_soc_instantiate_card(struct snd_soc_card *card)
1616{ 1612{
1617 struct snd_soc_codec *codec; 1613 struct snd_soc_codec *codec;
1618 struct snd_soc_codec_conf *codec_conf;
1619 enum snd_soc_compress_type compress_type;
1620 struct snd_soc_dai_link *dai_link; 1614 struct snd_soc_dai_link *dai_link;
1621 int ret, i, order, dai_fmt; 1615 int ret, i, order, dai_fmt;
1622 1616
@@ -1640,19 +1634,7 @@ static int snd_soc_instantiate_card(struct snd_soc_card *card)
1640 list_for_each_entry(codec, &codec_list, list) { 1634 list_for_each_entry(codec, &codec_list, list) {
1641 if (codec->cache_init) 1635 if (codec->cache_init)
1642 continue; 1636 continue;
1643 /* by default we don't override the compress_type */ 1637 ret = snd_soc_init_codec_cache(codec);
1644 compress_type = 0;
1645 /* check to see if we need to override the compress_type */
1646 for (i = 0; i < card->num_configs; ++i) {
1647 codec_conf = &card->codec_conf[i];
1648 if (!strcmp(codec->name, codec_conf->dev_name)) {
1649 compress_type = codec_conf->compress_type;
1650 if (compress_type && compress_type
1651 != codec->compress_type)
1652 break;
1653 }
1654 }
1655 ret = snd_soc_init_codec_cache(codec, compress_type);
1656 if (ret < 0) 1638 if (ret < 0)
1657 goto base_error; 1639 goto base_error;
1658 } 1640 }
@@ -4175,11 +4157,6 @@ int snd_soc_register_codec(struct device *dev,
4175 goto fail_codec; 4157 goto fail_codec;
4176 } 4158 }
4177 4159
4178 if (codec_drv->compress_type)
4179 codec->compress_type = codec_drv->compress_type;
4180 else
4181 codec->compress_type = SND_SOC_FLAT_COMPRESSION;
4182
4183 codec->write = codec_drv->write; 4160 codec->write = codec_drv->write;
4184 codec->read = codec_drv->read; 4161 codec->read = codec_drv->read;
4185 codec->volatile_register = codec_drv->volatile_register; 4162 codec->volatile_register = codec_drv->volatile_register;