Commit b32425ac authored by Takashi Iwai's avatar Takashi Iwai Committed by Jaroslav Kysela
Browse files

[ALSA] Fix possible races in timer callbacks



Fix possible races in timer callbacks.

Signed-off-by: default avatarTakashi Iwai <tiwai@suse.de>
parent 2eb061f4
Loading
Loading
Loading
Loading
+3 −2
Original line number Diff line number Diff line
@@ -662,12 +662,13 @@ void snd_timer_interrupt(struct snd_timer * timer, unsigned long ticks_left)
	struct snd_timer_instance *ti, *ts;
	unsigned long resolution, ticks;
	struct list_head *p, *q, *n, *ack_list_head;
	unsigned long flags;
	int use_tasklet = 0;

	if (timer == NULL)
		return;

	spin_lock(&timer->lock);
	spin_lock_irqsave(&timer->lock, flags);

	/* remember the current resolution */
	if (timer->hw.c_resolution)
@@ -752,7 +753,7 @@ void snd_timer_interrupt(struct snd_timer * timer, unsigned long ticks_left)

	/* do we have any slow callbacks? */
	use_tasklet = !list_empty(&timer->sack_list_head);
	spin_unlock(&timer->lock);
	spin_unlock_irqrestore(&timer->lock, flags);

	if (use_tasklet)
		tasklet_hi_schedule(&timer->task_queue);
+5 −5
Original line number Diff line number Diff line
@@ -231,8 +231,9 @@ static int snd_card_dummy_pcm_prepare(struct snd_pcm_substream *substream)
static void snd_card_dummy_pcm_timer_function(unsigned long data)
{
	struct snd_dummy_pcm *dpcm = (struct snd_dummy_pcm *)data;
	unsigned long flags;
	
	spin_lock(&dpcm->lock);
	spin_lock_irqsave(&dpcm->lock, flags);
	dpcm->timer.expires = 1 + jiffies;
	add_timer(&dpcm->timer);
	dpcm->pcm_irq_pos += dpcm->pcm_jiffie;
@@ -240,11 +241,10 @@ static void snd_card_dummy_pcm_timer_function(unsigned long data)
	dpcm->pcm_buf_pos %= dpcm->pcm_size;
	if (dpcm->pcm_irq_pos >= dpcm->pcm_count) {
		dpcm->pcm_irq_pos %= dpcm->pcm_count;
		spin_unlock(&dpcm->lock);
		spin_unlock_irqrestore(&dpcm->lock, flags);
		snd_pcm_period_elapsed(dpcm->substream);
		spin_lock(&dpcm->lock);
	}
	spin_unlock(&dpcm->lock);
	} else
		spin_unlock_irqrestore(&dpcm->lock, flags);
}

static snd_pcm_uframes_t snd_card_dummy_pcm_pointer(struct snd_pcm_substream *substream)
+3 −2
Original line number Diff line number Diff line
@@ -133,12 +133,13 @@ irqreturn_t snd_mpu401_uart_interrupt(int irq, void *dev_id, struct pt_regs *reg
static void snd_mpu401_uart_timer(unsigned long data)
{
	struct snd_mpu401 *mpu = (struct snd_mpu401 *)data;
	unsigned long flags;

	spin_lock(&mpu->timer_lock);
	spin_lock_irqsave(&mpu->timer_lock, flags);
	/*mpu->mode |= MPU401_MODE_TIMER;*/
	mpu->timer.expires = 1 + jiffies;
	add_timer(&mpu->timer);
	spin_unlock(&mpu->timer_lock);
	spin_unlock_irqrestore(&mpu->timer_lock, flags);
	if (mpu->rmidi)
		_snd_mpu401_uart_interrupt(mpu);
}
+3 −2
Original line number Diff line number Diff line
@@ -238,10 +238,11 @@ void snd_opl3_timer_func(unsigned long data)
{

	struct snd_opl3 *opl3 = (struct snd_opl3 *)data;
	unsigned long flags;
	int again = 0;
	int i;

	spin_lock(&opl3->sys_timer_lock);
	spin_lock_irqsave(&opl3->sys_timer_lock, flags);
	for (i = 0; i < opl3->max_voices; i++) {
		struct snd_opl3_voice *vp = &opl3->voices[i];
		if (vp->state > 0 && vp->note_off_check) {
@@ -257,7 +258,7 @@ void snd_opl3_timer_func(unsigned long data)
	} else {
		opl3->sys_timer_status = 0;
	}
	spin_unlock(&opl3->sys_timer_lock);
	spin_unlock_irqrestore(&opl3->sys_timer_lock, flags);
}

/*
+3 −2
Original line number Diff line number Diff line
@@ -609,8 +609,9 @@ static void snd_korg1212_SendStopAndWait(struct snd_korg1212 *korg1212)
static void snd_korg1212_timer_func(unsigned long data)
{
        struct snd_korg1212 *korg1212 = (struct snd_korg1212 *) data;
	unsigned long flags;
	
	spin_lock(&korg1212->lock);
	spin_lock_irqsave(&korg1212->lock, flags);
	if (korg1212->sharedBufferPtr->cardCommand == 0) {
		/* ack'ed */
		korg1212->stop_pending_cnt = 0;
@@ -632,7 +633,7 @@ static void snd_korg1212_timer_func(unsigned long data)
					   stateName[korg1212->cardState]);
		}
	}
	spin_unlock(&korg1212->lock);
	spin_unlock_irqrestore(&korg1212->lock, flags);
}

static int snd_korg1212_TurnOnIdleMonitor(struct snd_korg1212 *korg1212)
Loading