The error message in dapm_create_or_share_mixmux_kcontrol() refers to the string "name", which may be "long_name" that has been already freed. Delay the release of long_name to the place just before return.
Spotted by coverity CID 1042678.
Signed-off-by: Takashi Iwai tiwai@suse.de --- sound/soc/soc-dapm.c | 19 ++++++++++--------- 1 file changed, 10 insertions(+), 9 deletions(-)
diff --git a/sound/soc/soc-dapm.c b/sound/soc/soc-dapm.c index 2fb0b72..d2ff080 100644 --- a/sound/soc/soc-dapm.c +++ b/sound/soc/soc-dapm.c @@ -687,7 +687,7 @@ static int dapm_create_or_share_mixmux_kcontrol(struct snd_soc_dapm_widget *w, int shared; struct snd_kcontrol *kcontrol; bool wname_in_long_name, kcname_in_long_name; - char *long_name; + char *long_name = NULL; const char *name; int ret;
@@ -745,24 +745,23 @@ static int dapm_create_or_share_mixmux_kcontrol(struct snd_soc_dapm_widget *w,
name = long_name; } else if (wname_in_long_name) { - long_name = NULL; name = w->name + prefix_len; } else { - long_name = NULL; name = w->kcontrol_news[kci].name; }
kcontrol = snd_soc_cnew(&w->kcontrol_news[kci], NULL, name, prefix); - kfree(long_name); - if (!kcontrol) - return -ENOMEM; + if (!kcontrol) { + ret = -ENOMEM; + goto error; + } kcontrol->private_free = dapm_kcontrol_free;
ret = dapm_kcontrol_data_alloc(w, kcontrol); if (ret) { snd_ctl_free_one(kcontrol); - return ret; + goto error; }
ret = snd_ctl_add(card, kcontrol); @@ -770,16 +769,18 @@ static int dapm_create_or_share_mixmux_kcontrol(struct snd_soc_dapm_widget *w, dev_err(dapm->dev, "ASoC: failed to add widget %s dapm kcontrol %s: %d\n", w->name, name, ret); - return ret; + goto error; } }
ret = dapm_kcontrol_add_widget(kcontrol, w); if (ret) - return ret; + goto error;
w->kcontrols[kci] = kcontrol;
+ error: + kfree(long_name); return 0; }