aboutsummaryrefslogtreecommitdiffstats
path: root/sound/core/sound.c
diff options
context:
space:
mode:
authorClemens Ladisch <clemens@ladisch.de>2005-11-20 08:06:59 -0500
committerJaroslav Kysela <perex@suse.cz>2006-01-03 06:29:17 -0500
commitf87135f56cb266e031f5ec081dfbde7e43f55e80 (patch)
treec048abae6bb04df53f5d8d7dcffbf2c28bc638ff /sound/core/sound.c
parent6983b7240cd229787c3ee00e663ea94ea649d96a (diff)
[ALSA] dynamic minors (3/6): store device-specific object pointers dynamically
Instead of storing the pointers to the device-specific structures in an array, put them into the struct snd_minor, and look them up dynamically. This makes the device type modules independent of the minor number encoding. Signed-off-by: Clemens Ladisch <clemens@ladisch.de>
Diffstat (limited to 'sound/core/sound.c')
-rw-r--r--sound/core/sound.c46
1 files changed, 40 insertions, 6 deletions
diff --git a/sound/core/sound.c b/sound/core/sound.c
index a509f49fa0b..1e5eca54692 100644
--- a/sound/core/sound.c
+++ b/sound/core/sound.c
@@ -60,7 +60,6 @@ MODULE_ALIAS_CHARDEV_MAJOR(CONFIG_SND_MAJOR);
60int snd_ecards_limit; 60int snd_ecards_limit;
61 61
62static struct snd_minor *snd_minors[SNDRV_OS_MINORS]; 62static struct snd_minor *snd_minors[SNDRV_OS_MINORS];
63
64static DECLARE_MUTEX(sound_mutex); 63static DECLARE_MUTEX(sound_mutex);
65 64
66extern struct class *sound_class; 65extern struct class *sound_class;
@@ -107,6 +106,31 @@ static void snd_request_other(int minor)
107 106
108#endif /* request_module support */ 107#endif /* request_module support */
109 108
109/**
110 * snd_lookup_minor_data - get user data of a registered device
111 * @minor: the minor number
112 * @type: device type (SNDRV_DEVICE_TYPE_XXX)
113 *
114 * Checks that a minor device with the specified type is registered, and returns
115 * its user data pointer.
116 */
117void *snd_lookup_minor_data(unsigned int minor, int type)
118{
119 struct snd_minor *mreg;
120 void *private_data;
121
122 if (minor > ARRAY_SIZE(snd_minors))
123 return NULL;
124 down(&sound_mutex);
125 mreg = snd_minors[minor];
126 if (mreg && mreg->type == type)
127 private_data = mreg->private_data;
128 else
129 private_data = NULL;
130 up(&sound_mutex);
131 return private_data;
132}
133
110static int snd_open(struct inode *inode, struct file *file) 134static int snd_open(struct inode *inode, struct file *file)
111{ 135{
112 int minor = iminor(inode); 136 int minor = iminor(inode);
@@ -183,6 +207,7 @@ static int snd_kernel_minor(int type, struct snd_card *card, int dev)
183 * @card: the card instance 207 * @card: the card instance
184 * @dev: the device index 208 * @dev: the device index
185 * @f_ops: the file operations 209 * @f_ops: the file operations
210 * @private_data: user pointer for f_ops->open()
186 * @name: the device file name 211 * @name: the device file name
187 * 212 *
188 * Registers an ALSA device file for the given card. 213 * Registers an ALSA device file for the given card.
@@ -191,7 +216,8 @@ static int snd_kernel_minor(int type, struct snd_card *card, int dev)
191 * Retrurns zero if successful, or a negative error code on failure. 216 * Retrurns zero if successful, or a negative error code on failure.
192 */ 217 */
193int snd_register_device(int type, struct snd_card *card, int dev, 218int snd_register_device(int type, struct snd_card *card, int dev,
194 struct file_operations *f_ops, const char *name) 219 struct file_operations *f_ops, void *private_data,
220 const char *name)
195{ 221{
196 int minor = snd_kernel_minor(type, card, dev); 222 int minor = snd_kernel_minor(type, card, dev);
197 struct snd_minor *preg; 223 struct snd_minor *preg;
@@ -207,6 +233,7 @@ int snd_register_device(int type, struct snd_card *card, int dev,
207 preg->card = card ? card->number : -1; 233 preg->card = card ? card->number : -1;
208 preg->device = dev; 234 preg->device = dev;
209 preg->f_ops = f_ops; 235 preg->f_ops = f_ops;
236 preg->private_data = private_data;
210 strcpy(preg->name, name); 237 strcpy(preg->name, name);
211 down(&sound_mutex); 238 down(&sound_mutex);
212 if (snd_minors[minor]) { 239 if (snd_minors[minor]) {
@@ -238,13 +265,18 @@ int snd_register_device(int type, struct snd_card *card, int dev,
238 */ 265 */
239int snd_unregister_device(int type, struct snd_card *card, int dev) 266int snd_unregister_device(int type, struct snd_card *card, int dev)
240{ 267{
241 int minor = snd_kernel_minor(type, card, dev); 268 int cardnum, minor;
242 struct snd_minor *mptr; 269 struct snd_minor *mptr;
243 270
244 if (minor < 0) 271 cardnum = card ? card->number : -1;
245 return minor;
246 down(&sound_mutex); 272 down(&sound_mutex);
247 if ((mptr = snd_minors[minor]) == NULL) { 273 for (minor = 0; minor < ARRAY_SIZE(snd_minors); ++minor)
274 if ((mptr = snd_minors[minor]) != NULL &&
275 mptr->type == type &&
276 mptr->card == cardnum &&
277 mptr->device == dev)
278 break;
279 if (minor == ARRAY_SIZE(snd_minors)) {
248 up(&sound_mutex); 280 up(&sound_mutex);
249 return -EINVAL; 281 return -EINVAL;
250 } 282 }
@@ -392,9 +424,11 @@ EXPORT_SYMBOL(snd_request_card);
392#endif 424#endif
393EXPORT_SYMBOL(snd_register_device); 425EXPORT_SYMBOL(snd_register_device);
394EXPORT_SYMBOL(snd_unregister_device); 426EXPORT_SYMBOL(snd_unregister_device);
427EXPORT_SYMBOL(snd_lookup_minor_data);
395#if defined(CONFIG_SND_OSSEMUL) 428#if defined(CONFIG_SND_OSSEMUL)
396EXPORT_SYMBOL(snd_register_oss_device); 429EXPORT_SYMBOL(snd_register_oss_device);
397EXPORT_SYMBOL(snd_unregister_oss_device); 430EXPORT_SYMBOL(snd_unregister_oss_device);
431EXPORT_SYMBOL(snd_lookup_oss_minor_data);
398#endif 432#endif
399 /* memory.c */ 433 /* memory.c */
400EXPORT_SYMBOL(copy_to_user_fromio); 434EXPORT_SYMBOL(copy_to_user_fromio);