diff options
author | Takashi Iwai <tiwai@suse.de> | 2009-02-11 08:55:59 -0500 |
---|---|---|
committer | Takashi Iwai <tiwai@suse.de> | 2009-03-09 10:17:21 -0400 |
commit | f9d202833d0beac09ef1c6a41305151da4fe5d4c (patch) | |
tree | 4bd6b75853a5bad34fb17d95afa33b1e3f4997bb | |
parent | fec6c6fec3e20637bee5d276fb61dd8b49a3f9cc (diff) |
ALSA: rawmidi - Fix possible race in open
The module refcount should be handled in the register_mutex to avoid
possible races with module unloading.
Signed-off-by: Takashi Iwai <tiwai@suse.de>
-rw-r--r-- | sound/core/rawmidi.c | 14 |
1 files changed, 7 insertions, 7 deletions
diff --git a/sound/core/rawmidi.c b/sound/core/rawmidi.c index 002777ba336a..60f33e9412ad 100644 --- a/sound/core/rawmidi.c +++ b/sound/core/rawmidi.c | |||
@@ -237,15 +237,16 @@ int snd_rawmidi_kernel_open(struct snd_card *card, int device, int subdevice, | |||
237 | rfile->input = rfile->output = NULL; | 237 | rfile->input = rfile->output = NULL; |
238 | mutex_lock(®ister_mutex); | 238 | mutex_lock(®ister_mutex); |
239 | rmidi = snd_rawmidi_search(card, device); | 239 | rmidi = snd_rawmidi_search(card, device); |
240 | mutex_unlock(®ister_mutex); | ||
241 | if (rmidi == NULL) { | 240 | if (rmidi == NULL) { |
242 | err = -ENODEV; | 241 | mutex_unlock(®ister_mutex); |
243 | goto __error1; | 242 | return -ENODEV; |
244 | } | 243 | } |
245 | if (!try_module_get(rmidi->card->module)) { | 244 | if (!try_module_get(rmidi->card->module)) { |
246 | err = -EFAULT; | 245 | mutex_unlock(®ister_mutex); |
247 | goto __error1; | 246 | return -ENXIO; |
248 | } | 247 | } |
248 | mutex_unlock(®ister_mutex); | ||
249 | |||
249 | if (!(mode & SNDRV_RAWMIDI_LFLG_NOOPENLOCK)) | 250 | if (!(mode & SNDRV_RAWMIDI_LFLG_NOOPENLOCK)) |
250 | mutex_lock(&rmidi->open_mutex); | 251 | mutex_lock(&rmidi->open_mutex); |
251 | if (mode & SNDRV_RAWMIDI_LFLG_INPUT) { | 252 | if (mode & SNDRV_RAWMIDI_LFLG_INPUT) { |
@@ -370,10 +371,9 @@ int snd_rawmidi_kernel_open(struct snd_card *card, int device, int subdevice, | |||
370 | snd_rawmidi_runtime_free(sinput); | 371 | snd_rawmidi_runtime_free(sinput); |
371 | if (output != NULL) | 372 | if (output != NULL) |
372 | snd_rawmidi_runtime_free(soutput); | 373 | snd_rawmidi_runtime_free(soutput); |
373 | module_put(rmidi->card->module); | ||
374 | if (!(mode & SNDRV_RAWMIDI_LFLG_NOOPENLOCK)) | 374 | if (!(mode & SNDRV_RAWMIDI_LFLG_NOOPENLOCK)) |
375 | mutex_unlock(&rmidi->open_mutex); | 375 | mutex_unlock(&rmidi->open_mutex); |
376 | __error1: | 376 | module_put(rmidi->card->module); |
377 | return err; | 377 | return err; |
378 | } | 378 | } |
379 | 379 | ||