diff options
author | Mark Brown <broonie@opensource.wolfsonmicro.com> | 2012-09-10 05:07:24 -0400 |
---|---|---|
committer | Mark Brown <broonie@opensource.wolfsonmicro.com> | 2012-09-10 05:25:47 -0400 |
commit | 59ac2149aee9b69732dad602ea250ecb60b9e617 (patch) | |
tree | fd5828205bd28b3e8406f4731a80cecba6a06976 | |
parent | b9288f49dc5ac8342cc34163093c9f7d096b6378 (diff) |
ASoC: wm8523: Move device ID verification and reset to I2C probe
Ensure that we have confirmed that we've got the device in place before
we register with ASoC.
Signed-off-by: Mark Brown <broonie@opensource.wolfsonmicro.com>
-rw-r--r-- | sound/soc/codecs/wm8523.c | 84 |
1 files changed, 38 insertions, 46 deletions
diff --git a/sound/soc/codecs/wm8523.c b/sound/soc/codecs/wm8523.c index d7d5fe6866a6..8d5c27673501 100644 --- a/sound/soc/codecs/wm8523.c +++ b/sound/soc/codecs/wm8523.c | |||
@@ -68,11 +68,6 @@ static bool wm8523_volatile_register(struct device *dev, unsigned int reg) | |||
68 | } | 68 | } |
69 | } | 69 | } |
70 | 70 | ||
71 | static int wm8523_reset(struct snd_soc_codec *codec) | ||
72 | { | ||
73 | return snd_soc_write(codec, WM8523_DEVICE_ID, 0); | ||
74 | } | ||
75 | |||
76 | static const DECLARE_TLV_DB_SCALE(dac_tlv, -10000, 25, 0); | 71 | static const DECLARE_TLV_DB_SCALE(dac_tlv, -10000, 25, 0); |
77 | 72 | ||
78 | static const char *wm8523_zd_count_text[] = { | 73 | static const char *wm8523_zd_count_text[] = { |
@@ -409,38 +404,6 @@ static int wm8523_probe(struct snd_soc_codec *codec) | |||
409 | return ret; | 404 | return ret; |
410 | } | 405 | } |
411 | 406 | ||
412 | ret = regulator_bulk_enable(ARRAY_SIZE(wm8523->supplies), | ||
413 | wm8523->supplies); | ||
414 | if (ret != 0) { | ||
415 | dev_err(codec->dev, "Failed to enable supplies: %d\n", ret); | ||
416 | goto err_get; | ||
417 | } | ||
418 | |||
419 | ret = snd_soc_read(codec, WM8523_DEVICE_ID); | ||
420 | if (ret < 0) { | ||
421 | dev_err(codec->dev, "Failed to read ID register\n"); | ||
422 | goto err_enable; | ||
423 | } | ||
424 | if (ret != 0x8523) { | ||
425 | dev_err(codec->dev, "Device is not a WM8523, ID is %x\n", ret); | ||
426 | ret = -EINVAL; | ||
427 | goto err_enable; | ||
428 | } | ||
429 | |||
430 | ret = snd_soc_read(codec, WM8523_REVISION); | ||
431 | if (ret < 0) { | ||
432 | dev_err(codec->dev, "Failed to read revision register\n"); | ||
433 | goto err_enable; | ||
434 | } | ||
435 | dev_info(codec->dev, "revision %c\n", | ||
436 | (ret & WM8523_CHIP_REV_MASK) + 'A'); | ||
437 | |||
438 | ret = wm8523_reset(codec); | ||
439 | if (ret < 0) { | ||
440 | dev_err(codec->dev, "Failed to issue reset\n"); | ||
441 | goto err_enable; | ||
442 | } | ||
443 | |||
444 | /* Change some default settings - latch VU and enable ZC */ | 407 | /* Change some default settings - latch VU and enable ZC */ |
445 | snd_soc_update_bits(codec, WM8523_DAC_GAINR, | 408 | snd_soc_update_bits(codec, WM8523_DAC_GAINR, |
446 | WM8523_DACR_VU, WM8523_DACR_VU); | 409 | WM8523_DACR_VU, WM8523_DACR_VU); |
@@ -448,16 +411,7 @@ static int wm8523_probe(struct snd_soc_codec *codec) | |||
448 | 411 | ||
449 | wm8523_set_bias_level(codec, SND_SOC_BIAS_STANDBY); | 412 | wm8523_set_bias_level(codec, SND_SOC_BIAS_STANDBY); |
450 | 413 | ||
451 | /* Bias level configuration will have done an extra enable */ | ||
452 | regulator_bulk_disable(ARRAY_SIZE(wm8523->supplies), wm8523->supplies); | ||
453 | |||
454 | return 0; | 414 | return 0; |
455 | |||
456 | err_enable: | ||
457 | regulator_bulk_disable(ARRAY_SIZE(wm8523->supplies), wm8523->supplies); | ||
458 | err_get: | ||
459 | |||
460 | return ret; | ||
461 | } | 415 | } |
462 | 416 | ||
463 | static int wm8523_remove(struct snd_soc_codec *codec) | 417 | static int wm8523_remove(struct snd_soc_codec *codec) |
@@ -503,6 +457,7 @@ static __devinit int wm8523_i2c_probe(struct i2c_client *i2c, | |||
503 | const struct i2c_device_id *id) | 457 | const struct i2c_device_id *id) |
504 | { | 458 | { |
505 | struct wm8523_priv *wm8523; | 459 | struct wm8523_priv *wm8523; |
460 | unsigned int val; | ||
506 | int ret, i; | 461 | int ret, i; |
507 | 462 | ||
508 | wm8523 = devm_kzalloc(&i2c->dev, sizeof(struct wm8523_priv), | 463 | wm8523 = devm_kzalloc(&i2c->dev, sizeof(struct wm8523_priv), |
@@ -527,6 +482,40 @@ static __devinit int wm8523_i2c_probe(struct i2c_client *i2c, | |||
527 | return ret; | 482 | return ret; |
528 | } | 483 | } |
529 | 484 | ||
485 | ret = regulator_bulk_enable(ARRAY_SIZE(wm8523->supplies), | ||
486 | wm8523->supplies); | ||
487 | if (ret != 0) { | ||
488 | dev_err(&i2c->dev, "Failed to enable supplies: %d\n", ret); | ||
489 | return ret; | ||
490 | } | ||
491 | |||
492 | ret = regmap_read(wm8523->regmap, WM8523_DEVICE_ID, &val); | ||
493 | if (ret < 0) { | ||
494 | dev_err(&i2c->dev, "Failed to read ID register\n"); | ||
495 | goto err_enable; | ||
496 | } | ||
497 | if (val != 0x8523) { | ||
498 | dev_err(&i2c->dev, "Device is not a WM8523, ID is %x\n", ret); | ||
499 | ret = -EINVAL; | ||
500 | goto err_enable; | ||
501 | } | ||
502 | |||
503 | ret = regmap_read(wm8523->regmap, WM8523_REVISION, &val); | ||
504 | if (ret < 0) { | ||
505 | dev_err(&i2c->dev, "Failed to read revision register\n"); | ||
506 | goto err_enable; | ||
507 | } | ||
508 | dev_info(&i2c->dev, "revision %c\n", | ||
509 | (val & WM8523_CHIP_REV_MASK) + 'A'); | ||
510 | |||
511 | ret = regmap_write(wm8523->regmap, WM8523_DEVICE_ID, 0x8523); | ||
512 | if (ret != 0) { | ||
513 | dev_err(&i2c->dev, "Failed to reset device: %d\n", ret); | ||
514 | goto err_enable; | ||
515 | } | ||
516 | |||
517 | regulator_bulk_disable(ARRAY_SIZE(wm8523->supplies), wm8523->supplies); | ||
518 | |||
530 | i2c_set_clientdata(i2c, wm8523); | 519 | i2c_set_clientdata(i2c, wm8523); |
531 | 520 | ||
532 | ret = snd_soc_register_codec(&i2c->dev, | 521 | ret = snd_soc_register_codec(&i2c->dev, |
@@ -534,6 +523,9 @@ static __devinit int wm8523_i2c_probe(struct i2c_client *i2c, | |||
534 | 523 | ||
535 | return ret; | 524 | return ret; |
536 | 525 | ||
526 | err_enable: | ||
527 | regulator_bulk_disable(ARRAY_SIZE(wm8523->supplies), wm8523->supplies); | ||
528 | return ret; | ||
537 | } | 529 | } |
538 | 530 | ||
539 | static __devexit int wm8523_i2c_remove(struct i2c_client *client) | 531 | static __devexit int wm8523_i2c_remove(struct i2c_client *client) |