1 /* 2 * Routines for driver control interface 3 * Copyright (c) by Jaroslav Kysela <perex@perex.cz> 4 * 5 * 6 * This program is free software; you can redistribute it and/or modify 7 * it under the terms of the GNU General Public License as published by 8 * the Free Software Foundation; either version 2 of the License, or 9 * (at your option) any later version. 10 * 11 * This program is distributed in the hope that it will be useful, 12 * but WITHOUT ANY WARRANTY; without even the implied warranty of 13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 * GNU General Public License for more details. 15 * 16 * You should have received a copy of the GNU General Public License 17 * along with this program; if not, write to the Free Software 18 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA 19 * 20 */ 21 22 #include <sound/driver.h> 23 #include <linux/threads.h> 24 #include <linux/interrupt.h> 25 #include <linux/slab.h> 26 #include <linux/vmalloc.h> 27 #include <linux/time.h> 28 #include <sound/core.h> 29 #include <sound/minors.h> 30 #include <sound/info.h> 31 #include <sound/control.h> 32 33 /* max number of user-defined controls */ 34 #define MAX_USER_CONTROLS 32 35 36 struct snd_kctl_ioctl { 37 struct list_head list; /* list of all ioctls */ 38 snd_kctl_ioctl_func_t fioctl; 39 }; 40 41 static DECLARE_RWSEM(snd_ioctl_rwsem); 42 static LIST_HEAD(snd_control_ioctls); 43 #ifdef CONFIG_COMPAT 44 static LIST_HEAD(snd_control_compat_ioctls); 45 #endif 46 47 static int snd_ctl_open(struct inode *inode, struct file *file) 48 { 49 unsigned long flags; 50 struct snd_card *card; 51 struct snd_ctl_file *ctl; 52 int err; 53 54 card = snd_lookup_minor_data(iminor(inode), SNDRV_DEVICE_TYPE_CONTROL); 55 if (!card) { 56 err = -ENODEV; 57 goto __error1; 58 } 59 err = snd_card_file_add(card, file); 60 if (err < 0) { 61 err = -ENODEV; 62 goto __error1; 63 } 64 if (!try_module_get(card->module)) { 65 err = -EFAULT; 66 goto __error2; 67 } 68 ctl = kzalloc(sizeof(*ctl), GFP_KERNEL); 69 if (ctl == NULL) { 70 err = -ENOMEM; 71 goto __error; 72 } 73 INIT_LIST_HEAD(&ctl->events); 74 init_waitqueue_head(&ctl->change_sleep); 75 spin_lock_init(&ctl->read_lock); 76 ctl->card = card; 77 ctl->prefer_pcm_subdevice = -1; 78 ctl->prefer_rawmidi_subdevice = -1; 79 ctl->pid = current->pid; 80 file->private_data = ctl; 81 write_lock_irqsave(&card->ctl_files_rwlock, flags); 82 list_add_tail(&ctl->list, &card->ctl_files); 83 write_unlock_irqrestore(&card->ctl_files_rwlock, flags); 84 return 0; 85 86 __error: 87 module_put(card->module); 88 __error2: 89 snd_card_file_remove(card, file); 90 __error1: 91 return err; 92 } 93 94 static void snd_ctl_empty_read_queue(struct snd_ctl_file * ctl) 95 { 96 struct snd_kctl_event *cread; 97 98 spin_lock(&ctl->read_lock); 99 while (!list_empty(&ctl->events)) { 100 cread = snd_kctl_event(ctl->events.next); 101 list_del(&cread->list); 102 kfree(cread); 103 } 104 spin_unlock(&ctl->read_lock); 105 } 106 107 static int snd_ctl_release(struct inode *inode, struct file *file) 108 { 109 unsigned long flags; 110 struct snd_card *card; 111 struct snd_ctl_file *ctl; 112 struct snd_kcontrol *control; 113 unsigned int idx; 114 115 ctl = file->private_data; 116 fasync_helper(-1, file, 0, &ctl->fasync); 117 file->private_data = NULL; 118 card = ctl->card; 119 write_lock_irqsave(&card->ctl_files_rwlock, flags); 120 list_del(&ctl->list); 121 write_unlock_irqrestore(&card->ctl_files_rwlock, flags); 122 down_write(&card->controls_rwsem); 123 list_for_each_entry(control, &card->controls, list) 124 for (idx = 0; idx < control->count; idx++) 125 if (control->vd[idx].owner == ctl) 126 control->vd[idx].owner = NULL; 127 up_write(&card->controls_rwsem); 128 snd_ctl_empty_read_queue(ctl); 129 kfree(ctl); 130 module_put(card->module); 131 snd_card_file_remove(card, file); 132 return 0; 133 } 134 135 void snd_ctl_notify(struct snd_card *card, unsigned int mask, 136 struct snd_ctl_elem_id *id) 137 { 138 unsigned long flags; 139 struct snd_ctl_file *ctl; 140 struct snd_kctl_event *ev; 141 142 snd_assert(card != NULL && id != NULL, return); 143 read_lock(&card->ctl_files_rwlock); 144 #if defined(CONFIG_SND_MIXER_OSS) || defined(CONFIG_SND_MIXER_OSS_MODULE) 145 card->mixer_oss_change_count++; 146 #endif 147 list_for_each_entry(ctl, &card->ctl_files, list) { 148 if (!ctl->subscribed) 149 continue; 150 spin_lock_irqsave(&ctl->read_lock, flags); 151 list_for_each_entry(ev, &ctl->events, list) { 152 if (ev->id.numid == id->numid) { 153 ev->mask |= mask; 154 goto _found; 155 } 156 } 157 ev = kzalloc(sizeof(*ev), GFP_ATOMIC); 158 if (ev) { 159 ev->id = *id; 160 ev->mask = mask; 161 list_add_tail(&ev->list, &ctl->events); 162 } else { 163 snd_printk(KERN_ERR "No memory available to allocate event\n"); 164 } 165 _found: 166 wake_up(&ctl->change_sleep); 167 spin_unlock_irqrestore(&ctl->read_lock, flags); 168 kill_fasync(&ctl->fasync, SIGIO, POLL_IN); 169 } 170 read_unlock(&card->ctl_files_rwlock); 171 } 172 173 EXPORT_SYMBOL(snd_ctl_notify); 174 175 /** 176 * snd_ctl_new - create a control instance from the template 177 * @control: the control template 178 * @access: the default control access 179 * 180 * Allocates a new struct snd_kcontrol instance and copies the given template 181 * to the new instance. It does not copy volatile data (access). 182 * 183 * Returns the pointer of the new instance, or NULL on failure. 184 */ 185 static struct snd_kcontrol *snd_ctl_new(struct snd_kcontrol *control, 186 unsigned int access) 187 { 188 struct snd_kcontrol *kctl; 189 unsigned int idx; 190 191 snd_assert(control != NULL, return NULL); 192 snd_assert(control->count > 0, return NULL); 193 kctl = kzalloc(sizeof(*kctl) + sizeof(struct snd_kcontrol_volatile) * control->count, GFP_KERNEL); 194 if (kctl == NULL) { 195 snd_printk(KERN_ERR "Cannot allocate control instance\n"); 196 return NULL; 197 } 198 *kctl = *control; 199 for (idx = 0; idx < kctl->count; idx++) 200 kctl->vd[idx].access = access; 201 return kctl; 202 } 203 204 /** 205 * snd_ctl_new1 - create a control instance from the template 206 * @ncontrol: the initialization record 207 * @private_data: the private data to set 208 * 209 * Allocates a new struct snd_kcontrol instance and initialize from the given 210 * template. When the access field of ncontrol is 0, it's assumed as 211 * READWRITE access. When the count field is 0, it's assumes as one. 212 * 213 * Returns the pointer of the newly generated instance, or NULL on failure. 214 */ 215 struct snd_kcontrol *snd_ctl_new1(const struct snd_kcontrol_new *ncontrol, 216 void *private_data) 217 { 218 struct snd_kcontrol kctl; 219 unsigned int access; 220 221 snd_assert(ncontrol != NULL, return NULL); 222 snd_assert(ncontrol->info != NULL, return NULL); 223 memset(&kctl, 0, sizeof(kctl)); 224 kctl.id.iface = ncontrol->iface; 225 kctl.id.device = ncontrol->device; 226 kctl.id.subdevice = ncontrol->subdevice; 227 if (ncontrol->name) 228 strlcpy(kctl.id.name, ncontrol->name, sizeof(kctl.id.name)); 229 kctl.id.index = ncontrol->index; 230 kctl.count = ncontrol->count ? ncontrol->count : 1; 231 access = ncontrol->access == 0 ? SNDRV_CTL_ELEM_ACCESS_READWRITE : 232 (ncontrol->access & (SNDRV_CTL_ELEM_ACCESS_READWRITE| 233 SNDRV_CTL_ELEM_ACCESS_INACTIVE| 234 SNDRV_CTL_ELEM_ACCESS_DINDIRECT| 235 SNDRV_CTL_ELEM_ACCESS_INDIRECT| 236 SNDRV_CTL_ELEM_ACCESS_TLV_READWRITE| 237 SNDRV_CTL_ELEM_ACCESS_TLV_CALLBACK)); 238 kctl.info = ncontrol->info; 239 kctl.get = ncontrol->get; 240 kctl.put = ncontrol->put; 241 kctl.tlv.p = ncontrol->tlv.p; 242 kctl.private_value = ncontrol->private_value; 243 kctl.private_data = private_data; 244 return snd_ctl_new(&kctl, access); 245 } 246 247 EXPORT_SYMBOL(snd_ctl_new1); 248 249 /** 250 * snd_ctl_free_one - release the control instance 251 * @kcontrol: the control instance 252 * 253 * Releases the control instance created via snd_ctl_new() 254 * or snd_ctl_new1(). 255 * Don't call this after the control was added to the card. 256 */ 257 void snd_ctl_free_one(struct snd_kcontrol *kcontrol) 258 { 259 if (kcontrol) { 260 if (kcontrol->private_free) 261 kcontrol->private_free(kcontrol); 262 kfree(kcontrol); 263 } 264 } 265 266 EXPORT_SYMBOL(snd_ctl_free_one); 267 268 static unsigned int snd_ctl_hole_check(struct snd_card *card, 269 unsigned int count) 270 { 271 struct snd_kcontrol *kctl; 272 273 list_for_each_entry(kctl, &card->controls, list) { 274 if ((kctl->id.numid <= card->last_numid && 275 kctl->id.numid + kctl->count > card->last_numid) || 276 (kctl->id.numid <= card->last_numid + count - 1 && 277 kctl->id.numid + kctl->count > card->last_numid + count - 1)) 278 return card->last_numid = kctl->id.numid + kctl->count - 1; 279 } 280 return card->last_numid; 281 } 282 283 static int snd_ctl_find_hole(struct snd_card *card, unsigned int count) 284 { 285 unsigned int last_numid, iter = 100000; 286 287 last_numid = card->last_numid; 288 while (last_numid != snd_ctl_hole_check(card, count)) { 289 if (--iter == 0) { 290 /* this situation is very unlikely */ 291 snd_printk(KERN_ERR "unable to allocate new control numid\n"); 292 return -ENOMEM; 293 } 294 last_numid = card->last_numid; 295 } 296 return 0; 297 } 298 299 /** 300 * snd_ctl_add - add the control instance to the card 301 * @card: the card instance 302 * @kcontrol: the control instance to add 303 * 304 * Adds the control instance created via snd_ctl_new() or 305 * snd_ctl_new1() to the given card. Assigns also an unique 306 * numid used for fast search. 307 * 308 * Returns zero if successful, or a negative error code on failure. 309 * 310 * It frees automatically the control which cannot be added. 311 */ 312 int snd_ctl_add(struct snd_card *card, struct snd_kcontrol *kcontrol) 313 { 314 struct snd_ctl_elem_id id; 315 unsigned int idx; 316 int err = -EINVAL; 317 318 if (! kcontrol) 319 return err; 320 snd_assert(card != NULL, goto error); 321 snd_assert(kcontrol->info != NULL, goto error); 322 id = kcontrol->id; 323 down_write(&card->controls_rwsem); 324 if (snd_ctl_find_id(card, &id)) { 325 up_write(&card->controls_rwsem); 326 snd_printd(KERN_ERR "control %i:%i:%i:%s:%i is already present\n", 327 id.iface, 328 id.device, 329 id.subdevice, 330 id.name, 331 id.index); 332 err = -EBUSY; 333 goto error; 334 } 335 if (snd_ctl_find_hole(card, kcontrol->count) < 0) { 336 up_write(&card->controls_rwsem); 337 err = -ENOMEM; 338 goto error; 339 } 340 list_add_tail(&kcontrol->list, &card->controls); 341 card->controls_count += kcontrol->count; 342 kcontrol->id.numid = card->last_numid + 1; 343 card->last_numid += kcontrol->count; 344 up_write(&card->controls_rwsem); 345 for (idx = 0; idx < kcontrol->count; idx++, id.index++, id.numid++) 346 snd_ctl_notify(card, SNDRV_CTL_EVENT_MASK_ADD, &id); 347 return 0; 348 349 error: 350 snd_ctl_free_one(kcontrol); 351 return err; 352 } 353 354 EXPORT_SYMBOL(snd_ctl_add); 355 356 /** 357 * snd_ctl_remove - remove the control from the card and release it 358 * @card: the card instance 359 * @kcontrol: the control instance to remove 360 * 361 * Removes the control from the card and then releases the instance. 362 * You don't need to call snd_ctl_free_one(). You must be in 363 * the write lock - down_write(&card->controls_rwsem). 364 * 365 * Returns 0 if successful, or a negative error code on failure. 366 */ 367 int snd_ctl_remove(struct snd_card *card, struct snd_kcontrol *kcontrol) 368 { 369 struct snd_ctl_elem_id id; 370 unsigned int idx; 371 372 snd_assert(card != NULL && kcontrol != NULL, return -EINVAL); 373 list_del(&kcontrol->list); 374 card->controls_count -= kcontrol->count; 375 id = kcontrol->id; 376 for (idx = 0; idx < kcontrol->count; idx++, id.index++, id.numid++) 377 snd_ctl_notify(card, SNDRV_CTL_EVENT_MASK_REMOVE, &id); 378 snd_ctl_free_one(kcontrol); 379 return 0; 380 } 381 382 EXPORT_SYMBOL(snd_ctl_remove); 383 384 /** 385 * snd_ctl_remove_id - remove the control of the given id and release it 386 * @card: the card instance 387 * @id: the control id to remove 388 * 389 * Finds the control instance with the given id, removes it from the 390 * card list and releases it. 391 * 392 * Returns 0 if successful, or a negative error code on failure. 393 */ 394 int snd_ctl_remove_id(struct snd_card *card, struct snd_ctl_elem_id *id) 395 { 396 struct snd_kcontrol *kctl; 397 int ret; 398 399 down_write(&card->controls_rwsem); 400 kctl = snd_ctl_find_id(card, id); 401 if (kctl == NULL) { 402 up_write(&card->controls_rwsem); 403 return -ENOENT; 404 } 405 ret = snd_ctl_remove(card, kctl); 406 up_write(&card->controls_rwsem); 407 return ret; 408 } 409 410 EXPORT_SYMBOL(snd_ctl_remove_id); 411 412 /** 413 * snd_ctl_remove_unlocked_id - remove the unlocked control of the given id and release it 414 * @file: active control handle 415 * @id: the control id to remove 416 * 417 * Finds the control instance with the given id, removes it from the 418 * card list and releases it. 419 * 420 * Returns 0 if successful, or a negative error code on failure. 421 */ 422 static int snd_ctl_remove_unlocked_id(struct snd_ctl_file * file, 423 struct snd_ctl_elem_id *id) 424 { 425 struct snd_card *card = file->card; 426 struct snd_kcontrol *kctl; 427 int idx, ret; 428 429 down_write(&card->controls_rwsem); 430 kctl = snd_ctl_find_id(card, id); 431 if (kctl == NULL) { 432 up_write(&card->controls_rwsem); 433 return -ENOENT; 434 } 435 for (idx = 0; idx < kctl->count; idx++) 436 if (kctl->vd[idx].owner != NULL && kctl->vd[idx].owner != file) { 437 up_write(&card->controls_rwsem); 438 return -EBUSY; 439 } 440 ret = snd_ctl_remove(card, kctl); 441 up_write(&card->controls_rwsem); 442 return ret; 443 } 444 445 /** 446 * snd_ctl_rename_id - replace the id of a control on the card 447 * @card: the card instance 448 * @src_id: the old id 449 * @dst_id: the new id 450 * 451 * Finds the control with the old id from the card, and replaces the 452 * id with the new one. 453 * 454 * Returns zero if successful, or a negative error code on failure. 455 */ 456 int snd_ctl_rename_id(struct snd_card *card, struct snd_ctl_elem_id *src_id, 457 struct snd_ctl_elem_id *dst_id) 458 { 459 struct snd_kcontrol *kctl; 460 461 down_write(&card->controls_rwsem); 462 kctl = snd_ctl_find_id(card, src_id); 463 if (kctl == NULL) { 464 up_write(&card->controls_rwsem); 465 return -ENOENT; 466 } 467 kctl->id = *dst_id; 468 kctl->id.numid = card->last_numid + 1; 469 card->last_numid += kctl->count; 470 up_write(&card->controls_rwsem); 471 return 0; 472 } 473 474 EXPORT_SYMBOL(snd_ctl_rename_id); 475 476 /** 477 * snd_ctl_find_numid - find the control instance with the given number-id 478 * @card: the card instance 479 * @numid: the number-id to search 480 * 481 * Finds the control instance with the given number-id from the card. 482 * 483 * Returns the pointer of the instance if found, or NULL if not. 484 * 485 * The caller must down card->controls_rwsem before calling this function 486 * (if the race condition can happen). 487 */ 488 struct snd_kcontrol *snd_ctl_find_numid(struct snd_card *card, unsigned int numid) 489 { 490 struct snd_kcontrol *kctl; 491 492 snd_assert(card != NULL && numid != 0, return NULL); 493 list_for_each_entry(kctl, &card->controls, list) { 494 if (kctl->id.numid <= numid && kctl->id.numid + kctl->count > numid) 495 return kctl; 496 } 497 return NULL; 498 } 499 500 EXPORT_SYMBOL(snd_ctl_find_numid); 501 502 /** 503 * snd_ctl_find_id - find the control instance with the given id 504 * @card: the card instance 505 * @id: the id to search 506 * 507 * Finds the control instance with the given id from the card. 508 * 509 * Returns the pointer of the instance if found, or NULL if not. 510 * 511 * The caller must down card->controls_rwsem before calling this function 512 * (if the race condition can happen). 513 */ 514 struct snd_kcontrol *snd_ctl_find_id(struct snd_card *card, 515 struct snd_ctl_elem_id *id) 516 { 517 struct snd_kcontrol *kctl; 518 519 snd_assert(card != NULL && id != NULL, return NULL); 520 if (id->numid != 0) 521 return snd_ctl_find_numid(card, id->numid); 522 list_for_each_entry(kctl, &card->controls, list) { 523 if (kctl->id.iface != id->iface) 524 continue; 525 if (kctl->id.device != id->device) 526 continue; 527 if (kctl->id.subdevice != id->subdevice) 528 continue; 529 if (strncmp(kctl->id.name, id->name, sizeof(kctl->id.name))) 530 continue; 531 if (kctl->id.index > id->index) 532 continue; 533 if (kctl->id.index + kctl->count <= id->index) 534 continue; 535 return kctl; 536 } 537 return NULL; 538 } 539 540 EXPORT_SYMBOL(snd_ctl_find_id); 541 542 static int snd_ctl_card_info(struct snd_card *card, struct snd_ctl_file * ctl, 543 unsigned int cmd, void __user *arg) 544 { 545 struct snd_ctl_card_info *info; 546 547 info = kzalloc(sizeof(*info), GFP_KERNEL); 548 if (! info) 549 return -ENOMEM; 550 down_read(&snd_ioctl_rwsem); 551 info->card = card->number; 552 strlcpy(info->id, card->id, sizeof(info->id)); 553 strlcpy(info->driver, card->driver, sizeof(info->driver)); 554 strlcpy(info->name, card->shortname, sizeof(info->name)); 555 strlcpy(info->longname, card->longname, sizeof(info->longname)); 556 strlcpy(info->mixername, card->mixername, sizeof(info->mixername)); 557 strlcpy(info->components, card->components, sizeof(info->components)); 558 up_read(&snd_ioctl_rwsem); 559 if (copy_to_user(arg, info, sizeof(struct snd_ctl_card_info))) { 560 kfree(info); 561 return -EFAULT; 562 } 563 kfree(info); 564 return 0; 565 } 566 567 static int snd_ctl_elem_list(struct snd_card *card, 568 struct snd_ctl_elem_list __user *_list) 569 { 570 struct list_head *plist; 571 struct snd_ctl_elem_list list; 572 struct snd_kcontrol *kctl; 573 struct snd_ctl_elem_id *dst, *id; 574 unsigned int offset, space, first, jidx; 575 576 if (copy_from_user(&list, _list, sizeof(list))) 577 return -EFAULT; 578 offset = list.offset; 579 space = list.space; 580 first = 0; 581 /* try limit maximum space */ 582 if (space > 16384) 583 return -ENOMEM; 584 if (space > 0) { 585 /* allocate temporary buffer for atomic operation */ 586 dst = vmalloc(space * sizeof(struct snd_ctl_elem_id)); 587 if (dst == NULL) 588 return -ENOMEM; 589 down_read(&card->controls_rwsem); 590 list.count = card->controls_count; 591 plist = card->controls.next; 592 while (plist != &card->controls) { 593 if (offset == 0) 594 break; 595 kctl = snd_kcontrol(plist); 596 if (offset < kctl->count) 597 break; 598 offset -= kctl->count; 599 plist = plist->next; 600 } 601 list.used = 0; 602 id = dst; 603 while (space > 0 && plist != &card->controls) { 604 kctl = snd_kcontrol(plist); 605 for (jidx = offset; space > 0 && jidx < kctl->count; jidx++) { 606 snd_ctl_build_ioff(id, kctl, jidx); 607 id++; 608 space--; 609 list.used++; 610 } 611 plist = plist->next; 612 offset = 0; 613 } 614 up_read(&card->controls_rwsem); 615 if (list.used > 0 && 616 copy_to_user(list.pids, dst, 617 list.used * sizeof(struct snd_ctl_elem_id))) { 618 vfree(dst); 619 return -EFAULT; 620 } 621 vfree(dst); 622 } else { 623 down_read(&card->controls_rwsem); 624 list.count = card->controls_count; 625 up_read(&card->controls_rwsem); 626 } 627 if (copy_to_user(_list, &list, sizeof(list))) 628 return -EFAULT; 629 return 0; 630 } 631 632 static int snd_ctl_elem_info(struct snd_ctl_file *ctl, 633 struct snd_ctl_elem_info *info) 634 { 635 struct snd_card *card = ctl->card; 636 struct snd_kcontrol *kctl; 637 struct snd_kcontrol_volatile *vd; 638 unsigned int index_offset; 639 int result; 640 641 down_read(&card->controls_rwsem); 642 kctl = snd_ctl_find_id(card, &info->id); 643 if (kctl == NULL) { 644 up_read(&card->controls_rwsem); 645 return -ENOENT; 646 } 647 #ifdef CONFIG_SND_DEBUG 648 info->access = 0; 649 #endif 650 result = kctl->info(kctl, info); 651 if (result >= 0) { 652 snd_assert(info->access == 0, ); 653 index_offset = snd_ctl_get_ioff(kctl, &info->id); 654 vd = &kctl->vd[index_offset]; 655 snd_ctl_build_ioff(&info->id, kctl, index_offset); 656 info->access = vd->access; 657 if (vd->owner) { 658 info->access |= SNDRV_CTL_ELEM_ACCESS_LOCK; 659 if (vd->owner == ctl) 660 info->access |= SNDRV_CTL_ELEM_ACCESS_OWNER; 661 info->owner = vd->owner_pid; 662 } else { 663 info->owner = -1; 664 } 665 } 666 up_read(&card->controls_rwsem); 667 return result; 668 } 669 670 static int snd_ctl_elem_info_user(struct snd_ctl_file *ctl, 671 struct snd_ctl_elem_info __user *_info) 672 { 673 struct snd_ctl_elem_info info; 674 int result; 675 676 if (copy_from_user(&info, _info, sizeof(info))) 677 return -EFAULT; 678 snd_power_lock(ctl->card); 679 result = snd_power_wait(ctl->card, SNDRV_CTL_POWER_D0); 680 if (result >= 0) 681 result = snd_ctl_elem_info(ctl, &info); 682 snd_power_unlock(ctl->card); 683 if (result >= 0) 684 if (copy_to_user(_info, &info, sizeof(info))) 685 return -EFAULT; 686 return result; 687 } 688 689 int snd_ctl_elem_read(struct snd_card *card, struct snd_ctl_elem_value *control) 690 { 691 struct snd_kcontrol *kctl; 692 struct snd_kcontrol_volatile *vd; 693 unsigned int index_offset; 694 int result, indirect; 695 696 down_read(&card->controls_rwsem); 697 kctl = snd_ctl_find_id(card, &control->id); 698 if (kctl == NULL) { 699 result = -ENOENT; 700 } else { 701 index_offset = snd_ctl_get_ioff(kctl, &control->id); 702 vd = &kctl->vd[index_offset]; 703 indirect = vd->access & SNDRV_CTL_ELEM_ACCESS_INDIRECT ? 1 : 0; 704 if (control->indirect != indirect) { 705 result = -EACCES; 706 } else { 707 if ((vd->access & SNDRV_CTL_ELEM_ACCESS_READ) && kctl->get != NULL) { 708 snd_ctl_build_ioff(&control->id, kctl, index_offset); 709 result = kctl->get(kctl, control); 710 } else { 711 result = -EPERM; 712 } 713 } 714 } 715 up_read(&card->controls_rwsem); 716 return result; 717 } 718 719 static int snd_ctl_elem_read_user(struct snd_card *card, 720 struct snd_ctl_elem_value __user *_control) 721 { 722 struct snd_ctl_elem_value *control; 723 int result; 724 725 control = kmalloc(sizeof(*control), GFP_KERNEL); 726 if (control == NULL) 727 return -ENOMEM; 728 if (copy_from_user(control, _control, sizeof(*control))) { 729 kfree(control); 730 return -EFAULT; 731 } 732 snd_power_lock(card); 733 result = snd_power_wait(card, SNDRV_CTL_POWER_D0); 734 if (result >= 0) 735 result = snd_ctl_elem_read(card, control); 736 snd_power_unlock(card); 737 if (result >= 0) 738 if (copy_to_user(_control, control, sizeof(*control))) 739 result = -EFAULT; 740 kfree(control); 741 return result; 742 } 743 744 int snd_ctl_elem_write(struct snd_card *card, struct snd_ctl_file *file, 745 struct snd_ctl_elem_value *control) 746 { 747 struct snd_kcontrol *kctl; 748 struct snd_kcontrol_volatile *vd; 749 unsigned int index_offset; 750 int result, indirect; 751 752 down_read(&card->controls_rwsem); 753 kctl = snd_ctl_find_id(card, &control->id); 754 if (kctl == NULL) { 755 result = -ENOENT; 756 } else { 757 index_offset = snd_ctl_get_ioff(kctl, &control->id); 758 vd = &kctl->vd[index_offset]; 759 indirect = vd->access & SNDRV_CTL_ELEM_ACCESS_INDIRECT ? 1 : 0; 760 if (control->indirect != indirect) { 761 result = -EACCES; 762 } else { 763 if (!(vd->access & SNDRV_CTL_ELEM_ACCESS_WRITE) || 764 kctl->put == NULL || 765 (file && vd->owner != NULL && vd->owner != file)) { 766 result = -EPERM; 767 } else { 768 snd_ctl_build_ioff(&control->id, kctl, index_offset); 769 result = kctl->put(kctl, control); 770 } 771 if (result > 0) { 772 up_read(&card->controls_rwsem); 773 snd_ctl_notify(card, SNDRV_CTL_EVENT_MASK_VALUE, &control->id); 774 return 0; 775 } 776 } 777 } 778 up_read(&card->controls_rwsem); 779 return result; 780 } 781 782 static int snd_ctl_elem_write_user(struct snd_ctl_file *file, 783 struct snd_ctl_elem_value __user *_control) 784 { 785 struct snd_ctl_elem_value *control; 786 struct snd_card *card; 787 int result; 788 789 control = kmalloc(sizeof(*control), GFP_KERNEL); 790 if (control == NULL) 791 return -ENOMEM; 792 if (copy_from_user(control, _control, sizeof(*control))) { 793 kfree(control); 794 return -EFAULT; 795 } 796 card = file->card; 797 snd_power_lock(card); 798 result = snd_power_wait(card, SNDRV_CTL_POWER_D0); 799 if (result >= 0) 800 result = snd_ctl_elem_write(card, file, control); 801 snd_power_unlock(card); 802 if (result >= 0) 803 if (copy_to_user(_control, control, sizeof(*control))) 804 result = -EFAULT; 805 kfree(control); 806 return result; 807 } 808 809 static int snd_ctl_elem_lock(struct snd_ctl_file *file, 810 struct snd_ctl_elem_id __user *_id) 811 { 812 struct snd_card *card = file->card; 813 struct snd_ctl_elem_id id; 814 struct snd_kcontrol *kctl; 815 struct snd_kcontrol_volatile *vd; 816 int result; 817 818 if (copy_from_user(&id, _id, sizeof(id))) 819 return -EFAULT; 820 down_write(&card->controls_rwsem); 821 kctl = snd_ctl_find_id(card, &id); 822 if (kctl == NULL) { 823 result = -ENOENT; 824 } else { 825 vd = &kctl->vd[snd_ctl_get_ioff(kctl, &id)]; 826 if (vd->owner != NULL) 827 result = -EBUSY; 828 else { 829 vd->owner = file; 830 vd->owner_pid = current->pid; 831 result = 0; 832 } 833 } 834 up_write(&card->controls_rwsem); 835 return result; 836 } 837 838 static int snd_ctl_elem_unlock(struct snd_ctl_file *file, 839 struct snd_ctl_elem_id __user *_id) 840 { 841 struct snd_card *card = file->card; 842 struct snd_ctl_elem_id id; 843 struct snd_kcontrol *kctl; 844 struct snd_kcontrol_volatile *vd; 845 int result; 846 847 if (copy_from_user(&id, _id, sizeof(id))) 848 return -EFAULT; 849 down_write(&card->controls_rwsem); 850 kctl = snd_ctl_find_id(card, &id); 851 if (kctl == NULL) { 852 result = -ENOENT; 853 } else { 854 vd = &kctl->vd[snd_ctl_get_ioff(kctl, &id)]; 855 if (vd->owner == NULL) 856 result = -EINVAL; 857 else if (vd->owner != file) 858 result = -EPERM; 859 else { 860 vd->owner = NULL; 861 vd->owner_pid = 0; 862 result = 0; 863 } 864 } 865 up_write(&card->controls_rwsem); 866 return result; 867 } 868 869 struct user_element { 870 struct snd_ctl_elem_info info; 871 void *elem_data; /* element data */ 872 unsigned long elem_data_size; /* size of element data in bytes */ 873 void *tlv_data; /* TLV data */ 874 unsigned long tlv_data_size; /* TLV data size */ 875 void *priv_data; /* private data (like strings for enumerated type) */ 876 unsigned long priv_data_size; /* size of private data in bytes */ 877 }; 878 879 static int snd_ctl_elem_user_info(struct snd_kcontrol *kcontrol, 880 struct snd_ctl_elem_info *uinfo) 881 { 882 struct user_element *ue = kcontrol->private_data; 883 884 *uinfo = ue->info; 885 return 0; 886 } 887 888 static int snd_ctl_elem_user_get(struct snd_kcontrol *kcontrol, 889 struct snd_ctl_elem_value *ucontrol) 890 { 891 struct user_element *ue = kcontrol->private_data; 892 893 memcpy(&ucontrol->value, ue->elem_data, ue->elem_data_size); 894 return 0; 895 } 896 897 static int snd_ctl_elem_user_put(struct snd_kcontrol *kcontrol, 898 struct snd_ctl_elem_value *ucontrol) 899 { 900 int change; 901 struct user_element *ue = kcontrol->private_data; 902 903 change = memcmp(&ucontrol->value, ue->elem_data, ue->elem_data_size) != 0; 904 if (change) 905 memcpy(ue->elem_data, &ucontrol->value, ue->elem_data_size); 906 return change; 907 } 908 909 static int snd_ctl_elem_user_tlv(struct snd_kcontrol *kcontrol, 910 int op_flag, 911 unsigned int size, 912 unsigned int __user *tlv) 913 { 914 struct user_element *ue = kcontrol->private_data; 915 int change = 0; 916 void *new_data; 917 918 if (op_flag > 0) { 919 if (size > 1024 * 128) /* sane value */ 920 return -EINVAL; 921 new_data = kmalloc(size, GFP_KERNEL); 922 if (new_data == NULL) 923 return -ENOMEM; 924 if (copy_from_user(new_data, tlv, size)) { 925 kfree(new_data); 926 return -EFAULT; 927 } 928 change = ue->tlv_data_size != size; 929 if (!change) 930 change = memcmp(ue->tlv_data, new_data, size); 931 kfree(ue->tlv_data); 932 ue->tlv_data = new_data; 933 ue->tlv_data_size = size; 934 } else { 935 if (! ue->tlv_data_size || ! ue->tlv_data) 936 return -ENXIO; 937 if (size < ue->tlv_data_size) 938 return -ENOSPC; 939 if (copy_to_user(tlv, ue->tlv_data, ue->tlv_data_size)) 940 return -EFAULT; 941 } 942 return change; 943 } 944 945 static void snd_ctl_elem_user_free(struct snd_kcontrol *kcontrol) 946 { 947 struct user_element *ue = kcontrol->private_data; 948 if (ue->tlv_data) 949 kfree(ue->tlv_data); 950 kfree(ue); 951 } 952 953 static int snd_ctl_elem_add(struct snd_ctl_file *file, 954 struct snd_ctl_elem_info *info, int replace) 955 { 956 struct snd_card *card = file->card; 957 struct snd_kcontrol kctl, *_kctl; 958 unsigned int access; 959 long private_size; 960 struct user_element *ue; 961 int idx, err; 962 963 if (card->user_ctl_count >= MAX_USER_CONTROLS) 964 return -ENOMEM; 965 if (info->count > 1024) 966 return -EINVAL; 967 access = info->access == 0 ? SNDRV_CTL_ELEM_ACCESS_READWRITE : 968 (info->access & (SNDRV_CTL_ELEM_ACCESS_READWRITE| 969 SNDRV_CTL_ELEM_ACCESS_INACTIVE| 970 SNDRV_CTL_ELEM_ACCESS_TLV_READWRITE)); 971 info->id.numid = 0; 972 memset(&kctl, 0, sizeof(kctl)); 973 down_write(&card->controls_rwsem); 974 _kctl = snd_ctl_find_id(card, &info->id); 975 err = 0; 976 if (_kctl) { 977 if (replace) 978 err = snd_ctl_remove(card, _kctl); 979 else 980 err = -EBUSY; 981 } else { 982 if (replace) 983 err = -ENOENT; 984 } 985 up_write(&card->controls_rwsem); 986 if (err < 0) 987 return err; 988 memcpy(&kctl.id, &info->id, sizeof(info->id)); 989 kctl.count = info->owner ? info->owner : 1; 990 access |= SNDRV_CTL_ELEM_ACCESS_USER; 991 kctl.info = snd_ctl_elem_user_info; 992 if (access & SNDRV_CTL_ELEM_ACCESS_READ) 993 kctl.get = snd_ctl_elem_user_get; 994 if (access & SNDRV_CTL_ELEM_ACCESS_WRITE) 995 kctl.put = snd_ctl_elem_user_put; 996 if (access & SNDRV_CTL_ELEM_ACCESS_TLV_READWRITE) { 997 kctl.tlv.c = snd_ctl_elem_user_tlv; 998 access |= SNDRV_CTL_ELEM_ACCESS_TLV_CALLBACK; 999 } 1000 switch (info->type) { 1001 case SNDRV_CTL_ELEM_TYPE_BOOLEAN: 1002 case SNDRV_CTL_ELEM_TYPE_INTEGER: 1003 private_size = sizeof(long); 1004 if (info->count > 128) 1005 return -EINVAL; 1006 break; 1007 case SNDRV_CTL_ELEM_TYPE_INTEGER64: 1008 private_size = sizeof(long long); 1009 if (info->count > 64) 1010 return -EINVAL; 1011 break; 1012 case SNDRV_CTL_ELEM_TYPE_BYTES: 1013 private_size = sizeof(unsigned char); 1014 if (info->count > 512) 1015 return -EINVAL; 1016 break; 1017 case SNDRV_CTL_ELEM_TYPE_IEC958: 1018 private_size = sizeof(struct snd_aes_iec958); 1019 if (info->count != 1) 1020 return -EINVAL; 1021 break; 1022 default: 1023 return -EINVAL; 1024 } 1025 private_size *= info->count; 1026 ue = kzalloc(sizeof(struct user_element) + private_size, GFP_KERNEL); 1027 if (ue == NULL) 1028 return -ENOMEM; 1029 ue->info = *info; 1030 ue->info.access = 0; 1031 ue->elem_data = (char *)ue + sizeof(*ue); 1032 ue->elem_data_size = private_size; 1033 kctl.private_free = snd_ctl_elem_user_free; 1034 _kctl = snd_ctl_new(&kctl, access); 1035 if (_kctl == NULL) { 1036 kfree(ue); 1037 return -ENOMEM; 1038 } 1039 _kctl->private_data = ue; 1040 for (idx = 0; idx < _kctl->count; idx++) 1041 _kctl->vd[idx].owner = file; 1042 err = snd_ctl_add(card, _kctl); 1043 if (err < 0) 1044 return err; 1045 1046 down_write(&card->controls_rwsem); 1047 card->user_ctl_count++; 1048 up_write(&card->controls_rwsem); 1049 1050 return 0; 1051 } 1052 1053 static int snd_ctl_elem_add_user(struct snd_ctl_file *file, 1054 struct snd_ctl_elem_info __user *_info, int replace) 1055 { 1056 struct snd_ctl_elem_info info; 1057 if (copy_from_user(&info, _info, sizeof(info))) 1058 return -EFAULT; 1059 return snd_ctl_elem_add(file, &info, replace); 1060 } 1061 1062 static int snd_ctl_elem_remove(struct snd_ctl_file *file, 1063 struct snd_ctl_elem_id __user *_id) 1064 { 1065 struct snd_ctl_elem_id id; 1066 int err; 1067 1068 if (copy_from_user(&id, _id, sizeof(id))) 1069 return -EFAULT; 1070 err = snd_ctl_remove_unlocked_id(file, &id); 1071 if (! err) { 1072 struct snd_card *card = file->card; 1073 down_write(&card->controls_rwsem); 1074 card->user_ctl_count--; 1075 up_write(&card->controls_rwsem); 1076 } 1077 return err; 1078 } 1079 1080 static int snd_ctl_subscribe_events(struct snd_ctl_file *file, int __user *ptr) 1081 { 1082 int subscribe; 1083 if (get_user(subscribe, ptr)) 1084 return -EFAULT; 1085 if (subscribe < 0) { 1086 subscribe = file->subscribed; 1087 if (put_user(subscribe, ptr)) 1088 return -EFAULT; 1089 return 0; 1090 } 1091 if (subscribe) { 1092 file->subscribed = 1; 1093 return 0; 1094 } else if (file->subscribed) { 1095 snd_ctl_empty_read_queue(file); 1096 file->subscribed = 0; 1097 } 1098 return 0; 1099 } 1100 1101 static int snd_ctl_tlv_ioctl(struct snd_ctl_file *file, 1102 struct snd_ctl_tlv __user *_tlv, 1103 int op_flag) 1104 { 1105 struct snd_card *card = file->card; 1106 struct snd_ctl_tlv tlv; 1107 struct snd_kcontrol *kctl; 1108 struct snd_kcontrol_volatile *vd; 1109 unsigned int len; 1110 int err = 0; 1111 1112 if (copy_from_user(&tlv, _tlv, sizeof(tlv))) 1113 return -EFAULT; 1114 if (tlv.length < sizeof(unsigned int) * 3) 1115 return -EINVAL; 1116 down_read(&card->controls_rwsem); 1117 kctl = snd_ctl_find_numid(card, tlv.numid); 1118 if (kctl == NULL) { 1119 err = -ENOENT; 1120 goto __kctl_end; 1121 } 1122 if (kctl->tlv.p == NULL) { 1123 err = -ENXIO; 1124 goto __kctl_end; 1125 } 1126 vd = &kctl->vd[tlv.numid - kctl->id.numid]; 1127 if ((op_flag == 0 && (vd->access & SNDRV_CTL_ELEM_ACCESS_TLV_READ) == 0) || 1128 (op_flag > 0 && (vd->access & SNDRV_CTL_ELEM_ACCESS_TLV_WRITE) == 0) || 1129 (op_flag < 0 && (vd->access & SNDRV_CTL_ELEM_ACCESS_TLV_COMMAND) == 0)) { 1130 err = -ENXIO; 1131 goto __kctl_end; 1132 } 1133 if (vd->access & SNDRV_CTL_ELEM_ACCESS_TLV_CALLBACK) { 1134 if (file && vd->owner != NULL && vd->owner != file) { 1135 err = -EPERM; 1136 goto __kctl_end; 1137 } 1138 err = kctl->tlv.c(kctl, op_flag, tlv.length, _tlv->tlv); 1139 if (err > 0) { 1140 up_read(&card->controls_rwsem); 1141 snd_ctl_notify(card, SNDRV_CTL_EVENT_MASK_TLV, &kctl->id); 1142 return 0; 1143 } 1144 } else { 1145 if (op_flag) { 1146 err = -ENXIO; 1147 goto __kctl_end; 1148 } 1149 len = kctl->tlv.p[1] + 2 * sizeof(unsigned int); 1150 if (tlv.length < len) { 1151 err = -ENOMEM; 1152 goto __kctl_end; 1153 } 1154 if (copy_to_user(_tlv->tlv, kctl->tlv.p, len)) 1155 err = -EFAULT; 1156 } 1157 __kctl_end: 1158 up_read(&card->controls_rwsem); 1159 return err; 1160 } 1161 1162 static long snd_ctl_ioctl(struct file *file, unsigned int cmd, unsigned long arg) 1163 { 1164 struct snd_ctl_file *ctl; 1165 struct snd_card *card; 1166 struct snd_kctl_ioctl *p; 1167 void __user *argp = (void __user *)arg; 1168 int __user *ip = argp; 1169 int err; 1170 1171 ctl = file->private_data; 1172 card = ctl->card; 1173 snd_assert(card != NULL, return -ENXIO); 1174 switch (cmd) { 1175 case SNDRV_CTL_IOCTL_PVERSION: 1176 return put_user(SNDRV_CTL_VERSION, ip) ? -EFAULT : 0; 1177 case SNDRV_CTL_IOCTL_CARD_INFO: 1178 return snd_ctl_card_info(card, ctl, cmd, argp); 1179 case SNDRV_CTL_IOCTL_ELEM_LIST: 1180 return snd_ctl_elem_list(card, argp); 1181 case SNDRV_CTL_IOCTL_ELEM_INFO: 1182 return snd_ctl_elem_info_user(ctl, argp); 1183 case SNDRV_CTL_IOCTL_ELEM_READ: 1184 return snd_ctl_elem_read_user(card, argp); 1185 case SNDRV_CTL_IOCTL_ELEM_WRITE: 1186 return snd_ctl_elem_write_user(ctl, argp); 1187 case SNDRV_CTL_IOCTL_ELEM_LOCK: 1188 return snd_ctl_elem_lock(ctl, argp); 1189 case SNDRV_CTL_IOCTL_ELEM_UNLOCK: 1190 return snd_ctl_elem_unlock(ctl, argp); 1191 case SNDRV_CTL_IOCTL_ELEM_ADD: 1192 return snd_ctl_elem_add_user(ctl, argp, 0); 1193 case SNDRV_CTL_IOCTL_ELEM_REPLACE: 1194 return snd_ctl_elem_add_user(ctl, argp, 1); 1195 case SNDRV_CTL_IOCTL_ELEM_REMOVE: 1196 return snd_ctl_elem_remove(ctl, argp); 1197 case SNDRV_CTL_IOCTL_SUBSCRIBE_EVENTS: 1198 return snd_ctl_subscribe_events(ctl, ip); 1199 case SNDRV_CTL_IOCTL_TLV_READ: 1200 return snd_ctl_tlv_ioctl(ctl, argp, 0); 1201 case SNDRV_CTL_IOCTL_TLV_WRITE: 1202 return snd_ctl_tlv_ioctl(ctl, argp, 1); 1203 case SNDRV_CTL_IOCTL_TLV_COMMAND: 1204 return snd_ctl_tlv_ioctl(ctl, argp, -1); 1205 case SNDRV_CTL_IOCTL_POWER: 1206 return -ENOPROTOOPT; 1207 case SNDRV_CTL_IOCTL_POWER_STATE: 1208 #ifdef CONFIG_PM 1209 return put_user(card->power_state, ip) ? -EFAULT : 0; 1210 #else 1211 return put_user(SNDRV_CTL_POWER_D0, ip) ? -EFAULT : 0; 1212 #endif 1213 } 1214 down_read(&snd_ioctl_rwsem); 1215 list_for_each_entry(p, &snd_control_ioctls, list) { 1216 err = p->fioctl(card, ctl, cmd, arg); 1217 if (err != -ENOIOCTLCMD) { 1218 up_read(&snd_ioctl_rwsem); 1219 return err; 1220 } 1221 } 1222 up_read(&snd_ioctl_rwsem); 1223 snd_printdd("unknown ioctl = 0x%x\n", cmd); 1224 return -ENOTTY; 1225 } 1226 1227 static ssize_t snd_ctl_read(struct file *file, char __user *buffer, 1228 size_t count, loff_t * offset) 1229 { 1230 struct snd_ctl_file *ctl; 1231 int err = 0; 1232 ssize_t result = 0; 1233 1234 ctl = file->private_data; 1235 snd_assert(ctl != NULL && ctl->card != NULL, return -ENXIO); 1236 if (!ctl->subscribed) 1237 return -EBADFD; 1238 if (count < sizeof(struct snd_ctl_event)) 1239 return -EINVAL; 1240 spin_lock_irq(&ctl->read_lock); 1241 while (count >= sizeof(struct snd_ctl_event)) { 1242 struct snd_ctl_event ev; 1243 struct snd_kctl_event *kev; 1244 while (list_empty(&ctl->events)) { 1245 wait_queue_t wait; 1246 if ((file->f_flags & O_NONBLOCK) != 0 || result > 0) { 1247 err = -EAGAIN; 1248 goto __end_lock; 1249 } 1250 init_waitqueue_entry(&wait, current); 1251 add_wait_queue(&ctl->change_sleep, &wait); 1252 set_current_state(TASK_INTERRUPTIBLE); 1253 spin_unlock_irq(&ctl->read_lock); 1254 schedule(); 1255 remove_wait_queue(&ctl->change_sleep, &wait); 1256 if (signal_pending(current)) 1257 return -ERESTARTSYS; 1258 spin_lock_irq(&ctl->read_lock); 1259 } 1260 kev = snd_kctl_event(ctl->events.next); 1261 ev.type = SNDRV_CTL_EVENT_ELEM; 1262 ev.data.elem.mask = kev->mask; 1263 ev.data.elem.id = kev->id; 1264 list_del(&kev->list); 1265 spin_unlock_irq(&ctl->read_lock); 1266 kfree(kev); 1267 if (copy_to_user(buffer, &ev, sizeof(struct snd_ctl_event))) { 1268 err = -EFAULT; 1269 goto __end; 1270 } 1271 spin_lock_irq(&ctl->read_lock); 1272 buffer += sizeof(struct snd_ctl_event); 1273 count -= sizeof(struct snd_ctl_event); 1274 result += sizeof(struct snd_ctl_event); 1275 } 1276 __end_lock: 1277 spin_unlock_irq(&ctl->read_lock); 1278 __end: 1279 return result > 0 ? result : err; 1280 } 1281 1282 static unsigned int snd_ctl_poll(struct file *file, poll_table * wait) 1283 { 1284 unsigned int mask; 1285 struct snd_ctl_file *ctl; 1286 1287 ctl = file->private_data; 1288 if (!ctl->subscribed) 1289 return 0; 1290 poll_wait(file, &ctl->change_sleep, wait); 1291 1292 mask = 0; 1293 if (!list_empty(&ctl->events)) 1294 mask |= POLLIN | POLLRDNORM; 1295 1296 return mask; 1297 } 1298 1299 /* 1300 * register the device-specific control-ioctls. 1301 * called from each device manager like pcm.c, hwdep.c, etc. 1302 */ 1303 static int _snd_ctl_register_ioctl(snd_kctl_ioctl_func_t fcn, struct list_head *lists) 1304 { 1305 struct snd_kctl_ioctl *pn; 1306 1307 pn = kzalloc(sizeof(struct snd_kctl_ioctl), GFP_KERNEL); 1308 if (pn == NULL) 1309 return -ENOMEM; 1310 pn->fioctl = fcn; 1311 down_write(&snd_ioctl_rwsem); 1312 list_add_tail(&pn->list, lists); 1313 up_write(&snd_ioctl_rwsem); 1314 return 0; 1315 } 1316 1317 int snd_ctl_register_ioctl(snd_kctl_ioctl_func_t fcn) 1318 { 1319 return _snd_ctl_register_ioctl(fcn, &snd_control_ioctls); 1320 } 1321 1322 EXPORT_SYMBOL(snd_ctl_register_ioctl); 1323 1324 #ifdef CONFIG_COMPAT 1325 int snd_ctl_register_ioctl_compat(snd_kctl_ioctl_func_t fcn) 1326 { 1327 return _snd_ctl_register_ioctl(fcn, &snd_control_compat_ioctls); 1328 } 1329 1330 EXPORT_SYMBOL(snd_ctl_register_ioctl_compat); 1331 #endif 1332 1333 /* 1334 * de-register the device-specific control-ioctls. 1335 */ 1336 static int _snd_ctl_unregister_ioctl(snd_kctl_ioctl_func_t fcn, 1337 struct list_head *lists) 1338 { 1339 struct snd_kctl_ioctl *p; 1340 1341 snd_assert(fcn != NULL, return -EINVAL); 1342 down_write(&snd_ioctl_rwsem); 1343 list_for_each_entry(p, lists, list) { 1344 if (p->fioctl == fcn) { 1345 list_del(&p->list); 1346 up_write(&snd_ioctl_rwsem); 1347 kfree(p); 1348 return 0; 1349 } 1350 } 1351 up_write(&snd_ioctl_rwsem); 1352 snd_BUG(); 1353 return -EINVAL; 1354 } 1355 1356 int snd_ctl_unregister_ioctl(snd_kctl_ioctl_func_t fcn) 1357 { 1358 return _snd_ctl_unregister_ioctl(fcn, &snd_control_ioctls); 1359 } 1360 1361 EXPORT_SYMBOL(snd_ctl_unregister_ioctl); 1362 1363 #ifdef CONFIG_COMPAT 1364 int snd_ctl_unregister_ioctl_compat(snd_kctl_ioctl_func_t fcn) 1365 { 1366 return _snd_ctl_unregister_ioctl(fcn, &snd_control_compat_ioctls); 1367 } 1368 1369 EXPORT_SYMBOL(snd_ctl_unregister_ioctl_compat); 1370 #endif 1371 1372 static int snd_ctl_fasync(int fd, struct file * file, int on) 1373 { 1374 struct snd_ctl_file *ctl; 1375 int err; 1376 ctl = file->private_data; 1377 err = fasync_helper(fd, file, on, &ctl->fasync); 1378 if (err < 0) 1379 return err; 1380 return 0; 1381 } 1382 1383 /* 1384 * ioctl32 compat 1385 */ 1386 #ifdef CONFIG_COMPAT 1387 #include "control_compat.c" 1388 #else 1389 #define snd_ctl_ioctl_compat NULL 1390 #endif 1391 1392 /* 1393 * INIT PART 1394 */ 1395 1396 static const struct file_operations snd_ctl_f_ops = 1397 { 1398 .owner = THIS_MODULE, 1399 .read = snd_ctl_read, 1400 .open = snd_ctl_open, 1401 .release = snd_ctl_release, 1402 .poll = snd_ctl_poll, 1403 .unlocked_ioctl = snd_ctl_ioctl, 1404 .compat_ioctl = snd_ctl_ioctl_compat, 1405 .fasync = snd_ctl_fasync, 1406 }; 1407 1408 /* 1409 * registration of the control device 1410 */ 1411 static int snd_ctl_dev_register(struct snd_device *device) 1412 { 1413 struct snd_card *card = device->device_data; 1414 int err, cardnum; 1415 char name[16]; 1416 1417 snd_assert(card != NULL, return -ENXIO); 1418 cardnum = card->number; 1419 snd_assert(cardnum >= 0 && cardnum < SNDRV_CARDS, return -ENXIO); 1420 sprintf(name, "controlC%i", cardnum); 1421 if ((err = snd_register_device(SNDRV_DEVICE_TYPE_CONTROL, card, -1, 1422 &snd_ctl_f_ops, card, name)) < 0) 1423 return err; 1424 return 0; 1425 } 1426 1427 /* 1428 * disconnection of the control device 1429 */ 1430 static int snd_ctl_dev_disconnect(struct snd_device *device) 1431 { 1432 struct snd_card *card = device->device_data; 1433 struct snd_ctl_file *ctl; 1434 int err, cardnum; 1435 1436 snd_assert(card != NULL, return -ENXIO); 1437 cardnum = card->number; 1438 snd_assert(cardnum >= 0 && cardnum < SNDRV_CARDS, return -ENXIO); 1439 1440 down_read(&card->controls_rwsem); 1441 list_for_each_entry(ctl, &card->ctl_files, list) { 1442 wake_up(&ctl->change_sleep); 1443 kill_fasync(&ctl->fasync, SIGIO, POLL_ERR); 1444 } 1445 up_read(&card->controls_rwsem); 1446 1447 if ((err = snd_unregister_device(SNDRV_DEVICE_TYPE_CONTROL, 1448 card, -1)) < 0) 1449 return err; 1450 return 0; 1451 } 1452 1453 /* 1454 * free all controls 1455 */ 1456 static int snd_ctl_dev_free(struct snd_device *device) 1457 { 1458 struct snd_card *card = device->device_data; 1459 struct snd_kcontrol *control; 1460 1461 down_write(&card->controls_rwsem); 1462 while (!list_empty(&card->controls)) { 1463 control = snd_kcontrol(card->controls.next); 1464 snd_ctl_remove(card, control); 1465 } 1466 up_write(&card->controls_rwsem); 1467 return 0; 1468 } 1469 1470 /* 1471 * create control core: 1472 * called from init.c 1473 */ 1474 int snd_ctl_create(struct snd_card *card) 1475 { 1476 static struct snd_device_ops ops = { 1477 .dev_free = snd_ctl_dev_free, 1478 .dev_register = snd_ctl_dev_register, 1479 .dev_disconnect = snd_ctl_dev_disconnect, 1480 }; 1481 1482 snd_assert(card != NULL, return -ENXIO); 1483 return snd_device_new(card, SNDRV_DEV_CONTROL, card, &ops); 1484 } 1485 1486 /* 1487 * Frequently used control callbacks 1488 */ 1489 int snd_ctl_boolean_mono_info(struct snd_kcontrol *kcontrol, 1490 struct snd_ctl_elem_info *uinfo) 1491 { 1492 uinfo->type = SNDRV_CTL_ELEM_TYPE_BOOLEAN; 1493 uinfo->count = 1; 1494 uinfo->value.integer.min = 0; 1495 uinfo->value.integer.max = 1; 1496 return 0; 1497 } 1498 1499 EXPORT_SYMBOL(snd_ctl_boolean_mono_info); 1500 1501 int snd_ctl_boolean_stereo_info(struct snd_kcontrol *kcontrol, 1502 struct snd_ctl_elem_info *uinfo) 1503 { 1504 uinfo->type = SNDRV_CTL_ELEM_TYPE_BOOLEAN; 1505 uinfo->count = 2; 1506 uinfo->value.integer.min = 0; 1507 uinfo->value.integer.max = 1; 1508 return 0; 1509 } 1510 1511 EXPORT_SYMBOL(snd_ctl_boolean_stereo_info); 1512