Commit dec242b6 authored by Takashi Iwai's avatar Takashi Iwai

ALSA: gus: Fix memory leaks at memory allocator error paths

When snd_gf1_mem_xalloc() returns NULL, the current code still leaves
the formerly allocated block.name string but returns an error
immediately.  This patch does code-refactoring to move the kstrdup()
call itself into snd_gf1_mem_xalloc() and deals with the resource free
in the helper code by itself for fixing those memory leaks.
Suggested-by: default avatarJaroslav Kysela <perex@perex.cz>
Reviewed-by: default avatarJaroslav Kysela <perex@perex.cz>
Link: https://lore.kernel.org/r/20211213132444.22385-2-tiwai@suse.de
Link: https://lore.kernel.org/r/20211213141512.27359-1-tiwai@suse.deSigned-off-by: default avatarTakashi Iwai <tiwai@suse.de>
parent c2f51415
...@@ -24,8 +24,9 @@ void snd_gf1_mem_lock(struct snd_gf1_mem * alloc, int xup) ...@@ -24,8 +24,9 @@ void snd_gf1_mem_lock(struct snd_gf1_mem * alloc, int xup)
} }
} }
static struct snd_gf1_mem_block *snd_gf1_mem_xalloc(struct snd_gf1_mem * alloc, static struct snd_gf1_mem_block *
struct snd_gf1_mem_block * block) snd_gf1_mem_xalloc(struct snd_gf1_mem *alloc, struct snd_gf1_mem_block *block,
const char *name)
{ {
struct snd_gf1_mem_block *pblock, *nblock; struct snd_gf1_mem_block *pblock, *nblock;
...@@ -33,6 +34,12 @@ static struct snd_gf1_mem_block *snd_gf1_mem_xalloc(struct snd_gf1_mem * alloc, ...@@ -33,6 +34,12 @@ static struct snd_gf1_mem_block *snd_gf1_mem_xalloc(struct snd_gf1_mem * alloc,
if (nblock == NULL) if (nblock == NULL)
return NULL; return NULL;
*nblock = *block; *nblock = *block;
nblock->name = kstrdup(name, GFP_KERNEL);
if (!nblock->name) {
kfree(nblock);
return NULL;
}
pblock = alloc->first; pblock = alloc->first;
while (pblock) { while (pblock) {
if (pblock->ptr > nblock->ptr) { if (pblock->ptr > nblock->ptr) {
...@@ -198,12 +205,7 @@ struct snd_gf1_mem_block *snd_gf1_mem_alloc(struct snd_gf1_mem * alloc, int owne ...@@ -198,12 +205,7 @@ struct snd_gf1_mem_block *snd_gf1_mem_alloc(struct snd_gf1_mem * alloc, int owne
if (share_id != NULL) if (share_id != NULL)
memcpy(&block.share_id, share_id, sizeof(block.share_id)); memcpy(&block.share_id, share_id, sizeof(block.share_id));
block.owner = owner; block.owner = owner;
block.name = kstrdup(name, GFP_KERNEL); nblock = snd_gf1_mem_xalloc(alloc, &block, name);
if (block.name == NULL) {
snd_gf1_mem_lock(alloc, 1);
return NULL;
}
nblock = snd_gf1_mem_xalloc(alloc, &block);
snd_gf1_mem_lock(alloc, 1); snd_gf1_mem_lock(alloc, 1);
return nblock; return nblock;
} }
...@@ -240,14 +242,12 @@ int snd_gf1_mem_init(struct snd_gus_card * gus) ...@@ -240,14 +242,12 @@ int snd_gf1_mem_init(struct snd_gus_card * gus)
if (gus->gf1.enh_mode) { if (gus->gf1.enh_mode) {
block.ptr = 0; block.ptr = 0;
block.size = 1024; block.size = 1024;
block.name = kstrdup("InterWave LFOs", GFP_KERNEL); if (!snd_gf1_mem_xalloc(alloc, &block, "InterWave LFOs"))
if (block.name == NULL || snd_gf1_mem_xalloc(alloc, &block) == NULL)
return -ENOMEM; return -ENOMEM;
} }
block.ptr = gus->gf1.default_voice_address; block.ptr = gus->gf1.default_voice_address;
block.size = 4; block.size = 4;
block.name = kstrdup("Voice default (NULL's)", GFP_KERNEL); if (!snd_gf1_mem_xalloc(alloc, &block, "Voice default (NULL's)"))
if (block.name == NULL || snd_gf1_mem_xalloc(alloc, &block) == NULL)
return -ENOMEM; return -ENOMEM;
#ifdef CONFIG_SND_DEBUG #ifdef CONFIG_SND_DEBUG
snd_card_ro_proc_new(gus->card, "gusmem", gus, snd_gf1_mem_info_read); snd_card_ro_proc_new(gus->card, "gusmem", gus, snd_gf1_mem_info_read);
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment