diff options
author | Mark Brown <broonie@linaro.org> | 2013-06-26 07:45:59 -0400 |
---|---|---|
committer | Mark Brown <broonie@linaro.org> | 2013-06-27 04:48:42 -0400 |
commit | b047e1cce8fe32475ab61846772943a5e4c0a908 (patch) | |
tree | 9d04d8101d161b96f96c2e2e5bd03900011828ec /sound | |
parent | b49dff8cb61cd4715991612e2eb6905b73a0be78 (diff) |
ASoC: ac97: Support multi-platform AC'97
Currently we can only have a single platform built in with AC'97 support
due to the use of a global variable to provide the bus operations. Fix
this by making that variable a pointer and having the bus drivers set the
operations prior to registering.
This is not a particularly good or nice approach but it avoids blocking
multiplatform and a real fix involves fixing the fairly deep problems
with AC'97 support - we should be converting it to a real bus.
Acked-by: Arnd Bergmann <arnd@arndb.de>
Reviewed-by: Stephen Warren <swarren@nvidia.com>
Signed-off-by: Mark Brown <broonie@linaro.org>
Diffstat (limited to 'sound')
-rw-r--r-- | sound/soc/au1x/ac97c.c | 7 | ||||
-rw-r--r-- | sound/soc/au1x/psc-ac97.c | 7 | ||||
-rw-r--r-- | sound/soc/blackfin/bf5xx-ac97.c | 11 | ||||
-rw-r--r-- | sound/soc/cirrus/ep93xx-ac97.c | 10 | ||||
-rw-r--r-- | sound/soc/codecs/ac97.c | 7 | ||||
-rw-r--r-- | sound/soc/codecs/ad1980.c | 12 | ||||
-rw-r--r-- | sound/soc/codecs/stac9766.c | 22 | ||||
-rw-r--r-- | sound/soc/codecs/wm9705.c | 14 | ||||
-rw-r--r-- | sound/soc/codecs/wm9712.c | 18 | ||||
-rw-r--r-- | sound/soc/codecs/wm9713.c | 18 | ||||
-rw-r--r-- | sound/soc/fsl/imx-ssi.c | 11 | ||||
-rw-r--r-- | sound/soc/fsl/mpc5200_psc_ac97.c | 10 | ||||
-rw-r--r-- | sound/soc/nuc900/nuc900-ac97.c | 11 | ||||
-rw-r--r-- | sound/soc/pxa/pxa2xx-ac97.c | 8 | ||||
-rw-r--r-- | sound/soc/samsung/ac97.c | 12 | ||||
-rw-r--r-- | sound/soc/sh/hac.c | 8 | ||||
-rw-r--r-- | sound/soc/soc-core.c | 16 | ||||
-rw-r--r-- | sound/soc/tegra/tegra20_ac97.c | 12 | ||||
-rw-r--r-- | sound/soc/txx9/txx9aclc-ac97.c | 8 |
19 files changed, 151 insertions, 71 deletions
diff --git a/sound/soc/au1x/ac97c.c b/sound/soc/au1x/ac97c.c index a51dabe20cbb..d6f7694fcad4 100644 --- a/sound/soc/au1x/ac97c.c +++ b/sound/soc/au1x/ac97c.c | |||
@@ -179,13 +179,12 @@ static void au1xac97c_ac97_cold_reset(struct snd_ac97 *ac97) | |||
179 | } | 179 | } |
180 | 180 | ||
181 | /* AC97 controller operations */ | 181 | /* AC97 controller operations */ |
182 | struct snd_ac97_bus_ops soc_ac97_ops = { | 182 | static struct snd_ac97_bus_ops ac97c_bus_ops = { |
183 | .read = au1xac97c_ac97_read, | 183 | .read = au1xac97c_ac97_read, |
184 | .write = au1xac97c_ac97_write, | 184 | .write = au1xac97c_ac97_write, |
185 | .reset = au1xac97c_ac97_cold_reset, | 185 | .reset = au1xac97c_ac97_cold_reset, |
186 | .warm_reset = au1xac97c_ac97_warm_reset, | 186 | .warm_reset = au1xac97c_ac97_warm_reset, |
187 | }; | 187 | }; |
188 | EXPORT_SYMBOL_GPL(soc_ac97_ops); /* globals be gone! */ | ||
189 | 188 | ||
190 | static int alchemy_ac97c_startup(struct snd_pcm_substream *substream, | 189 | static int alchemy_ac97c_startup(struct snd_pcm_substream *substream, |
191 | struct snd_soc_dai *dai) | 190 | struct snd_soc_dai *dai) |
@@ -272,6 +271,10 @@ static int au1xac97c_drvprobe(struct platform_device *pdev) | |||
272 | 271 | ||
273 | platform_set_drvdata(pdev, ctx); | 272 | platform_set_drvdata(pdev, ctx); |
274 | 273 | ||
274 | ret = snd_soc_set_ac97_ops(&ac97c_bus_ops); | ||
275 | if (ret) | ||
276 | return ret; | ||
277 | |||
275 | ret = snd_soc_register_component(&pdev->dev, &au1xac97c_component, | 278 | ret = snd_soc_register_component(&pdev->dev, &au1xac97c_component, |
276 | &au1xac97c_dai_driver, 1); | 279 | &au1xac97c_dai_driver, 1); |
277 | if (ret) | 280 | if (ret) |
diff --git a/sound/soc/au1x/psc-ac97.c b/sound/soc/au1x/psc-ac97.c index a97ba1367b69..a822ab822bb7 100644 --- a/sound/soc/au1x/psc-ac97.c +++ b/sound/soc/au1x/psc-ac97.c | |||
@@ -201,13 +201,12 @@ static void au1xpsc_ac97_cold_reset(struct snd_ac97 *ac97) | |||
201 | } | 201 | } |
202 | 202 | ||
203 | /* AC97 controller operations */ | 203 | /* AC97 controller operations */ |
204 | struct snd_ac97_bus_ops soc_ac97_ops = { | 204 | static struct snd_ac97_bus_ops psc_ac97_ops = { |
205 | .read = au1xpsc_ac97_read, | 205 | .read = au1xpsc_ac97_read, |
206 | .write = au1xpsc_ac97_write, | 206 | .write = au1xpsc_ac97_write, |
207 | .reset = au1xpsc_ac97_cold_reset, | 207 | .reset = au1xpsc_ac97_cold_reset, |
208 | .warm_reset = au1xpsc_ac97_warm_reset, | 208 | .warm_reset = au1xpsc_ac97_warm_reset, |
209 | }; | 209 | }; |
210 | EXPORT_SYMBOL_GPL(soc_ac97_ops); | ||
211 | 210 | ||
212 | static int au1xpsc_ac97_hw_params(struct snd_pcm_substream *substream, | 211 | static int au1xpsc_ac97_hw_params(struct snd_pcm_substream *substream, |
213 | struct snd_pcm_hw_params *params, | 212 | struct snd_pcm_hw_params *params, |
@@ -417,6 +416,10 @@ static int au1xpsc_ac97_drvprobe(struct platform_device *pdev) | |||
417 | 416 | ||
418 | platform_set_drvdata(pdev, wd); | 417 | platform_set_drvdata(pdev, wd); |
419 | 418 | ||
419 | ret = snd_soc_set_ac97_ops(&psc_ac97_ops); | ||
420 | if (ret) | ||
421 | return ret; | ||
422 | |||
420 | ret = snd_soc_register_component(&pdev->dev, &au1xpsc_ac97_component, | 423 | ret = snd_soc_register_component(&pdev->dev, &au1xpsc_ac97_component, |
421 | &wd->dai_drv, 1); | 424 | &wd->dai_drv, 1); |
422 | if (ret) | 425 | if (ret) |
diff --git a/sound/soc/blackfin/bf5xx-ac97.c b/sound/soc/blackfin/bf5xx-ac97.c index 024e2dbe6c7f..c5af677ba49c 100644 --- a/sound/soc/blackfin/bf5xx-ac97.c +++ b/sound/soc/blackfin/bf5xx-ac97.c | |||
@@ -198,13 +198,12 @@ static void bf5xx_ac97_cold_reset(struct snd_ac97 *ac97) | |||
198 | #endif | 198 | #endif |
199 | } | 199 | } |
200 | 200 | ||
201 | struct snd_ac97_bus_ops soc_ac97_ops = { | 201 | static struct snd_ac97_bus_ops bf5xx_ac97_ops = { |
202 | .read = bf5xx_ac97_read, | 202 | .read = bf5xx_ac97_read, |
203 | .write = bf5xx_ac97_write, | 203 | .write = bf5xx_ac97_write, |
204 | .warm_reset = bf5xx_ac97_warm_reset, | 204 | .warm_reset = bf5xx_ac97_warm_reset, |
205 | .reset = bf5xx_ac97_cold_reset, | 205 | .reset = bf5xx_ac97_cold_reset, |
206 | }; | 206 | }; |
207 | EXPORT_SYMBOL_GPL(soc_ac97_ops); | ||
208 | 207 | ||
209 | #ifdef CONFIG_PM | 208 | #ifdef CONFIG_PM |
210 | static int bf5xx_ac97_suspend(struct snd_soc_dai *dai) | 209 | static int bf5xx_ac97_suspend(struct snd_soc_dai *dai) |
@@ -336,6 +335,12 @@ static int asoc_bfin_ac97_probe(struct platform_device *pdev) | |||
336 | goto sport_config_err; | 335 | goto sport_config_err; |
337 | } | 336 | } |
338 | 337 | ||
338 | ret = snd_soc_set_ac97_ops(&bf5xx_ac97_ops); | ||
339 | if (ret != 0) { | ||
340 | dev_err(&pdev->dev, "Failed to set AC'97 ops: %d\n", ret); | ||
341 | goto sport_config_err; | ||
342 | } | ||
343 | |||
339 | ret = snd_soc_register_component(&pdev->dev, &bfin_ac97_component, | 344 | ret = snd_soc_register_component(&pdev->dev, &bfin_ac97_component, |
340 | &bfin_ac97_dai, 1); | 345 | &bfin_ac97_dai, 1); |
341 | if (ret) { | 346 | if (ret) { |
@@ -350,6 +355,7 @@ static int asoc_bfin_ac97_probe(struct platform_device *pdev) | |||
350 | sport_config_err: | 355 | sport_config_err: |
351 | sport_done(sport_handle); | 356 | sport_done(sport_handle); |
352 | sport_err: | 357 | sport_err: |
358 | snd_soc_set_ac97_ops(NULL); | ||
353 | 359 | ||
354 | return ret; | 360 | return ret; |
355 | } | 361 | } |
@@ -360,6 +366,7 @@ static int asoc_bfin_ac97_remove(struct platform_device *pdev) | |||
360 | 366 | ||
361 | snd_soc_unregister_component(&pdev->dev); | 367 | snd_soc_unregister_component(&pdev->dev); |
362 | sport_done(sport_handle); | 368 | sport_done(sport_handle); |
369 | snd_soc_set_ac97_ops(NULL); | ||
363 | 370 | ||
364 | return 0; | 371 | return 0; |
365 | } | 372 | } |
diff --git a/sound/soc/cirrus/ep93xx-ac97.c b/sound/soc/cirrus/ep93xx-ac97.c index d49e0556e381..4bc9490e2c84 100644 --- a/sound/soc/cirrus/ep93xx-ac97.c +++ b/sound/soc/cirrus/ep93xx-ac97.c | |||
@@ -237,13 +237,12 @@ static irqreturn_t ep93xx_ac97_interrupt(int irq, void *dev_id) | |||
237 | return IRQ_HANDLED; | 237 | return IRQ_HANDLED; |
238 | } | 238 | } |
239 | 239 | ||
240 | struct snd_ac97_bus_ops soc_ac97_ops = { | 240 | static struct snd_ac97_bus_ops ep93xx_ac97_ops = { |
241 | .read = ep93xx_ac97_read, | 241 | .read = ep93xx_ac97_read, |
242 | .write = ep93xx_ac97_write, | 242 | .write = ep93xx_ac97_write, |
243 | .reset = ep93xx_ac97_cold_reset, | 243 | .reset = ep93xx_ac97_cold_reset, |
244 | .warm_reset = ep93xx_ac97_warm_reset, | 244 | .warm_reset = ep93xx_ac97_warm_reset, |
245 | }; | 245 | }; |
246 | EXPORT_SYMBOL_GPL(soc_ac97_ops); | ||
247 | 246 | ||
248 | static int ep93xx_ac97_trigger(struct snd_pcm_substream *substream, | 247 | static int ep93xx_ac97_trigger(struct snd_pcm_substream *substream, |
249 | int cmd, struct snd_soc_dai *dai) | 248 | int cmd, struct snd_soc_dai *dai) |
@@ -395,6 +394,10 @@ static int ep93xx_ac97_probe(struct platform_device *pdev) | |||
395 | ep93xx_ac97_info = info; | 394 | ep93xx_ac97_info = info; |
396 | platform_set_drvdata(pdev, info); | 395 | platform_set_drvdata(pdev, info); |
397 | 396 | ||
397 | ret = snd_soc_set_ac97_ops(&ep93xx_ac97_ops); | ||
398 | if (ret) | ||
399 | goto fail; | ||
400 | |||
398 | ret = snd_soc_register_component(&pdev->dev, &ep93xx_ac97_component, | 401 | ret = snd_soc_register_component(&pdev->dev, &ep93xx_ac97_component, |
399 | &ep93xx_ac97_dai, 1); | 402 | &ep93xx_ac97_dai, 1); |
400 | if (ret) | 403 | if (ret) |
@@ -405,6 +408,7 @@ static int ep93xx_ac97_probe(struct platform_device *pdev) | |||
405 | fail: | 408 | fail: |
406 | platform_set_drvdata(pdev, NULL); | 409 | platform_set_drvdata(pdev, NULL); |
407 | ep93xx_ac97_info = NULL; | 410 | ep93xx_ac97_info = NULL; |
411 | snd_soc_set_ac97_ops(NULL); | ||
408 | return ret; | 412 | return ret; |
409 | } | 413 | } |
410 | 414 | ||
@@ -420,6 +424,8 @@ static int ep93xx_ac97_remove(struct platform_device *pdev) | |||
420 | platform_set_drvdata(pdev, NULL); | 424 | platform_set_drvdata(pdev, NULL); |
421 | ep93xx_ac97_info = NULL; | 425 | ep93xx_ac97_info = NULL; |
422 | 426 | ||
427 | snd_soc_set_ac97_ops(NULL); | ||
428 | |||
423 | return 0; | 429 | return 0; |
424 | } | 430 | } |
425 | 431 | ||
diff --git a/sound/soc/codecs/ac97.c b/sound/soc/codecs/ac97.c index ef2ae32ffc66..ec7351803c24 100644 --- a/sound/soc/codecs/ac97.c +++ b/sound/soc/codecs/ac97.c | |||
@@ -62,13 +62,13 @@ static struct snd_soc_dai_driver ac97_dai = { | |||
62 | static unsigned int ac97_read(struct snd_soc_codec *codec, | 62 | static unsigned int ac97_read(struct snd_soc_codec *codec, |
63 | unsigned int reg) | 63 | unsigned int reg) |
64 | { | 64 | { |
65 | return soc_ac97_ops.read(codec->ac97, reg); | 65 | return soc_ac97_ops->read(codec->ac97, reg); |
66 | } | 66 | } |
67 | 67 | ||
68 | static int ac97_write(struct snd_soc_codec *codec, unsigned int reg, | 68 | static int ac97_write(struct snd_soc_codec *codec, unsigned int reg, |
69 | unsigned int val) | 69 | unsigned int val) |
70 | { | 70 | { |
71 | soc_ac97_ops.write(codec->ac97, reg, val); | 71 | soc_ac97_ops->write(codec->ac97, reg, val); |
72 | return 0; | 72 | return 0; |
73 | } | 73 | } |
74 | 74 | ||
@@ -79,7 +79,8 @@ static int ac97_soc_probe(struct snd_soc_codec *codec) | |||
79 | int ret; | 79 | int ret; |
80 | 80 | ||
81 | /* add codec as bus device for standard ac97 */ | 81 | /* add codec as bus device for standard ac97 */ |
82 | ret = snd_ac97_bus(codec->card->snd_card, 0, &soc_ac97_ops, NULL, &ac97_bus); | 82 | ret = snd_ac97_bus(codec->card->snd_card, 0, soc_ac97_ops, NULL, |
83 | &ac97_bus); | ||
83 | if (ret < 0) | 84 | if (ret < 0) |
84 | return ret; | 85 | return ret; |
85 | 86 | ||
diff --git a/sound/soc/codecs/ad1980.c b/sound/soc/codecs/ad1980.c index f385342947d3..89fcf7d6e7b8 100644 --- a/sound/soc/codecs/ad1980.c +++ b/sound/soc/codecs/ad1980.c | |||
@@ -108,7 +108,7 @@ static unsigned int ac97_read(struct snd_soc_codec *codec, | |||
108 | case AC97_EXTENDED_STATUS: | 108 | case AC97_EXTENDED_STATUS: |
109 | case AC97_VENDOR_ID1: | 109 | case AC97_VENDOR_ID1: |
110 | case AC97_VENDOR_ID2: | 110 | case AC97_VENDOR_ID2: |
111 | return soc_ac97_ops.read(codec->ac97, reg); | 111 | return soc_ac97_ops->read(codec->ac97, reg); |
112 | default: | 112 | default: |
113 | reg = reg >> 1; | 113 | reg = reg >> 1; |
114 | 114 | ||
@@ -124,7 +124,7 @@ static int ac97_write(struct snd_soc_codec *codec, unsigned int reg, | |||
124 | { | 124 | { |
125 | u16 *cache = codec->reg_cache; | 125 | u16 *cache = codec->reg_cache; |
126 | 126 | ||
127 | soc_ac97_ops.write(codec->ac97, reg, val); | 127 | soc_ac97_ops->write(codec->ac97, reg, val); |
128 | reg = reg >> 1; | 128 | reg = reg >> 1; |
129 | if (reg < ARRAY_SIZE(ad1980_reg)) | 129 | if (reg < ARRAY_SIZE(ad1980_reg)) |
130 | cache[reg] = val; | 130 | cache[reg] = val; |
@@ -154,13 +154,13 @@ static int ad1980_reset(struct snd_soc_codec *codec, int try_warm) | |||
154 | u16 retry_cnt = 0; | 154 | u16 retry_cnt = 0; |
155 | 155 | ||
156 | retry: | 156 | retry: |
157 | if (try_warm && soc_ac97_ops.warm_reset) { | 157 | if (try_warm && soc_ac97_ops->warm_reset) { |
158 | soc_ac97_ops.warm_reset(codec->ac97); | 158 | soc_ac97_ops->warm_reset(codec->ac97); |
159 | if (ac97_read(codec, AC97_RESET) == 0x0090) | 159 | if (ac97_read(codec, AC97_RESET) == 0x0090) |
160 | return 1; | 160 | return 1; |
161 | } | 161 | } |
162 | 162 | ||
163 | soc_ac97_ops.reset(codec->ac97); | 163 | soc_ac97_ops->reset(codec->ac97); |
164 | /* Set bit 16slot in register 74h, then every slot will has only 16 | 164 | /* Set bit 16slot in register 74h, then every slot will has only 16 |
165 | * bits. This command is sent out in 20bit mode, in which case the | 165 | * bits. This command is sent out in 20bit mode, in which case the |
166 | * first nibble of data is eaten by the addr. (Tag is always 16 bit)*/ | 166 | * first nibble of data is eaten by the addr. (Tag is always 16 bit)*/ |
@@ -186,7 +186,7 @@ static int ad1980_soc_probe(struct snd_soc_codec *codec) | |||
186 | 186 | ||
187 | printk(KERN_INFO "AD1980 SoC Audio Codec\n"); | 187 | printk(KERN_INFO "AD1980 SoC Audio Codec\n"); |
188 | 188 | ||
189 | ret = snd_soc_new_ac97_codec(codec, &soc_ac97_ops, 0); | 189 | ret = snd_soc_new_ac97_codec(codec, soc_ac97_ops, 0); |
190 | if (ret < 0) { | 190 | if (ret < 0) { |
191 | printk(KERN_ERR "ad1980: failed to register AC97 codec\n"); | 191 | printk(KERN_ERR "ad1980: failed to register AC97 codec\n"); |
192 | return ret; | 192 | return ret; |
diff --git a/sound/soc/codecs/stac9766.c b/sound/soc/codecs/stac9766.c index cbc7ae322324..a5455c1aea42 100644 --- a/sound/soc/codecs/stac9766.c +++ b/sound/soc/codecs/stac9766.c | |||
@@ -143,14 +143,14 @@ static int stac9766_ac97_write(struct snd_soc_codec *codec, unsigned int reg, | |||
143 | 143 | ||
144 | if (reg > AC97_STAC_PAGE0) { | 144 | if (reg > AC97_STAC_PAGE0) { |
145 | stac9766_ac97_write(codec, AC97_INT_PAGING, 0); | 145 | stac9766_ac97_write(codec, AC97_INT_PAGING, 0); |
146 | soc_ac97_ops.write(codec->ac97, reg, val); | 146 | soc_ac97_ops->write(codec->ac97, reg, val); |
147 | stac9766_ac97_write(codec, AC97_INT_PAGING, 1); | 147 | stac9766_ac97_write(codec, AC97_INT_PAGING, 1); |
148 | return 0; | 148 | return 0; |
149 | } | 149 | } |
150 | if (reg / 2 >= ARRAY_SIZE(stac9766_reg)) | 150 | if (reg / 2 >= ARRAY_SIZE(stac9766_reg)) |
151 | return -EIO; | 151 | return -EIO; |
152 | 152 | ||
153 | soc_ac97_ops.write(codec->ac97, reg, val); | 153 | soc_ac97_ops->write(codec->ac97, reg, val); |
154 | cache[reg / 2] = val; | 154 | cache[reg / 2] = val; |
155 | return 0; | 155 | return 0; |
156 | } | 156 | } |
@@ -162,7 +162,7 @@ static unsigned int stac9766_ac97_read(struct snd_soc_codec *codec, | |||
162 | 162 | ||
163 | if (reg > AC97_STAC_PAGE0) { | 163 | if (reg > AC97_STAC_PAGE0) { |
164 | stac9766_ac97_write(codec, AC97_INT_PAGING, 0); | 164 | stac9766_ac97_write(codec, AC97_INT_PAGING, 0); |
165 | val = soc_ac97_ops.read(codec->ac97, reg - AC97_STAC_PAGE0); | 165 | val = soc_ac97_ops->read(codec->ac97, reg - AC97_STAC_PAGE0); |
166 | stac9766_ac97_write(codec, AC97_INT_PAGING, 1); | 166 | stac9766_ac97_write(codec, AC97_INT_PAGING, 1); |
167 | return val; | 167 | return val; |
168 | } | 168 | } |
@@ -173,7 +173,7 @@ static unsigned int stac9766_ac97_read(struct snd_soc_codec *codec, | |||
173 | reg == AC97_INT_PAGING || reg == AC97_VENDOR_ID1 || | 173 | reg == AC97_INT_PAGING || reg == AC97_VENDOR_ID1 || |
174 | reg == AC97_VENDOR_ID2) { | 174 | reg == AC97_VENDOR_ID2) { |
175 | 175 | ||
176 | val = soc_ac97_ops.read(codec->ac97, reg); | 176 | val = soc_ac97_ops->read(codec->ac97, reg); |
177 | return val; | 177 | return val; |
178 | } | 178 | } |
179 | return cache[reg / 2]; | 179 | return cache[reg / 2]; |
@@ -240,15 +240,15 @@ static int stac9766_set_bias_level(struct snd_soc_codec *codec, | |||
240 | 240 | ||
241 | static int stac9766_reset(struct snd_soc_codec *codec, int try_warm) | 241 | static int stac9766_reset(struct snd_soc_codec *codec, int try_warm) |
242 | { | 242 | { |
243 | if (try_warm && soc_ac97_ops.warm_reset) { | 243 | if (try_warm && soc_ac97_ops->warm_reset) { |
244 | soc_ac97_ops.warm_reset(codec->ac97); | 244 | soc_ac97_ops->warm_reset(codec->ac97); |
245 | if (stac9766_ac97_read(codec, 0) == stac9766_reg[0]) | 245 | if (stac9766_ac97_read(codec, 0) == stac9766_reg[0]) |
246 | return 1; | 246 | return 1; |
247 | } | 247 | } |
248 | 248 | ||
249 | soc_ac97_ops.reset(codec->ac97); | 249 | soc_ac97_ops->reset(codec->ac97); |
250 | if (soc_ac97_ops.warm_reset) | 250 | if (soc_ac97_ops->warm_reset) |
251 | soc_ac97_ops.warm_reset(codec->ac97); | 251 | soc_ac97_ops->warm_reset(codec->ac97); |
252 | if (stac9766_ac97_read(codec, 0) != stac9766_reg[0]) | 252 | if (stac9766_ac97_read(codec, 0) != stac9766_reg[0]) |
253 | return -EIO; | 253 | return -EIO; |
254 | return 0; | 254 | return 0; |
@@ -272,7 +272,7 @@ reset: | |||
272 | return -EIO; | 272 | return -EIO; |
273 | } | 273 | } |
274 | codec->ac97->bus->ops->warm_reset(codec->ac97); | 274 | codec->ac97->bus->ops->warm_reset(codec->ac97); |
275 | id = soc_ac97_ops.read(codec->ac97, AC97_VENDOR_ID2); | 275 | id = soc_ac97_ops->read(codec->ac97, AC97_VENDOR_ID2); |
276 | if (id != 0x4c13) { | 276 | if (id != 0x4c13) { |
277 | stac9766_reset(codec, 0); | 277 | stac9766_reset(codec, 0); |
278 | reset++; | 278 | reset++; |
@@ -336,7 +336,7 @@ static int stac9766_codec_probe(struct snd_soc_codec *codec) | |||
336 | { | 336 | { |
337 | int ret = 0; | 337 | int ret = 0; |
338 | 338 | ||
339 | ret = snd_soc_new_ac97_codec(codec, &soc_ac97_ops, 0); | 339 | ret = snd_soc_new_ac97_codec(codec, soc_ac97_ops, 0); |
340 | if (ret < 0) | 340 | if (ret < 0) |
341 | goto codec_err; | 341 | goto codec_err; |
342 | 342 | ||
diff --git a/sound/soc/codecs/wm9705.c b/sound/soc/codecs/wm9705.c index a5fc61dbcd47..70ce6793c5bd 100644 --- a/sound/soc/codecs/wm9705.c +++ b/sound/soc/codecs/wm9705.c | |||
@@ -209,7 +209,7 @@ static unsigned int ac97_read(struct snd_soc_codec *codec, unsigned int reg) | |||
209 | case AC97_RESET: | 209 | case AC97_RESET: |
210 | case AC97_VENDOR_ID1: | 210 | case AC97_VENDOR_ID1: |
211 | case AC97_VENDOR_ID2: | 211 | case AC97_VENDOR_ID2: |
212 | return soc_ac97_ops.read(codec->ac97, reg); | 212 | return soc_ac97_ops->read(codec->ac97, reg); |
213 | default: | 213 | default: |
214 | reg = reg >> 1; | 214 | reg = reg >> 1; |
215 | 215 | ||
@@ -225,7 +225,7 @@ static int ac97_write(struct snd_soc_codec *codec, unsigned int reg, | |||
225 | { | 225 | { |
226 | u16 *cache = codec->reg_cache; | 226 | u16 *cache = codec->reg_cache; |
227 | 227 | ||
228 | soc_ac97_ops.write(codec->ac97, reg, val); | 228 | soc_ac97_ops->write(codec->ac97, reg, val); |
229 | reg = reg >> 1; | 229 | reg = reg >> 1; |
230 | if (reg < (ARRAY_SIZE(wm9705_reg))) | 230 | if (reg < (ARRAY_SIZE(wm9705_reg))) |
231 | cache[reg] = val; | 231 | cache[reg] = val; |
@@ -294,8 +294,8 @@ static struct snd_soc_dai_driver wm9705_dai[] = { | |||
294 | 294 | ||
295 | static int wm9705_reset(struct snd_soc_codec *codec) | 295 | static int wm9705_reset(struct snd_soc_codec *codec) |
296 | { | 296 | { |
297 | if (soc_ac97_ops.reset) { | 297 | if (soc_ac97_ops->reset) { |
298 | soc_ac97_ops.reset(codec->ac97); | 298 | soc_ac97_ops->reset(codec->ac97); |
299 | if (ac97_read(codec, 0) == wm9705_reg[0]) | 299 | if (ac97_read(codec, 0) == wm9705_reg[0]) |
300 | return 0; /* Success */ | 300 | return 0; /* Success */ |
301 | } | 301 | } |
@@ -306,7 +306,7 @@ static int wm9705_reset(struct snd_soc_codec *codec) | |||
306 | #ifdef CONFIG_PM | 306 | #ifdef CONFIG_PM |
307 | static int wm9705_soc_suspend(struct snd_soc_codec *codec) | 307 | static int wm9705_soc_suspend(struct snd_soc_codec *codec) |
308 | { | 308 | { |
309 | soc_ac97_ops.write(codec->ac97, AC97_POWERDOWN, 0xffff); | 309 | soc_ac97_ops->write(codec->ac97, AC97_POWERDOWN, 0xffff); |
310 | 310 | ||
311 | return 0; | 311 | return 0; |
312 | } | 312 | } |
@@ -323,7 +323,7 @@ static int wm9705_soc_resume(struct snd_soc_codec *codec) | |||
323 | } | 323 | } |
324 | 324 | ||
325 | for (i = 2; i < ARRAY_SIZE(wm9705_reg) << 1; i += 2) { | 325 | for (i = 2; i < ARRAY_SIZE(wm9705_reg) << 1; i += 2) { |
326 | soc_ac97_ops.write(codec->ac97, i, cache[i>>1]); | 326 | soc_ac97_ops->write(codec->ac97, i, cache[i>>1]); |
327 | } | 327 | } |
328 | 328 | ||
329 | return 0; | 329 | return 0; |
@@ -337,7 +337,7 @@ static int wm9705_soc_probe(struct snd_soc_codec *codec) | |||
337 | { | 337 | { |
338 | int ret = 0; | 338 | int ret = 0; |
339 | 339 | ||
340 | ret = snd_soc_new_ac97_codec(codec, &soc_ac97_ops, 0); | 340 | ret = snd_soc_new_ac97_codec(codec, soc_ac97_ops, 0); |
341 | if (ret < 0) { | 341 | if (ret < 0) { |
342 | printk(KERN_ERR "wm9705: failed to register AC97 codec\n"); | 342 | printk(KERN_ERR "wm9705: failed to register AC97 codec\n"); |
343 | return ret; | 343 | return ret; |
diff --git a/sound/soc/codecs/wm9712.c b/sound/soc/codecs/wm9712.c index 8e9a6a3eeb1a..c5eb746087b4 100644 --- a/sound/soc/codecs/wm9712.c +++ b/sound/soc/codecs/wm9712.c | |||
@@ -455,7 +455,7 @@ static unsigned int ac97_read(struct snd_soc_codec *codec, | |||
455 | if (reg == AC97_RESET || reg == AC97_GPIO_STATUS || | 455 | if (reg == AC97_RESET || reg == AC97_GPIO_STATUS || |
456 | reg == AC97_VENDOR_ID1 || reg == AC97_VENDOR_ID2 || | 456 | reg == AC97_VENDOR_ID1 || reg == AC97_VENDOR_ID2 || |
457 | reg == AC97_REC_GAIN) | 457 | reg == AC97_REC_GAIN) |
458 | return soc_ac97_ops.read(codec->ac97, reg); | 458 | return soc_ac97_ops->read(codec->ac97, reg); |
459 | else { | 459 | else { |
460 | reg = reg >> 1; | 460 | reg = reg >> 1; |
461 | 461 | ||
@@ -472,7 +472,7 @@ static int ac97_write(struct snd_soc_codec *codec, unsigned int reg, | |||
472 | u16 *cache = codec->reg_cache; | 472 | u16 *cache = codec->reg_cache; |
473 | 473 | ||
474 | if (reg < 0x7c) | 474 | if (reg < 0x7c) |
475 | soc_ac97_ops.write(codec->ac97, reg, val); | 475 | soc_ac97_ops->write(codec->ac97, reg, val); |
476 | reg = reg >> 1; | 476 | reg = reg >> 1; |
477 | if (reg < (ARRAY_SIZE(wm9712_reg))) | 477 | if (reg < (ARRAY_SIZE(wm9712_reg))) |
478 | cache[reg] = val; | 478 | cache[reg] = val; |
@@ -581,15 +581,15 @@ static int wm9712_set_bias_level(struct snd_soc_codec *codec, | |||
581 | 581 | ||
582 | static int wm9712_reset(struct snd_soc_codec *codec, int try_warm) | 582 | static int wm9712_reset(struct snd_soc_codec *codec, int try_warm) |
583 | { | 583 | { |
584 | if (try_warm && soc_ac97_ops.warm_reset) { | 584 | if (try_warm && soc_ac97_ops->warm_reset) { |
585 | soc_ac97_ops.warm_reset(codec->ac97); | 585 | soc_ac97_ops->warm_reset(codec->ac97); |
586 | if (ac97_read(codec, 0) == wm9712_reg[0]) | 586 | if (ac97_read(codec, 0) == wm9712_reg[0]) |
587 | return 1; | 587 | return 1; |
588 | } | 588 | } |
589 | 589 | ||
590 | soc_ac97_ops.reset(codec->ac97); | 590 | soc_ac97_ops->reset(codec->ac97); |
591 | if (soc_ac97_ops.warm_reset) | 591 | if (soc_ac97_ops->warm_reset) |
592 | soc_ac97_ops.warm_reset(codec->ac97); | 592 | soc_ac97_ops->warm_reset(codec->ac97); |
593 | if (ac97_read(codec, 0) != wm9712_reg[0]) | 593 | if (ac97_read(codec, 0) != wm9712_reg[0]) |
594 | goto err; | 594 | goto err; |
595 | return 0; | 595 | return 0; |
@@ -624,7 +624,7 @@ static int wm9712_soc_resume(struct snd_soc_codec *codec) | |||
624 | if (i == AC97_INT_PAGING || i == AC97_POWERDOWN || | 624 | if (i == AC97_INT_PAGING || i == AC97_POWERDOWN || |
625 | (i > 0x58 && i != 0x5c)) | 625 | (i > 0x58 && i != 0x5c)) |
626 | continue; | 626 | continue; |
627 | soc_ac97_ops.write(codec->ac97, i, cache[i>>1]); | 627 | soc_ac97_ops->write(codec->ac97, i, cache[i>>1]); |
628 | } | 628 | } |
629 | } | 629 | } |
630 | 630 | ||
@@ -635,7 +635,7 @@ static int wm9712_soc_probe(struct snd_soc_codec *codec) | |||
635 | { | 635 | { |
636 | int ret = 0; | 636 | int ret = 0; |
637 | 637 | ||
638 | ret = snd_soc_new_ac97_codec(codec, &soc_ac97_ops, 0); | 638 | ret = snd_soc_new_ac97_codec(codec, soc_ac97_ops, 0); |
639 | if (ret < 0) { | 639 | if (ret < 0) { |
640 | printk(KERN_ERR "wm9712: failed to register AC97 codec\n"); | 640 | printk(KERN_ERR "wm9712: failed to register AC97 codec\n"); |
641 | return ret; | 641 | return ret; |
diff --git a/sound/soc/codecs/wm9713.c b/sound/soc/codecs/wm9713.c index f7afa68d8c7f..a53e175c015a 100644 --- a/sound/soc/codecs/wm9713.c +++ b/sound/soc/codecs/wm9713.c | |||
@@ -652,7 +652,7 @@ static unsigned int ac97_read(struct snd_soc_codec *codec, | |||
652 | if (reg == AC97_RESET || reg == AC97_GPIO_STATUS || | 652 | if (reg == AC97_RESET || reg == AC97_GPIO_STATUS || |
653 | reg == AC97_VENDOR_ID1 || reg == AC97_VENDOR_ID2 || | 653 | reg == AC97_VENDOR_ID1 || reg == AC97_VENDOR_ID2 || |
654 | reg == AC97_CD) | 654 | reg == AC97_CD) |
655 | return soc_ac97_ops.read(codec->ac97, reg); | 655 | return soc_ac97_ops->read(codec->ac97, reg); |
656 | else { | 656 | else { |
657 | reg = reg >> 1; | 657 | reg = reg >> 1; |
658 | 658 | ||
@@ -668,7 +668,7 @@ static int ac97_write(struct snd_soc_codec *codec, unsigned int reg, | |||
668 | { | 668 | { |
669 | u16 *cache = codec->reg_cache; | 669 | u16 *cache = codec->reg_cache; |
670 | if (reg < 0x7c) | 670 | if (reg < 0x7c) |
671 | soc_ac97_ops.write(codec->ac97, reg, val); | 671 | soc_ac97_ops->write(codec->ac97, reg, val); |
672 | reg = reg >> 1; | 672 | reg = reg >> 1; |
673 | if (reg < (ARRAY_SIZE(wm9713_reg))) | 673 | if (reg < (ARRAY_SIZE(wm9713_reg))) |
674 | cache[reg] = val; | 674 | cache[reg] = val; |
@@ -1095,15 +1095,15 @@ static struct snd_soc_dai_driver wm9713_dai[] = { | |||
1095 | 1095 | ||
1096 | int wm9713_reset(struct snd_soc_codec *codec, int try_warm) | 1096 | int wm9713_reset(struct snd_soc_codec *codec, int try_warm) |
1097 | { | 1097 | { |
1098 | if (try_warm && soc_ac97_ops.warm_reset) { | 1098 | if (try_warm && soc_ac97_ops->warm_reset) { |
1099 | soc_ac97_ops.warm_reset(codec->ac97); | 1099 | soc_ac97_ops->warm_reset(codec->ac97); |
1100 | if (ac97_read(codec, 0) == wm9713_reg[0]) | 1100 | if (ac97_read(codec, 0) == wm9713_reg[0]) |
1101 | return 1; | 1101 | return 1; |
1102 | } | 1102 | } |
1103 | 1103 | ||
1104 | soc_ac97_ops.reset(codec->ac97); | 1104 | soc_ac97_ops->reset(codec->ac97); |
1105 | if (soc_ac97_ops.warm_reset) | 1105 | if (soc_ac97_ops->warm_reset) |
1106 | soc_ac97_ops.warm_reset(codec->ac97); | 1106 | soc_ac97_ops->warm_reset(codec->ac97); |
1107 | if (ac97_read(codec, 0) != wm9713_reg[0]) | 1107 | if (ac97_read(codec, 0) != wm9713_reg[0]) |
1108 | return -EIO; | 1108 | return -EIO; |
1109 | return 0; | 1109 | return 0; |
@@ -1180,7 +1180,7 @@ static int wm9713_soc_resume(struct snd_soc_codec *codec) | |||
1180 | if (i == AC97_POWERDOWN || i == AC97_EXTENDED_MID || | 1180 | if (i == AC97_POWERDOWN || i == AC97_EXTENDED_MID || |
1181 | i == AC97_EXTENDED_MSTATUS || i > 0x66) | 1181 | i == AC97_EXTENDED_MSTATUS || i > 0x66) |
1182 | continue; | 1182 | continue; |
1183 | soc_ac97_ops.write(codec->ac97, i, cache[i>>1]); | 1183 | soc_ac97_ops->write(codec->ac97, i, cache[i>>1]); |
1184 | } | 1184 | } |
1185 | } | 1185 | } |
1186 | 1186 | ||
@@ -1197,7 +1197,7 @@ static int wm9713_soc_probe(struct snd_soc_codec *codec) | |||
1197 | return -ENOMEM; | 1197 | return -ENOMEM; |
1198 | snd_soc_codec_set_drvdata(codec, wm9713); | 1198 | snd_soc_codec_set_drvdata(codec, wm9713); |
1199 | 1199 | ||
1200 | ret = snd_soc_new_ac97_codec(codec, &soc_ac97_ops, 0); | 1200 | ret = snd_soc_new_ac97_codec(codec, soc_ac97_ops, 0); |
1201 | if (ret < 0) | 1201 | if (ret < 0) |
1202 | goto codec_err; | 1202 | goto codec_err; |
1203 | 1203 | ||
diff --git a/sound/soc/fsl/imx-ssi.c b/sound/soc/fsl/imx-ssi.c index c6fa03e2114a..bd40849454a8 100644 --- a/sound/soc/fsl/imx-ssi.c +++ b/sound/soc/fsl/imx-ssi.c | |||
@@ -501,13 +501,12 @@ static void imx_ssi_ac97_warm_reset(struct snd_ac97 *ac97) | |||
501 | imx_ssi_ac97_read(ac97, 0); | 501 | imx_ssi_ac97_read(ac97, 0); |
502 | } | 502 | } |
503 | 503 | ||
504 | struct snd_ac97_bus_ops soc_ac97_ops = { | 504 | static struct snd_ac97_bus_ops imx_ssi_ac97_ops = { |
505 | .read = imx_ssi_ac97_read, | 505 | .read = imx_ssi_ac97_read, |
506 | .write = imx_ssi_ac97_write, | 506 | .write = imx_ssi_ac97_write, |
507 | .reset = imx_ssi_ac97_reset, | 507 | .reset = imx_ssi_ac97_reset, |
508 | .warm_reset = imx_ssi_ac97_warm_reset | 508 | .warm_reset = imx_ssi_ac97_warm_reset |
509 | }; | 509 | }; |
510 | EXPORT_SYMBOL_GPL(soc_ac97_ops); | ||
511 | 510 | ||
512 | static int imx_ssi_probe(struct platform_device *pdev) | 511 | static int imx_ssi_probe(struct platform_device *pdev) |
513 | { | 512 | { |
@@ -583,6 +582,12 @@ static int imx_ssi_probe(struct platform_device *pdev) | |||
583 | 582 | ||
584 | platform_set_drvdata(pdev, ssi); | 583 | platform_set_drvdata(pdev, ssi); |
585 | 584 | ||
585 | ret = snd_soc_set_ac97_ops(&imx_ssi_ac97_ops); | ||
586 | if (ret != 0) { | ||
587 | dev_err(&pdev->dev, "Failed to set AC'97 ops: %d\n", ret); | ||
588 | goto failed_register; | ||
589 | } | ||
590 | |||
586 | ret = snd_soc_register_component(&pdev->dev, &imx_component, | 591 | ret = snd_soc_register_component(&pdev->dev, &imx_component, |
587 | dai, 1); | 592 | dai, 1); |
588 | if (ret) { | 593 | if (ret) { |
@@ -630,6 +635,7 @@ failed_register: | |||
630 | release_mem_region(res->start, resource_size(res)); | 635 | release_mem_region(res->start, resource_size(res)); |
631 | clk_disable_unprepare(ssi->clk); | 636 | clk_disable_unprepare(ssi->clk); |
632 | failed_clk: | 637 | failed_clk: |
638 | snd_soc_set_ac97_ops(NULL); | ||
633 | 639 | ||
634 | return ret; | 640 | return ret; |
635 | } | 641 | } |
@@ -649,6 +655,7 @@ static int imx_ssi_remove(struct platform_device *pdev) | |||
649 | 655 | ||
650 | release_mem_region(res->start, resource_size(res)); | 656 | release_mem_region(res->start, resource_size(res)); |
651 | clk_disable_unprepare(ssi->clk); | 657 | clk_disable_unprepare(ssi->clk); |
658 | snd_soc_set_ac97_ops(NULL); | ||
652 | 659 | ||
653 | return 0; | 660 | return 0; |
654 | } | 661 | } |
diff --git a/sound/soc/fsl/mpc5200_psc_ac97.c b/sound/soc/fsl/mpc5200_psc_ac97.c index 4141b35ef0bb..3ef7a0c92efa 100644 --- a/sound/soc/fsl/mpc5200_psc_ac97.c +++ b/sound/soc/fsl/mpc5200_psc_ac97.c | |||
@@ -131,13 +131,12 @@ static void psc_ac97_cold_reset(struct snd_ac97 *ac97) | |||
131 | psc_ac97_warm_reset(ac97); | 131 | psc_ac97_warm_reset(ac97); |
132 | } | 132 | } |
133 | 133 | ||
134 | struct snd_ac97_bus_ops soc_ac97_ops = { | 134 | static struct snd_ac97_bus_ops psc_ac97_ops = { |
135 | .read = psc_ac97_read, | 135 | .read = psc_ac97_read, |
136 | .write = psc_ac97_write, | 136 | .write = psc_ac97_write, |
137 | .reset = psc_ac97_cold_reset, | 137 | .reset = psc_ac97_cold_reset, |
138 | .warm_reset = psc_ac97_warm_reset, | 138 | .warm_reset = psc_ac97_warm_reset, |
139 | }; | 139 | }; |
140 | EXPORT_SYMBOL_GPL(soc_ac97_ops); | ||
141 | 140 | ||
142 | static int psc_ac97_hw_analog_params(struct snd_pcm_substream *substream, | 141 | static int psc_ac97_hw_analog_params(struct snd_pcm_substream *substream, |
143 | struct snd_pcm_hw_params *params, | 142 | struct snd_pcm_hw_params *params, |
@@ -290,6 +289,12 @@ static int psc_ac97_of_probe(struct platform_device *op) | |||
290 | if (rc != 0) | 289 | if (rc != 0) |
291 | return rc; | 290 | return rc; |
292 | 291 | ||
292 | rc = snd_soc_set_ac97_ops(&psc_ac97_ops); | ||
293 | if (rc != 0) { | ||
294 | dev_err(&op->dev, "Failed to set AC'97 ops: %d\n", ret); | ||
295 | return rc; | ||
296 | } | ||
297 | |||
293 | rc = snd_soc_register_component(&op->dev, &psc_ac97_component, | 298 | rc = snd_soc_register_component(&op->dev, &psc_ac97_component, |
294 | psc_ac97_dai, ARRAY_SIZE(psc_ac97_dai)); | 299 | psc_ac97_dai, ARRAY_SIZE(psc_ac97_dai)); |
295 | if (rc != 0) { | 300 | if (rc != 0) { |
@@ -318,6 +323,7 @@ static int psc_ac97_of_remove(struct platform_device *op) | |||
318 | { | 323 | { |
319 | mpc5200_audio_dma_destroy(op); | 324 | mpc5200_audio_dma_destroy(op); |
320 | snd_soc_unregister_component(&op->dev); | 325 | snd_soc_unregister_component(&op->dev); |
326 | snd_soc_set_ac97_ops(NULL); | ||
321 | return 0; | 327 | return 0; |
322 | } | 328 | } |
323 | 329 | ||
diff --git a/sound/soc/nuc900/nuc900-ac97.c b/sound/soc/nuc900/nuc900-ac97.c index 8dea4c1fd997..f4c2417a8730 100644 --- a/sound/soc/nuc900/nuc900-ac97.c +++ b/sound/soc/nuc900/nuc900-ac97.c | |||
@@ -197,13 +197,12 @@ static void nuc900_ac97_cold_reset(struct snd_ac97 *ac97) | |||
197 | } | 197 | } |
198 | 198 | ||
199 | /* AC97 controller operations */ | 199 | /* AC97 controller operations */ |
200 | struct snd_ac97_bus_ops soc_ac97_ops = { | 200 | static struct snd_ac97_bus_ops nuc900_ac97_ops = { |
201 | .read = nuc900_ac97_read, | 201 | .read = nuc900_ac97_read, |
202 | .write = nuc900_ac97_write, | 202 | .write = nuc900_ac97_write, |
203 | .reset = nuc900_ac97_cold_reset, | 203 | .reset = nuc900_ac97_cold_reset, |
204 | .warm_reset = nuc900_ac97_warm_reset, | 204 | .warm_reset = nuc900_ac97_warm_reset, |
205 | } | 205 | }; |
206 | EXPORT_SYMBOL_GPL(soc_ac97_ops); | ||
207 | 206 | ||
208 | static int nuc900_ac97_trigger(struct snd_pcm_substream *substream, | 207 | static int nuc900_ac97_trigger(struct snd_pcm_substream *substream, |
209 | int cmd, struct snd_soc_dai *dai) | 208 | int cmd, struct snd_soc_dai *dai) |
@@ -356,6 +355,10 @@ static int nuc900_ac97_drvprobe(struct platform_device *pdev) | |||
356 | 355 | ||
357 | nuc900_ac97_data = nuc900_audio; | 356 | nuc900_ac97_data = nuc900_audio; |
358 | 357 | ||
358 | ret = snd_soc_set_ac97_ops(&nuc900_ac97_ops); | ||
359 | if (ret) | ||
360 | goto out; | ||
361 | |||
359 | ret = snd_soc_register_component(&pdev->dev, &nuc900_ac97_component, | 362 | ret = snd_soc_register_component(&pdev->dev, &nuc900_ac97_component, |
360 | &nuc900_ac97_dai, 1); | 363 | &nuc900_ac97_dai, 1); |
361 | if (ret) | 364 | if (ret) |
@@ -367,6 +370,7 @@ static int nuc900_ac97_drvprobe(struct platform_device *pdev) | |||
367 | return 0; | 370 | return 0; |
368 | 371 | ||
369 | out: | 372 | out: |
373 | snd_soc_set_ac97_ops(NULL); | ||
370 | return ret; | 374 | return ret; |
371 | } | 375 | } |
372 | 376 | ||
@@ -375,6 +379,7 @@ static int nuc900_ac97_drvremove(struct platform_device *pdev) | |||
375 | snd_soc_unregister_component(&pdev->dev); | 379 | snd_soc_unregister_component(&pdev->dev); |
376 | 380 | ||
377 | nuc900_ac97_data = NULL; | 381 | nuc900_ac97_data = NULL; |
382 | snd_soc_set_ac97_ops(NULL); | ||
378 | 383 | ||
379 | return 0; | 384 | return 0; |
380 | } | 385 | } |
diff --git a/sound/soc/pxa/pxa2xx-ac97.c b/sound/soc/pxa/pxa2xx-ac97.c index 57ea8e6c5488..a3c22ba25f08 100644 --- a/sound/soc/pxa/pxa2xx-ac97.c +++ b/sound/soc/pxa/pxa2xx-ac97.c | |||
@@ -41,13 +41,12 @@ static void pxa2xx_ac97_cold_reset(struct snd_ac97 *ac97) | |||
41 | pxa2xx_ac97_finish_reset(ac97); | 41 | pxa2xx_ac97_finish_reset(ac97); |
42 | } | 42 | } |
43 | 43 | ||
44 | struct snd_ac97_bus_ops soc_ac97_ops = { | 44 | static struct snd_ac97_bus_ops pxa2xx_ac97_ops = { |
45 | .read = pxa2xx_ac97_read, | 45 | .read = pxa2xx_ac97_read, |
46 | .write = pxa2xx_ac97_write, | 46 | .write = pxa2xx_ac97_write, |
47 | .warm_reset = pxa2xx_ac97_warm_reset, | 47 | .warm_reset = pxa2xx_ac97_warm_reset, |
48 | .reset = pxa2xx_ac97_cold_reset, | 48 | .reset = pxa2xx_ac97_cold_reset, |
49 | }; | 49 | }; |
50 | EXPORT_SYMBOL_GPL(soc_ac97_ops); | ||
51 | 50 | ||
52 | static struct pxa2xx_pcm_dma_params pxa2xx_ac97_pcm_stereo_out = { | 51 | static struct pxa2xx_pcm_dma_params pxa2xx_ac97_pcm_stereo_out = { |
53 | .name = "AC97 PCM Stereo out", | 52 | .name = "AC97 PCM Stereo out", |
@@ -244,6 +243,10 @@ static int pxa2xx_ac97_dev_probe(struct platform_device *pdev) | |||
244 | return -ENXIO; | 243 | return -ENXIO; |
245 | } | 244 | } |
246 | 245 | ||
246 | ret = snd_soc_set_ac97_ops(&pxa2xx_ac97_ops); | ||
247 | if (ret != 0) | ||
248 | return ret; | ||
249 | |||
247 | /* Punt most of the init to the SoC probe; we may need the machine | 250 | /* Punt most of the init to the SoC probe; we may need the machine |
248 | * driver to do interesting things with the clocking to get us up | 251 | * driver to do interesting things with the clocking to get us up |
249 | * and running. | 252 | * and running. |
@@ -255,6 +258,7 @@ static int pxa2xx_ac97_dev_probe(struct platform_device *pdev) | |||
255 | static int pxa2xx_ac97_dev_remove(struct platform_device *pdev) | 258 | static int pxa2xx_ac97_dev_remove(struct platform_device *pdev) |
256 | { | 259 | { |
257 | snd_soc_unregister_component(&pdev->dev); | 260 | snd_soc_unregister_component(&pdev->dev); |
261 | snd_soc_set_ac97_ops(NULL); | ||
258 | return 0; | 262 | return 0; |
259 | } | 263 | } |
260 | 264 | ||
diff --git a/sound/soc/samsung/ac97.c b/sound/soc/samsung/ac97.c index 04d7fd461484..2dd623fa3882 100644 --- a/sound/soc/samsung/ac97.c +++ b/sound/soc/samsung/ac97.c | |||
@@ -214,13 +214,12 @@ static irqreturn_t s3c_ac97_irq(int irq, void *dev_id) | |||
214 | return IRQ_HANDLED; | 214 | return IRQ_HANDLED; |
215 | } | 215 | } |
216 | 216 | ||
217 | struct snd_ac97_bus_ops soc_ac97_ops = { | 217 | static struct snd_ac97_bus_ops s3c_ac97_ops = { |
218 | .read = s3c_ac97_read, | 218 | .read = s3c_ac97_read, |
219 | .write = s3c_ac97_write, | 219 | .write = s3c_ac97_write, |
220 | .warm_reset = s3c_ac97_warm_reset, | 220 | .warm_reset = s3c_ac97_warm_reset, |
221 | .reset = s3c_ac97_cold_reset, | 221 | .reset = s3c_ac97_cold_reset, |
222 | }; | 222 | }; |
223 | EXPORT_SYMBOL_GPL(soc_ac97_ops); | ||
224 | 223 | ||
225 | static int s3c_ac97_hw_params(struct snd_pcm_substream *substream, | 224 | static int s3c_ac97_hw_params(struct snd_pcm_substream *substream, |
226 | struct snd_pcm_hw_params *params, | 225 | struct snd_pcm_hw_params *params, |
@@ -452,6 +451,12 @@ static int s3c_ac97_probe(struct platform_device *pdev) | |||
452 | goto err4; | 451 | goto err4; |
453 | } | 452 | } |
454 | 453 | ||
454 | ret = snd_soc_set_ac97_ops(&s3c_ac97_ops); | ||
455 | if (ret != 0) { | ||
456 | dev_err(&pdev->dev, "Failed to set AC'97 ops: %d\n", ret); | ||
457 | goto err4; | ||
458 | } | ||
459 | |||
455 | ret = snd_soc_register_component(&pdev->dev, &s3c_ac97_component, | 460 | ret = snd_soc_register_component(&pdev->dev, &s3c_ac97_component, |
456 | s3c_ac97_dai, ARRAY_SIZE(s3c_ac97_dai)); | 461 | s3c_ac97_dai, ARRAY_SIZE(s3c_ac97_dai)); |
457 | if (ret) | 462 | if (ret) |
@@ -472,7 +477,7 @@ err4: | |||
472 | err3: | 477 | err3: |
473 | clk_disable_unprepare(s3c_ac97.ac97_clk); | 478 | clk_disable_unprepare(s3c_ac97.ac97_clk); |
474 | err2: | 479 | err2: |
475 | 480 | snd_soc_set_ac97_ops(NULL); | |
476 | return ret; | 481 | return ret; |
477 | } | 482 | } |
478 | 483 | ||
@@ -488,6 +493,7 @@ static int s3c_ac97_remove(struct platform_device *pdev) | |||
488 | free_irq(irq_res->start, NULL); | 493 | free_irq(irq_res->start, NULL); |
489 | 494 | ||
490 | clk_disable_unprepare(s3c_ac97.ac97_clk); | 495 | clk_disable_unprepare(s3c_ac97.ac97_clk); |
496 | snd_soc_set_ac97_ops(NULL); | ||
491 | 497 | ||
492 | return 0; | 498 | return 0; |
493 | } | 499 | } |
diff --git a/sound/soc/sh/hac.c b/sound/soc/sh/hac.c index af19f77b7bf0..0af2e4dfd139 100644 --- a/sound/soc/sh/hac.c +++ b/sound/soc/sh/hac.c | |||
@@ -227,13 +227,12 @@ static void hac_ac97_coldrst(struct snd_ac97 *ac97) | |||
227 | hac_ac97_warmrst(ac97); | 227 | hac_ac97_warmrst(ac97); |
228 | } | 228 | } |
229 | 229 | ||
230 | struct snd_ac97_bus_ops soc_ac97_ops = { | 230 | static struct snd_ac97_bus_ops hac_ac97_ops = { |
231 | .read = hac_ac97_read, | 231 | .read = hac_ac97_read, |
232 | .write = hac_ac97_write, | 232 | .write = hac_ac97_write, |
233 | .reset = hac_ac97_coldrst, | 233 | .reset = hac_ac97_coldrst, |
234 | .warm_reset = hac_ac97_warmrst, | 234 | .warm_reset = hac_ac97_warmrst, |
235 | }; | 235 | }; |
236 | EXPORT_SYMBOL_GPL(soc_ac97_ops); | ||
237 | 236 | ||
238 | static int hac_hw_params(struct snd_pcm_substream *substream, | 237 | static int hac_hw_params(struct snd_pcm_substream *substream, |
239 | struct snd_pcm_hw_params *params, | 238 | struct snd_pcm_hw_params *params, |
@@ -316,6 +315,10 @@ static const struct snd_soc_component_driver sh4_hac_component = { | |||
316 | 315 | ||
317 | static int hac_soc_platform_probe(struct platform_device *pdev) | 316 | static int hac_soc_platform_probe(struct platform_device *pdev) |
318 | { | 317 | { |
318 | ret = snd_soc_set_ac97_ops(&hac_ac97_ops); | ||
319 | if (ret != 0) | ||
320 | return ret; | ||
321 | |||
319 | return snd_soc_register_component(&pdev->dev, &sh4_hac_component, | 322 | return snd_soc_register_component(&pdev->dev, &sh4_hac_component, |
320 | sh4_hac_dai, ARRAY_SIZE(sh4_hac_dai)); | 323 | sh4_hac_dai, ARRAY_SIZE(sh4_hac_dai)); |
321 | } | 324 | } |
@@ -323,6 +326,7 @@ static int hac_soc_platform_probe(struct platform_device *pdev) | |||
323 | static int hac_soc_platform_remove(struct platform_device *pdev) | 326 | static int hac_soc_platform_remove(struct platform_device *pdev) |
324 | { | 327 | { |
325 | snd_soc_unregister_component(&pdev->dev); | 328 | snd_soc_unregister_component(&pdev->dev); |
329 | snd_soc_set_ac97_ops(NULL); | ||
326 | return 0; | 330 | return 0; |
327 | } | 331 | } |
328 | 332 | ||
diff --git a/sound/soc/soc-core.c b/sound/soc/soc-core.c index d56bbea6e75e..562d72e04e6e 100644 --- a/sound/soc/soc-core.c +++ b/sound/soc/soc-core.c | |||
@@ -2079,6 +2079,22 @@ int snd_soc_new_ac97_codec(struct snd_soc_codec *codec, | |||
2079 | } | 2079 | } |
2080 | EXPORT_SYMBOL_GPL(snd_soc_new_ac97_codec); | 2080 | EXPORT_SYMBOL_GPL(snd_soc_new_ac97_codec); |
2081 | 2081 | ||
2082 | struct snd_ac97_bus_ops *soc_ac97_ops; | ||
2083 | |||
2084 | int snd_soc_set_ac97_ops(struct snd_ac97_bus_ops *ops) | ||
2085 | { | ||
2086 | if (ops == soc_ac97_ops) | ||
2087 | return 0; | ||
2088 | |||
2089 | if (soc_ac97_ops && ops) | ||
2090 | return -EBUSY; | ||
2091 | |||
2092 | soc_ac97_ops = ops; | ||
2093 | |||
2094 | return 0; | ||
2095 | } | ||
2096 | EXPORT_SYMBOL_GPL(snd_soc_set_ac97_ops); | ||
2097 | |||
2082 | /** | 2098 | /** |
2083 | * snd_soc_free_ac97_codec - free AC97 codec device | 2099 | * snd_soc_free_ac97_codec - free AC97 codec device |
2084 | * @codec: audio codec | 2100 | * @codec: audio codec |
diff --git a/sound/soc/tegra/tegra20_ac97.c b/sound/soc/tegra/tegra20_ac97.c index 48037f784a86..f52eab6d2231 100644 --- a/sound/soc/tegra/tegra20_ac97.c +++ b/sound/soc/tegra/tegra20_ac97.c | |||
@@ -142,13 +142,12 @@ static void tegra20_ac97_codec_write(struct snd_ac97 *ac97_snd, | |||
142 | } while (!time_after(jiffies, timeout)); | 142 | } while (!time_after(jiffies, timeout)); |
143 | } | 143 | } |
144 | 144 | ||
145 | struct snd_ac97_bus_ops soc_ac97_ops = { | 145 | static struct snd_ac97_bus_ops tegra20_ac97_ops = { |
146 | .read = tegra20_ac97_codec_read, | 146 | .read = tegra20_ac97_codec_read, |
147 | .write = tegra20_ac97_codec_write, | 147 | .write = tegra20_ac97_codec_write, |
148 | .reset = tegra20_ac97_codec_reset, | 148 | .reset = tegra20_ac97_codec_reset, |
149 | .warm_reset = tegra20_ac97_codec_warm_reset, | 149 | .warm_reset = tegra20_ac97_codec_warm_reset, |
150 | }; | 150 | }; |
151 | EXPORT_SYMBOL_GPL(soc_ac97_ops); | ||
152 | 151 | ||
153 | static inline void tegra20_ac97_start_playback(struct tegra20_ac97 *ac97) | 152 | static inline void tegra20_ac97_start_playback(struct tegra20_ac97 *ac97) |
154 | { | 153 | { |
@@ -409,6 +408,12 @@ static int tegra20_ac97_platform_probe(struct platform_device *pdev) | |||
409 | goto err_asoc_utils_fini; | 408 | goto err_asoc_utils_fini; |
410 | } | 409 | } |
411 | 410 | ||
411 | ret = snd_soc_set_ac97_ops(&tegra20_ac97_ops); | ||
412 | if (ret) { | ||
413 | dev_err(&pdev->dev, "Failed to set AC'97 ops: %d\n", ret); | ||
414 | goto err_asoc_utils_fini; | ||
415 | } | ||
416 | |||
412 | ret = snd_soc_register_component(&pdev->dev, &tegra20_ac97_component, | 417 | ret = snd_soc_register_component(&pdev->dev, &tegra20_ac97_component, |
413 | &tegra20_ac97_dai, 1); | 418 | &tegra20_ac97_dai, 1); |
414 | if (ret) { | 419 | if (ret) { |
@@ -436,6 +441,7 @@ err_asoc_utils_fini: | |||
436 | tegra_asoc_utils_fini(&ac97->util_data); | 441 | tegra_asoc_utils_fini(&ac97->util_data); |
437 | err_clk_put: | 442 | err_clk_put: |
438 | err: | 443 | err: |
444 | snd_soc_set_ac97_ops(NULL); | ||
439 | return ret; | 445 | return ret; |
440 | } | 446 | } |
441 | 447 | ||
@@ -450,6 +456,8 @@ static int tegra20_ac97_platform_remove(struct platform_device *pdev) | |||
450 | 456 | ||
451 | clk_disable_unprepare(ac97->clk_ac97); | 457 | clk_disable_unprepare(ac97->clk_ac97); |
452 | 458 | ||
459 | snd_soc_set_ac97_ops(NULL); | ||
460 | |||
453 | return 0; | 461 | return 0; |
454 | } | 462 | } |
455 | 463 | ||
diff --git a/sound/soc/txx9/txx9aclc-ac97.c b/sound/soc/txx9/txx9aclc-ac97.c index 8ee8d4220014..4bcce8a3cded 100644 --- a/sound/soc/txx9/txx9aclc-ac97.c +++ b/sound/soc/txx9/txx9aclc-ac97.c | |||
@@ -119,12 +119,11 @@ static void txx9aclc_ac97_cold_reset(struct snd_ac97 *ac97) | |||
119 | } | 119 | } |
120 | 120 | ||
121 | /* AC97 controller operations */ | 121 | /* AC97 controller operations */ |
122 | struct snd_ac97_bus_ops soc_ac97_ops = { | 122 | static struct snd_ac97_bus_ops txx9aclc_ac97_ops = { |
123 | .read = txx9aclc_ac97_read, | 123 | .read = txx9aclc_ac97_read, |
124 | .write = txx9aclc_ac97_write, | 124 | .write = txx9aclc_ac97_write, |
125 | .reset = txx9aclc_ac97_cold_reset, | 125 | .reset = txx9aclc_ac97_cold_reset, |
126 | }; | 126 | }; |
127 | EXPORT_SYMBOL_GPL(soc_ac97_ops); | ||
128 | 127 | ||
129 | static irqreturn_t txx9aclc_ac97_irq(int irq, void *dev_id) | 128 | static irqreturn_t txx9aclc_ac97_irq(int irq, void *dev_id) |
130 | { | 129 | { |
@@ -206,6 +205,10 @@ static int txx9aclc_ac97_dev_probe(struct platform_device *pdev) | |||
206 | if (err < 0) | 205 | if (err < 0) |
207 | return err; | 206 | return err; |
208 | 207 | ||
208 | err = snd_soc_set_ac97_ops(&txx9aclc_ac97_ops); | ||
209 | if (err < 0) | ||
210 | return err; | ||
211 | |||
209 | return snd_soc_register_component(&pdev->dev, &txx9aclc_ac97_component, | 212 | return snd_soc_register_component(&pdev->dev, &txx9aclc_ac97_component, |
210 | &txx9aclc_ac97_dai, 1); | 213 | &txx9aclc_ac97_dai, 1); |
211 | } | 214 | } |
@@ -213,6 +216,7 @@ static int txx9aclc_ac97_dev_probe(struct platform_device *pdev) | |||
213 | static int txx9aclc_ac97_dev_remove(struct platform_device *pdev) | 216 | static int txx9aclc_ac97_dev_remove(struct platform_device *pdev) |
214 | { | 217 | { |
215 | snd_soc_unregister_component(&pdev->dev); | 218 | snd_soc_unregister_component(&pdev->dev); |
219 | snd_soc_set_ac97_ops(NULL); | ||
216 | return 0; | 220 | return 0; |
217 | } | 221 | } |
218 | 222 | ||