Skip to content

Commit b306e84

Browse files
committed
ASoC: wm8961: Move device identification and reset to I2C probe
This is more idiomatic as it means we verify that the device is there prior to trying to do the card probe. Signed-off-by: Mark Brown <[email protected]>
1 parent 35ecf7c commit b306e84

File tree

1 file changed

+33
-27
lines changed

1 file changed

+33
-27
lines changed

sound/soc/codecs/wm8961.c

Lines changed: 33 additions & 27 deletions
Original file line numberDiff line numberDiff line change
@@ -187,11 +187,6 @@ static bool wm8961_readable(struct device *dev, unsigned int reg)
187187
}
188188
}
189189

190-
static int wm8961_reset(struct snd_soc_codec *codec)
191-
{
192-
return snd_soc_write(codec, WM8961_SOFTWARE_RESET, 0);
193-
}
194-
195190
/*
196191
* The headphone output supports special anti-pop sequences giving
197192
* silent power up and power down.
@@ -840,7 +835,6 @@ static struct snd_soc_dai_driver wm8961_dai = {
840835

841836
static int wm8961_probe(struct snd_soc_codec *codec)
842837
{
843-
struct wm8961_priv *wm8961 = snd_soc_codec_get_drvdata(codec);
844838
struct snd_soc_dapm_context *dapm = &codec->dapm;
845839
int ret = 0;
846840
u16 reg;
@@ -851,27 +845,6 @@ static int wm8961_probe(struct snd_soc_codec *codec)
851845
return ret;
852846
}
853847

854-
reg = snd_soc_read(codec, WM8961_SOFTWARE_RESET);
855-
if (reg != 0x1801) {
856-
dev_err(codec->dev, "Device is not a WM8961: ID=0x%x\n", reg);
857-
return -EINVAL;
858-
}
859-
860-
/* This isn't volatile - readback doesn't correspond to write */
861-
regcache_cache_bypass(wm8961->regmap, true);
862-
reg = snd_soc_read(codec, WM8961_RIGHT_INPUT_VOLUME);
863-
regcache_cache_bypass(wm8961->regmap, false);
864-
dev_info(codec->dev, "WM8961 family %d revision %c\n",
865-
(reg & WM8961_DEVICE_ID_MASK) >> WM8961_DEVICE_ID_SHIFT,
866-
((reg & WM8961_CHIP_REV_MASK) >> WM8961_CHIP_REV_SHIFT)
867-
+ 'A');
868-
869-
ret = wm8961_reset(codec);
870-
if (ret < 0) {
871-
dev_err(codec->dev, "Failed to issue reset\n");
872-
return ret;
873-
}
874-
875848
/* Enable class W */
876849
reg = snd_soc_read(codec, WM8961_CHARGE_PUMP_B);
877850
reg |= WM8961_CP_DYN_PWR_MASK;
@@ -968,6 +941,7 @@ static __devinit int wm8961_i2c_probe(struct i2c_client *i2c,
968941
const struct i2c_device_id *id)
969942
{
970943
struct wm8961_priv *wm8961;
944+
unsigned int val;
971945
int ret;
972946

973947
wm8961 = devm_kzalloc(&i2c->dev, sizeof(struct wm8961_priv),
@@ -979,6 +953,38 @@ static __devinit int wm8961_i2c_probe(struct i2c_client *i2c,
979953
if (IS_ERR(wm8961->regmap))
980954
return PTR_ERR(wm8961->regmap);
981955

956+
ret = regmap_read(wm8961->regmap, WM8961_SOFTWARE_RESET, &val);
957+
if (ret != 0) {
958+
dev_err(&i2c->dev, "Failed to read chip ID: %d\n", ret);
959+
return ret;
960+
}
961+
962+
if (val != 0x1801) {
963+
dev_err(&i2c->dev, "Device is not a WM8961: ID=0x%x\n", val);
964+
return -EINVAL;
965+
}
966+
967+
/* This isn't volatile - readback doesn't correspond to write */
968+
regcache_cache_bypass(wm8961->regmap, true);
969+
ret = regmap_read(wm8961->regmap, WM8961_RIGHT_INPUT_VOLUME, &val);
970+
regcache_cache_bypass(wm8961->regmap, false);
971+
972+
if (ret != 0) {
973+
dev_err(&i2c->dev, "Failed to read chip revision: %d\n", ret);
974+
return ret;
975+
}
976+
977+
dev_info(&i2c->dev, "WM8961 family %d revision %c\n",
978+
(val & WM8961_DEVICE_ID_MASK) >> WM8961_DEVICE_ID_SHIFT,
979+
((val & WM8961_CHIP_REV_MASK) >> WM8961_CHIP_REV_SHIFT)
980+
+ 'A');
981+
982+
ret = regmap_write(wm8961->regmap, WM8961_SOFTWARE_RESET, 0x1801);
983+
if (ret != 0) {
984+
dev_err(&i2c->dev, "Failed to issue reset: %d\n", ret);
985+
return ret;
986+
}
987+
982988
i2c_set_clientdata(i2c, wm8961);
983989

984990
ret = snd_soc_register_codec(&i2c->dev,

0 commit comments

Comments
 (0)