1*4882a593Smuzhiyun /* SPDX-License-Identifier: GPL-2.0-or-later */ 2*4882a593Smuzhiyun #ifndef __SOUND_TIMER_H 3*4882a593Smuzhiyun #define __SOUND_TIMER_H 4*4882a593Smuzhiyun 5*4882a593Smuzhiyun /* 6*4882a593Smuzhiyun * Timer abstract layer 7*4882a593Smuzhiyun * Copyright (c) by Jaroslav Kysela <perex@perex.cz>, 8*4882a593Smuzhiyun * Abramo Bagnara <abramo@alsa-project.org> 9*4882a593Smuzhiyun */ 10*4882a593Smuzhiyun 11*4882a593Smuzhiyun #include <sound/asound.h> 12*4882a593Smuzhiyun #include <linux/interrupt.h> 13*4882a593Smuzhiyun #include <linux/android_kabi.h> 14*4882a593Smuzhiyun 15*4882a593Smuzhiyun #define snd_timer_chip(timer) ((timer)->private_data) 16*4882a593Smuzhiyun 17*4882a593Smuzhiyun #define SNDRV_TIMER_DEVICES 16 18*4882a593Smuzhiyun 19*4882a593Smuzhiyun #define SNDRV_TIMER_DEV_FLG_PCM 0x10000000 20*4882a593Smuzhiyun 21*4882a593Smuzhiyun #define SNDRV_TIMER_HW_AUTO 0x00000001 /* auto trigger is supported */ 22*4882a593Smuzhiyun #define SNDRV_TIMER_HW_STOP 0x00000002 /* call stop before start */ 23*4882a593Smuzhiyun #define SNDRV_TIMER_HW_SLAVE 0x00000004 /* only slave timer (variable resolution) */ 24*4882a593Smuzhiyun #define SNDRV_TIMER_HW_FIRST 0x00000008 /* first tick can be incomplete */ 25*4882a593Smuzhiyun #define SNDRV_TIMER_HW_WORK 0x00000010 /* timer is called from work */ 26*4882a593Smuzhiyun 27*4882a593Smuzhiyun #define SNDRV_TIMER_IFLG_SLAVE 0x00000001 28*4882a593Smuzhiyun #define SNDRV_TIMER_IFLG_RUNNING 0x00000002 29*4882a593Smuzhiyun #define SNDRV_TIMER_IFLG_START 0x00000004 30*4882a593Smuzhiyun #define SNDRV_TIMER_IFLG_AUTO 0x00000008 /* auto restart */ 31*4882a593Smuzhiyun #define SNDRV_TIMER_IFLG_FAST 0x00000010 /* fast callback (do not use work) */ 32*4882a593Smuzhiyun #define SNDRV_TIMER_IFLG_CALLBACK 0x00000020 /* timer callback is active */ 33*4882a593Smuzhiyun #define SNDRV_TIMER_IFLG_EXCLUSIVE 0x00000040 /* exclusive owner - no more instances */ 34*4882a593Smuzhiyun #define SNDRV_TIMER_IFLG_EARLY_EVENT 0x00000080 /* write early event to the poll queue */ 35*4882a593Smuzhiyun 36*4882a593Smuzhiyun #define SNDRV_TIMER_FLG_CHANGE 0x00000001 37*4882a593Smuzhiyun #define SNDRV_TIMER_FLG_RESCHED 0x00000002 /* need reschedule */ 38*4882a593Smuzhiyun 39*4882a593Smuzhiyun struct snd_timer; 40*4882a593Smuzhiyun 41*4882a593Smuzhiyun struct snd_timer_hardware { 42*4882a593Smuzhiyun /* -- must be filled with low-level driver */ 43*4882a593Smuzhiyun unsigned int flags; /* various flags */ 44*4882a593Smuzhiyun unsigned long resolution; /* average timer resolution for one tick in nsec */ 45*4882a593Smuzhiyun unsigned long resolution_min; /* minimal resolution */ 46*4882a593Smuzhiyun unsigned long resolution_max; /* maximal resolution */ 47*4882a593Smuzhiyun unsigned long ticks; /* max timer ticks per interrupt */ 48*4882a593Smuzhiyun /* -- low-level functions -- */ 49*4882a593Smuzhiyun int (*open) (struct snd_timer * timer); 50*4882a593Smuzhiyun int (*close) (struct snd_timer * timer); 51*4882a593Smuzhiyun unsigned long (*c_resolution) (struct snd_timer * timer); 52*4882a593Smuzhiyun int (*start) (struct snd_timer * timer); 53*4882a593Smuzhiyun int (*stop) (struct snd_timer * timer); 54*4882a593Smuzhiyun int (*set_period) (struct snd_timer * timer, unsigned long period_num, unsigned long period_den); 55*4882a593Smuzhiyun int (*precise_resolution) (struct snd_timer * timer, unsigned long *num, unsigned long *den); 56*4882a593Smuzhiyun 57*4882a593Smuzhiyun ANDROID_KABI_RESERVE(1); 58*4882a593Smuzhiyun }; 59*4882a593Smuzhiyun 60*4882a593Smuzhiyun struct snd_timer { 61*4882a593Smuzhiyun int tmr_class; 62*4882a593Smuzhiyun struct snd_card *card; 63*4882a593Smuzhiyun struct module *module; 64*4882a593Smuzhiyun int tmr_device; 65*4882a593Smuzhiyun int tmr_subdevice; 66*4882a593Smuzhiyun char id[64]; 67*4882a593Smuzhiyun char name[80]; 68*4882a593Smuzhiyun unsigned int flags; 69*4882a593Smuzhiyun int running; /* running instances */ 70*4882a593Smuzhiyun unsigned long sticks; /* schedule ticks */ 71*4882a593Smuzhiyun void *private_data; 72*4882a593Smuzhiyun void (*private_free) (struct snd_timer *timer); 73*4882a593Smuzhiyun struct snd_timer_hardware hw; 74*4882a593Smuzhiyun spinlock_t lock; 75*4882a593Smuzhiyun struct list_head device_list; 76*4882a593Smuzhiyun struct list_head open_list_head; 77*4882a593Smuzhiyun struct list_head active_list_head; 78*4882a593Smuzhiyun struct list_head ack_list_head; 79*4882a593Smuzhiyun struct list_head sack_list_head; /* slow ack list head */ 80*4882a593Smuzhiyun struct work_struct task_work; 81*4882a593Smuzhiyun int max_instances; /* upper limit of timer instances */ 82*4882a593Smuzhiyun int num_instances; /* current number of timer instances */ 83*4882a593Smuzhiyun 84*4882a593Smuzhiyun ANDROID_KABI_RESERVE(1); 85*4882a593Smuzhiyun }; 86*4882a593Smuzhiyun 87*4882a593Smuzhiyun struct snd_timer_instance { 88*4882a593Smuzhiyun struct snd_timer *timer; 89*4882a593Smuzhiyun char *owner; 90*4882a593Smuzhiyun unsigned int flags; 91*4882a593Smuzhiyun void *private_data; 92*4882a593Smuzhiyun void (*private_free) (struct snd_timer_instance *ti); 93*4882a593Smuzhiyun void (*callback) (struct snd_timer_instance *timeri, 94*4882a593Smuzhiyun unsigned long ticks, unsigned long resolution); 95*4882a593Smuzhiyun void (*ccallback) (struct snd_timer_instance * timeri, 96*4882a593Smuzhiyun int event, 97*4882a593Smuzhiyun struct timespec64 * tstamp, 98*4882a593Smuzhiyun unsigned long resolution); 99*4882a593Smuzhiyun void (*disconnect)(struct snd_timer_instance *timeri); 100*4882a593Smuzhiyun void *callback_data; 101*4882a593Smuzhiyun unsigned long ticks; /* auto-load ticks when expired */ 102*4882a593Smuzhiyun unsigned long cticks; /* current ticks */ 103*4882a593Smuzhiyun unsigned long pticks; /* accumulated ticks for callback */ 104*4882a593Smuzhiyun unsigned long resolution; /* current resolution for work */ 105*4882a593Smuzhiyun unsigned long lost; /* lost ticks */ 106*4882a593Smuzhiyun int slave_class; 107*4882a593Smuzhiyun unsigned int slave_id; 108*4882a593Smuzhiyun struct list_head open_list; 109*4882a593Smuzhiyun struct list_head active_list; 110*4882a593Smuzhiyun struct list_head ack_list; 111*4882a593Smuzhiyun struct list_head slave_list_head; 112*4882a593Smuzhiyun struct list_head slave_active_head; 113*4882a593Smuzhiyun struct snd_timer_instance *master; 114*4882a593Smuzhiyun 115*4882a593Smuzhiyun ANDROID_KABI_RESERVE(1); 116*4882a593Smuzhiyun }; 117*4882a593Smuzhiyun 118*4882a593Smuzhiyun /* 119*4882a593Smuzhiyun * Registering 120*4882a593Smuzhiyun */ 121*4882a593Smuzhiyun 122*4882a593Smuzhiyun int snd_timer_new(struct snd_card *card, char *id, struct snd_timer_id *tid, struct snd_timer **rtimer); 123*4882a593Smuzhiyun void snd_timer_notify(struct snd_timer *timer, int event, struct timespec64 *tstamp); 124*4882a593Smuzhiyun int snd_timer_global_new(char *id, int device, struct snd_timer **rtimer); 125*4882a593Smuzhiyun int snd_timer_global_free(struct snd_timer *timer); 126*4882a593Smuzhiyun int snd_timer_global_register(struct snd_timer *timer); 127*4882a593Smuzhiyun 128*4882a593Smuzhiyun struct snd_timer_instance *snd_timer_instance_new(const char *owner); 129*4882a593Smuzhiyun void snd_timer_instance_free(struct snd_timer_instance *timeri); 130*4882a593Smuzhiyun int snd_timer_open(struct snd_timer_instance *timeri, struct snd_timer_id *tid, unsigned int slave_id); 131*4882a593Smuzhiyun void snd_timer_close(struct snd_timer_instance *timeri); 132*4882a593Smuzhiyun unsigned long snd_timer_resolution(struct snd_timer_instance *timeri); 133*4882a593Smuzhiyun int snd_timer_start(struct snd_timer_instance *timeri, unsigned int ticks); 134*4882a593Smuzhiyun int snd_timer_stop(struct snd_timer_instance *timeri); 135*4882a593Smuzhiyun int snd_timer_continue(struct snd_timer_instance *timeri); 136*4882a593Smuzhiyun int snd_timer_pause(struct snd_timer_instance *timeri); 137*4882a593Smuzhiyun 138*4882a593Smuzhiyun void snd_timer_interrupt(struct snd_timer *timer, unsigned long ticks_left); 139*4882a593Smuzhiyun 140*4882a593Smuzhiyun #endif /* __SOUND_TIMER_H */ 141