diff options
author | Mark Brown <broonie@kernel.org> | 2016-09-29 15:43:55 -0400 |
---|---|---|
committer | Mark Brown <broonie@kernel.org> | 2016-09-29 15:43:55 -0400 |
commit | e4cf86a35ca1bc7c2de3ebb34bb5e8aa79c5bca9 (patch) | |
tree | 79e5ede0b90bed8e16ab3475034d6b7c8c54806c | |
parent | b669010e5878dfda9c1b494f96fc122b67f8d880 (diff) | |
parent | a114580f8f3e5bdefc14d75d6c3ba7032210b980 (diff) |
Merge remote-tracking branch 'asoc/fix/tpa6130a2' into asoc-linus
-rw-r--r-- | sound/soc/codecs/tpa6130a2.c | 49 |
1 files changed, 26 insertions, 23 deletions
diff --git a/sound/soc/codecs/tpa6130a2.c b/sound/soc/codecs/tpa6130a2.c index f1ea052a822e..3b6faed91d7e 100644 --- a/sound/soc/codecs/tpa6130a2.c +++ b/sound/soc/codecs/tpa6130a2.c | |||
@@ -52,7 +52,7 @@ struct tpa6130a2_data { | |||
52 | 52 | ||
53 | static int tpa6130a2_power(struct tpa6130a2_data *data, bool enable) | 53 | static int tpa6130a2_power(struct tpa6130a2_data *data, bool enable) |
54 | { | 54 | { |
55 | int ret; | 55 | int ret = 0, ret2; |
56 | 56 | ||
57 | if (enable) { | 57 | if (enable) { |
58 | ret = regulator_enable(data->supply); | 58 | ret = regulator_enable(data->supply); |
@@ -64,20 +64,34 @@ static int tpa6130a2_power(struct tpa6130a2_data *data, bool enable) | |||
64 | /* Power on */ | 64 | /* Power on */ |
65 | if (data->power_gpio >= 0) | 65 | if (data->power_gpio >= 0) |
66 | gpio_set_value(data->power_gpio, 1); | 66 | gpio_set_value(data->power_gpio, 1); |
67 | |||
68 | /* Sync registers */ | ||
69 | regcache_cache_only(data->regmap, false); | ||
70 | ret = regcache_sync(data->regmap); | ||
71 | if (ret != 0) { | ||
72 | dev_err(data->dev, | ||
73 | "Failed to sync registers: %d\n", ret); | ||
74 | goto regcache_sync_failed; | ||
75 | } | ||
67 | } else { | 76 | } else { |
77 | /* Powered off device does not retain registers. While device | ||
78 | * is off, any register updates (i.e. volume changes) should | ||
79 | * happen in cache only. | ||
80 | */ | ||
81 | regcache_mark_dirty(data->regmap); | ||
82 | regcache_sync_failed: | ||
83 | regcache_cache_only(data->regmap, true); | ||
84 | |||
68 | /* Power off */ | 85 | /* Power off */ |
69 | if (data->power_gpio >= 0) | 86 | if (data->power_gpio >= 0) |
70 | gpio_set_value(data->power_gpio, 0); | 87 | gpio_set_value(data->power_gpio, 0); |
71 | 88 | ||
72 | ret = regulator_disable(data->supply); | 89 | ret2 = regulator_disable(data->supply); |
73 | if (ret != 0) { | 90 | if (ret2 != 0) { |
74 | dev_err(data->dev, | 91 | dev_err(data->dev, |
75 | "Failed to disable supply: %d\n", ret); | 92 | "Failed to disable supply: %d\n", ret2); |
76 | return ret; | 93 | return ret ? ret : ret2; |
77 | } | 94 | } |
78 | |||
79 | /* device regs does not match the cache state anymore */ | ||
80 | regcache_mark_dirty(data->regmap); | ||
81 | } | 95 | } |
82 | 96 | ||
83 | return ret; | 97 | return ret; |
@@ -88,25 +102,14 @@ static int tpa6130a2_power_event(struct snd_soc_dapm_widget *w, | |||
88 | { | 102 | { |
89 | struct snd_soc_component *c = snd_soc_dapm_to_component(w->dapm); | 103 | struct snd_soc_component *c = snd_soc_dapm_to_component(w->dapm); |
90 | struct tpa6130a2_data *data = snd_soc_component_get_drvdata(c); | 104 | struct tpa6130a2_data *data = snd_soc_component_get_drvdata(c); |
91 | int ret; | ||
92 | 105 | ||
93 | /* before widget power up */ | ||
94 | if (SND_SOC_DAPM_EVENT_ON(event)) { | 106 | if (SND_SOC_DAPM_EVENT_ON(event)) { |
95 | /* Turn on the chip */ | 107 | /* Before widget power up: turn chip on, sync registers */ |
96 | tpa6130a2_power(data, true); | 108 | return tpa6130a2_power(data, true); |
97 | /* Sync the registers */ | ||
98 | ret = regcache_sync(data->regmap); | ||
99 | if (ret < 0) { | ||
100 | dev_err(c->dev, "Failed to initialize chip\n"); | ||
101 | tpa6130a2_power(data, false); | ||
102 | return ret; | ||
103 | } | ||
104 | /* after widget power down */ | ||
105 | } else { | 109 | } else { |
106 | tpa6130a2_power(data, false); | 110 | /* After widget power down: turn chip off */ |
111 | return tpa6130a2_power(data, false); | ||
107 | } | 112 | } |
108 | |||
109 | return 0; | ||
110 | } | 113 | } |
111 | 114 | ||
112 | /* | 115 | /* |