]> git.ipfire.org Git - people/ms/linux.git/commitdiff
[ALSA] Fix use after free in opl3_seq and opl3_oss
authorDave Jones <davej@redhat.com>
Thu, 14 Dec 2006 23:39:00 +0000 (00:39 +0100)
committerAdrian Bunk <bunk@stusta.de>
Thu, 14 Dec 2006 23:39:00 +0000 (00:39 +0100)
Don't read from free'd memory.  Also make use of the return
value, and don't register the device if something went wrong
creating the port.

Coverity #954, #955

Signed-off-by: Dave Jones <davej@redhat.com>
Signed-off-by: Adrian Bunk <bunk@stusta.de>
sound/drivers/opl3/opl3_oss.c
sound/drivers/opl3/opl3_seq.c

index 0345ae6476812803e1b539d75ffc54835b576cc8..fccf019a6d85968a5ff8f26953d0f9dba655d654 100644 (file)
@@ -104,8 +104,10 @@ static int snd_opl3_oss_create_port(struct snd_opl3 * opl3)
                                                          voices, voices,
                                                          name);
        if (opl3->oss_chset->port < 0) {
+               int port;
+               port = opl3->oss_chset->port;
                snd_midi_channel_free_set(opl3->oss_chset);
-               return opl3->oss_chset->port;
+               return port;
        }
        return 0;
 }
@@ -136,10 +138,10 @@ void snd_opl3_init_seq_oss(struct snd_opl3 *opl3, char *name)
        arg->oper = oss_callback;
        arg->private_data = opl3;
 
-       snd_opl3_oss_create_port(opl3);
-
-       /* register to OSS synth table */
-       snd_device_register(opl3->card, dev);
+       if (snd_opl3_oss_create_port(opl3)) {
+               /* register to OSS synth table */
+               snd_device_register(opl3->card, dev);
+       }
 }
 
 /* unregister */
index c4ead790008a32ac66c3b35eff538f6dabae1fa8..56b1d1a964a9308a8617dbf342f4373359d5b71f 100644 (file)
@@ -207,8 +207,10 @@ static int snd_opl3_synth_create_port(struct snd_opl3 * opl3)
                                                      16, voices,
                                                      name);
        if (opl3->chset->port < 0) {
+               int port;
+               port = opl3->chset->port;
                snd_midi_channel_free_set(opl3->chset);
-               return opl3->chset->port;
+               return port;
        }
        return 0;
 }
@@ -218,7 +220,7 @@ static int snd_opl3_synth_create_port(struct snd_opl3 * opl3)
 static int snd_opl3_seq_new_device(struct snd_seq_device *dev)
 {
        struct snd_opl3 *opl3;
-       int client;
+       int client, err;
        char name[32];
        int opl_ver;
 
@@ -239,7 +241,11 @@ static int snd_opl3_seq_new_device(struct snd_seq_device *dev)
        if (client < 0)
                return client;
 
-       snd_opl3_synth_create_port(opl3);
+       if ((err = snd_opl3_synth_create_port(opl3)) < 0) {
+               snd_seq_delete_kernel_client(client);
+               opl3->seq_client = -1;
+               return err;
+       }
 
        /* initialize instrument list */
        opl3->ilist = snd_seq_instr_list_new();