diff --git a/sound/core/seq/seq_clientmgr.c b/sound/core/seq/seq_clientmgr.c index 0d0e0c2651c2..7fa0219c9758 100644 --- a/sound/core/seq/seq_clientmgr.c +++ b/sound/core/seq/seq_clientmgr.c @@ -1014,7 +1014,7 @@ static ssize_t snd_seq_write(struct file *file, const char __user *buf, { struct snd_seq_client *client = file->private_data; int written = 0, len; - int err; + int err, handled; struct snd_seq_event event; if (!(snd_seq_file_flags(file) & SNDRV_SEQ_LFLG_OUTPUT)) @@ -1027,6 +1027,8 @@ static ssize_t snd_seq_write(struct file *file, const char __user *buf, if (!client->accept_output || client->pool == NULL) return -ENXIO; + repeat: + handled = 0; /* allocate the pool now if the pool is not allocated yet */ mutex_lock(&client->ioctl_mutex); if (client->pool->size > 0 && !snd_seq_write_pool_allocated(client)) { @@ -1086,12 +1088,19 @@ static ssize_t snd_seq_write(struct file *file, const char __user *buf, 0, 0, &client->ioctl_mutex); if (err < 0) break; + handled++; __skip_event: /* Update pointers and counts */ count -= len; buf += len; written += len; + + /* let's have a coffee break if too many events are queued */ + if (++handled >= 200) { + mutex_unlock(&client->ioctl_mutex); + goto repeat; + } } out: