Commit 40ed9444 authored by Takashi Iwai's avatar Takashi Iwai

ALSA: timer: Introduce disconnect op to snd_timer_instance

Instead of the previous ugly hack, introduce a new op, disconnect, to
snd_timer_instance object for handling the wake up of pending tasks
more cleanly.

Bugzilla: https://bugzilla.kernel.org/show_bug.cgi?id=109431Signed-off-by: default avatarTakashi Iwai <tiwai@suse.de>
parent 230323da
...@@ -104,6 +104,7 @@ struct snd_timer_instance { ...@@ -104,6 +104,7 @@ struct snd_timer_instance {
int event, int event,
struct timespec * tstamp, struct timespec * tstamp,
unsigned long resolution); unsigned long resolution);
void (*disconnect)(struct snd_timer_instance *timeri);
void *callback_data; void *callback_data;
unsigned long ticks; /* auto-load ticks when expired */ unsigned long ticks; /* auto-load ticks when expired */
unsigned long cticks; /* current ticks */ unsigned long cticks; /* current ticks */
......
...@@ -899,11 +899,6 @@ static int snd_timer_dev_register(struct snd_device *dev) ...@@ -899,11 +899,6 @@ static int snd_timer_dev_register(struct snd_device *dev)
return 0; return 0;
} }
/* just for reference in snd_timer_dev_disconnect() below */
static void snd_timer_user_ccallback(struct snd_timer_instance *timeri,
int event, struct timespec *tstamp,
unsigned long resolution);
static int snd_timer_dev_disconnect(struct snd_device *device) static int snd_timer_dev_disconnect(struct snd_device *device)
{ {
struct snd_timer *timer = device->device_data; struct snd_timer *timer = device->device_data;
...@@ -913,13 +908,8 @@ static int snd_timer_dev_disconnect(struct snd_device *device) ...@@ -913,13 +908,8 @@ static int snd_timer_dev_disconnect(struct snd_device *device)
list_del_init(&timer->device_list); list_del_init(&timer->device_list);
/* wake up pending sleepers */ /* wake up pending sleepers */
list_for_each_entry(ti, &timer->open_list_head, open_list) { list_for_each_entry(ti, &timer->open_list_head, open_list) {
/* FIXME: better to have a ti.disconnect() op */ if (ti->disconnect)
if (ti->ccallback == snd_timer_user_ccallback) { ti->disconnect(ti);
struct snd_timer_user *tu = ti->callback_data;
tu->disconnected = true;
wake_up(&tu->qchange_sleep);
}
} }
mutex_unlock(&register_mutex); mutex_unlock(&register_mutex);
return 0; return 0;
...@@ -1227,6 +1217,14 @@ static void snd_timer_user_ccallback(struct snd_timer_instance *timeri, ...@@ -1227,6 +1217,14 @@ static void snd_timer_user_ccallback(struct snd_timer_instance *timeri,
wake_up(&tu->qchange_sleep); wake_up(&tu->qchange_sleep);
} }
static void snd_timer_user_disconnect(struct snd_timer_instance *timeri)
{
struct snd_timer_user *tu = timeri->callback_data;
tu->disconnected = true;
wake_up(&tu->qchange_sleep);
}
static void snd_timer_user_tinterrupt(struct snd_timer_instance *timeri, static void snd_timer_user_tinterrupt(struct snd_timer_instance *timeri,
unsigned long resolution, unsigned long resolution,
unsigned long ticks) unsigned long ticks)
...@@ -1600,6 +1598,7 @@ static int snd_timer_user_tselect(struct file *file, ...@@ -1600,6 +1598,7 @@ static int snd_timer_user_tselect(struct file *file,
? snd_timer_user_tinterrupt : snd_timer_user_interrupt; ? snd_timer_user_tinterrupt : snd_timer_user_interrupt;
tu->timeri->ccallback = snd_timer_user_ccallback; tu->timeri->ccallback = snd_timer_user_ccallback;
tu->timeri->callback_data = (void *)tu; tu->timeri->callback_data = (void *)tu;
tu->timeri->disconnect = snd_timer_user_disconnect;
} }
__err: __err:
......
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