[alsa-devel] memory leak in mix/pcm_upmix.c mix/pcm_downmix.c!!!
eg. in function:SND_PCM_PLUGIN_DEFINE_FUNC(upmix) 487 mix = calloc(1, sizeof(*mix)); 488 if (mix == NULL) 489 return -ENOMEM;
mix is allocated here. but at close function, it is not freed, and no __destructor function available to free it.
and in alsa-lib/src/pcm/pcm_extplug.c static int snd_pcm_extplug_close(snd_pcm_t *pcm) { extplug_priv_t *ext = pcm->private_data;
snd_pcm_close(ext->plug.gen.slave); clear_ext_params(ext); if (ext->data->callback->close) { ext->data->callback->close(ext->data); } free(ext); return 0; } this function does NOT free ext->data. and 366 static int upmix_close(snd_pcm_extplug_t *ext) 367 { 368 snd_pcm_upmix_t *mix = (snd_pcm_upmix_t *)ext; 369 free(mix->delayline[0]); 370 free(mix->delayline[1]); 371 return 0; 372 }
and this function does NOT free mix itself.
so I think there is memory leak.
i notice some ioplug plugin does free. but most extplug plugin do NOT free pointer allocated at open function.
2017-08-30 13:51 GMT+08:00 boozer asm asmboozer@gmail.com:
eg. in function:SND_PCM_PLUGIN_DEFINE_FUNC(upmix) 487 mix = calloc(1, sizeof(*mix)); 488 if (mix == NULL) 489 return -ENOMEM;
mix is allocated here. but at close function, it is not freed, and no __destructor function available to free it.
and in alsa-lib/src/pcm/pcm_extplug.c static int snd_pcm_extplug_close(snd_pcm_t *pcm) { extplug_priv_t *ext = pcm->private_data;
snd_pcm_close(ext->plug.gen.slave); clear_ext_params(ext); if (ext->data->callback->close) { ext->data->callback->close(ext->data); } free(ext); return 0;
} this function does NOT free ext->data. and 366 static int upmix_close(snd_pcm_extplug_t *ext) 367 { 368 snd_pcm_upmix_t *mix = (snd_pcm_upmix_t *)ext; 369 free(mix->delayline[0]); 370 free(mix->delayline[1]); 371 return 0; 372 }
and this function does NOT free mix itself.
so I think there is memory leak.
On Wed, 30 Aug 2017 07:51:59 +0200, boozer asm wrote:
eg. in function:SND_PCM_PLUGIN_DEFINE_FUNC(upmix) 487 mix = calloc(1, sizeof(*mix)); 488 if (mix == NULL) 489 return -ENOMEM;
mix is allocated here. but at close function, it is not freed, and no __destructor function available to free it.
and in alsa-lib/src/pcm/pcm_extplug.c static int snd_pcm_extplug_close(snd_pcm_t *pcm) { extplug_priv_t *ext = pcm->private_data;
snd_pcm_close(ext->plug.gen.slave); clear_ext_params(ext); if (ext->data->callback->close) { ext->data->callback->close(ext->data); } free(ext); return 0;
} this function does NOT free ext->data. and 366 static int upmix_close(snd_pcm_extplug_t *ext) 367 { 368 snd_pcm_upmix_t *mix = (snd_pcm_upmix_t *)ext; 369 free(mix->delayline[0]); 370 free(mix->delayline[1]); 371 return 0; 372 }
and this function does NOT free mix itself.
so I think there is memory leak.
It's freed in snd_pcm_extplug_close(). mix is identical with ext in the case of upmix.
Takashi
Hi Takashi,
i think mix is same as ext->data instead ext. ext is of extplug_priv_t *; so it is definitely not mix which is of snd_pcm_upmix_t
33 struct snd_pcm_upmix { 34 snd_pcm_extplug_t ext;
typedef struct snd_pcm_extplug_priv { snd_pcm_plugin_t plug; snd_pcm_extplug_t *data; between upmix and extplug_priv, there is a gap plug, which forbid ext to be converted to mix directly. so free(ext) in snd_pcm_extplug_close does NOT promise it will free mix too.
2017-08-30 15:02 GMT+08:00 Takashi Iwai tiwai@suse.de:
On Wed, 30 Aug 2017 07:51:59 +0200, boozer asm wrote:
eg. in function:SND_PCM_PLUGIN_DEFINE_FUNC(upmix) 487 mix = calloc(1, sizeof(*mix)); 488 if (mix == NULL) 489 return -ENOMEM;
mix is allocated here. but at close function, it is not freed, and no __destructor function available to free it.
and in alsa-lib/src/pcm/pcm_extplug.c static int snd_pcm_extplug_close(snd_pcm_t *pcm) { extplug_priv_t *ext = pcm->private_data;
snd_pcm_close(ext->plug.gen.slave); clear_ext_params(ext); if (ext->data->callback->close) { ext->data->callback->close(ext->data); } free(ext); return 0;
} this function does NOT free ext->data. and 366 static int upmix_close(snd_pcm_extplug_t *ext) 367 { 368 snd_pcm_upmix_t *mix = (snd_pcm_upmix_t *)ext; 369 free(mix->delayline[0]); 370 free(mix->delayline[1]); 371 return 0; 372 }
and this function does NOT free mix itself.
so I think there is memory leak.
It's freed in snd_pcm_extplug_close(). mix is identical with ext in the case of upmix.
Takashi
On Wed, 30 Aug 2017 09:59:59 +0200, boozer asm wrote:
Hi Takashi,
i think mix is same as ext->data instead ext. ext is of extplug_priv_t *; so it is definitely not mix which is of snd_pcm_upmix_t
33 struct snd_pcm_upmix { 34 snd_pcm_extplug_t ext;
typedef struct snd_pcm_extplug_priv { snd_pcm_plugin_t plug; snd_pcm_extplug_t *data; between upmix and extplug_priv, there is a gap plug, which forbid ext to be converted to mix directly. so free(ext) in snd_pcm_extplug_close does NOT promise it will free mix too.
OK, then care to submit patches?
thanks,
Takashi
not sure what's the best place to call free. 1. static int snd_pcm_extplug_close(snd_pcm_t *pcm) { extplug_priv_t *ext = pcm->private_data;
snd_pcm_close(ext->plug.gen.slave); clear_ext_params(ext); if (ext->data->callback->close) { ext->data->callback->close(ext->data); } if (ext->data) free(ext->data); free(ext); return 0; }
2. 366 static int upmix_close(snd_pcm_extplug_t *ext) 367 { 368 snd_pcm_upmix_t *mix = (snd_pcm_upmix_t *)ext; 369 free(mix->delayline[0]); 370 free(mix->delayline[1]); free(mix); 371 return 0; 372 }
3. apply method in alsa-plugins/maemo/alsa-dsp.c:748:static void alsa_dsp_descructor(void) __attribute__ ((destructor));
with each methods, there are some plugins pcm_ files affected.
2017-08-30 16:17 GMT+08:00 Takashi Iwai tiwai@suse.de:
On Wed, 30 Aug 2017 09:59:59 +0200, boozer asm wrote:
Hi Takashi,
i think mix is same as ext->data instead ext. ext is of extplug_priv_t *; so it is definitely not mix which is of snd_pcm_upmix_t
33 struct snd_pcm_upmix { 34 snd_pcm_extplug_t ext;
typedef struct snd_pcm_extplug_priv { snd_pcm_plugin_t plug; snd_pcm_extplug_t *data; between upmix and extplug_priv, there is a gap plug, which forbid ext to
be
converted to mix directly. so free(ext) in snd_pcm_extplug_close does NOT promise it will free mix
too.
OK, then care to submit patches?
thanks,
Takashi
On Wed, 30 Aug 2017 10:28:35 +0200, boozer asm wrote:
not sure what's the best place to call free.
static int snd_pcm_extplug_close(snd_pcm_t *pcm) { extplug_priv_t *ext = pcm->private_data;
snd_pcm_close(ext->plug.gen.slave); clear_ext_params(ext); if (ext->data->callback->close) { ext->data->callback->close(ext->data); } if (ext->data) free(ext->data); free(ext); return 0;
}
366 static int upmix_close(snd_pcm_extplug_t *ext) 367 { 368 snd_pcm_upmix_t *mix = (snd_pcm_upmix_t *)ext; 369 free(mix->delayline[0]); 370 free(mix->delayline[1]); free(mix); 371 return 0; 372 }
- apply method in alsa-plugins/maemo/alsa-dsp.c:748:static void
alsa_dsp_descructor(void) __attribute__ ((destructor));
with each methods, there are some plugins pcm_ files affected.
2 is the way to go. 1 may lead to double-free for the plugins that have already the right code. 3 is too specific to implementation.
Takashi
participants (2)
-
boozer asm
-
Takashi Iwai