a0965c6c901f8979cb1ebaaa54cb4a7979b1ae90
[platform/upstream/alsa-lib.git] / src / control / control.c
1 /**
2  * \file control/control.c
3  * \brief CTL interface - primitive controls
4  * \author Abramo Bagnara <abramo@alsa-project.org>
5  * \date 2000
6  *
7  * CTL interface is designed to access primitive controls.
8  * See \ref control page for more details.
9  */
10 /*
11  *  Control Interface - main file
12  *  Copyright (c) 2000 by Abramo Bagnara <abramo@alsa-project.org>
13  *
14  *
15  *   This library is free software; you can redistribute it and/or modify
16  *   it under the terms of the GNU Lesser General Public License as
17  *   published by the Free Software Foundation; either version 2.1 of
18  *   the License, or (at your option) any later version.
19  *
20  *   This program is distributed in the hope that it will be useful,
21  *   but WITHOUT ANY WARRANTY; without even the implied warranty of
22  *   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
23  *   GNU Lesser General Public License for more details.
24  *
25  *   You should have received a copy of the GNU Lesser General Public
26  *   License along with this library; if not, write to the Free Software
27  *   Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
28  *
29  */
30
31 /*! \page control Control interface
32
33 <P>Control interface is designed to access primitive controls. There is
34 also interface notifying about control and structure changes.
35
36 \section control_general_overview General overview
37
38 The primitive controls can be integer, boolean, enumerators, bytes
39 and IEC958 structure.
40
41 */
42
43 #include <stdio.h>
44 #include <stdlib.h>
45 #include <stdint.h>
46 #include <stdarg.h>
47 #include <unistd.h>
48 #include <string.h>
49 #include <fcntl.h>
50 #include <signal.h>
51 #include <sys/poll.h>
52 #include "control_local.h"
53
54 /**
55  * \brief get identifier of CTL handle
56  * \param ctl CTL handle
57  * \return ascii identifier of CTL handle
58  *
59  * Returns the ASCII identifier of given CTL handle. It's the same
60  * identifier specified in snd_ctl_open().
61  */
62 const char *snd_ctl_name(snd_ctl_t *ctl)
63 {
64         assert(ctl);
65         return ctl->name;
66 }
67
68 /**
69  * \brief get type of CTL handle
70  * \param ctl CTL handle
71  * \return type of CTL handle
72  *
73  * Returns the type #snd_ctl_type_t of given CTL handle.
74  */
75 snd_ctl_type_t snd_ctl_type(snd_ctl_t *ctl)
76 {
77         assert(ctl);
78         return ctl->type;
79 }
80
81 /**
82  * \brief close CTL handle
83  * \param ctl CTL handle
84  * \return 0 on success otherwise a negative error code
85  *
86  * Closes the specified CTL handle and frees all associated
87  * resources.
88  */
89 int snd_ctl_close(snd_ctl_t *ctl)
90 {
91         int err;
92         while (!list_empty(&ctl->async_handlers)) {
93                 snd_async_handler_t *h = list_entry(&ctl->async_handlers.next, snd_async_handler_t, hlist);
94                 snd_async_del_handler(h);
95         }
96         err = ctl->ops->close(ctl);
97         free(ctl->name);
98         snd_dlobj_cache_put(ctl->open_func);
99         free(ctl);
100         return err;
101 }
102
103 /**
104  * \brief set nonblock mode
105  * \param ctl CTL handle
106  * \param nonblock 0 = block, 1 = nonblock mode
107  * \return 0 on success otherwise a negative error code
108  */
109 int snd_ctl_nonblock(snd_ctl_t *ctl, int nonblock)
110 {
111         int err;
112         assert(ctl);
113         err = ctl->ops->nonblock(ctl, nonblock);
114         if (err < 0)
115                 return err;
116         ctl->nonblock = nonblock;
117         return 0;
118 }
119
120 #ifndef DOC_HIDDEN
121 int snd_ctl_new(snd_ctl_t **ctlp, snd_ctl_type_t type, const char *name)
122 {
123         snd_ctl_t *ctl;
124         ctl = calloc(1, sizeof(*ctl));
125         if (!ctl)
126                 return -ENOMEM;
127         ctl->type = type;
128         if (name)
129                 ctl->name = strdup(name);
130         INIT_LIST_HEAD(&ctl->async_handlers);
131         *ctlp = ctl;
132         return 0;
133 }
134         
135
136 /**
137  * \brief set async mode
138  * \param ctl CTL handle
139  * \param sig Signal to raise: < 0 disable, 0 default (SIGIO)
140  * \param pid Process ID to signal: 0 current
141  * \return 0 on success otherwise a negative error code
142  *
143  * A signal is raised when a change happens.
144  */
145 int snd_ctl_async(snd_ctl_t *ctl, int sig, pid_t pid)
146 {
147         assert(ctl);
148         if (sig == 0)
149                 sig = SIGIO;
150         if (pid == 0)
151                 pid = getpid();
152         return ctl->ops->async(ctl, sig, pid);
153 }
154 #endif
155
156 /**
157  * \brief get count of poll descriptors for CTL handle
158  * \param ctl CTL handle
159  * \return count of poll descriptors
160  */
161 int snd_ctl_poll_descriptors_count(snd_ctl_t *ctl)
162 {
163         assert(ctl);
164         if (ctl->ops->poll_descriptors_count)
165                 return ctl->ops->poll_descriptors_count(ctl);
166         if (ctl->poll_fd < 0)
167                 return 0;
168         return 1;
169 }
170
171 /**
172  * \brief get poll descriptors
173  * \param ctl CTL handle
174  * \param pfds array of poll descriptors
175  * \param space space in the poll descriptor array
176  * \return count of filled descriptors
177  */
178 int snd_ctl_poll_descriptors(snd_ctl_t *ctl, struct pollfd *pfds, unsigned int space)
179 {
180         assert(ctl && pfds);
181         if (ctl->ops->poll_descriptors)
182                 return ctl->ops->poll_descriptors(ctl, pfds, space);
183         if (ctl->poll_fd < 0)
184                 return 0;
185         if (space > 0) {
186                 pfds->fd = ctl->poll_fd;
187                 pfds->events = POLLIN|POLLERR|POLLNVAL;
188                 return 1;
189         }
190         return 0;
191 }
192
193 /**
194  * \brief get returned events from poll descriptors
195  * \param ctl CTL handle
196  * \param pfds array of poll descriptors
197  * \param nfds count of poll descriptors
198  * \param revents returned events
199  * \return zero if success, otherwise a negative error code
200  */
201 int snd_ctl_poll_descriptors_revents(snd_ctl_t *ctl, struct pollfd *pfds, unsigned int nfds, unsigned short *revents)
202 {
203         assert(ctl && pfds && revents);
204         if (ctl->ops->poll_revents)
205                 return ctl->ops->poll_revents(ctl, pfds, nfds, revents);
206         if (nfds == 1) {
207                 *revents = pfds->revents;
208                 return 0;
209         }
210         return -EINVAL;
211 }
212
213 /**
214  * \brief Ask to be informed about events (poll, #snd_async_add_ctl_handler, #snd_ctl_read)
215  * \param ctl CTL handle
216  * \param subscribe 0 = unsubscribe, 1 = subscribe
217  * \return 0 on success otherwise a negative error code
218  */
219 int snd_ctl_subscribe_events(snd_ctl_t *ctl, int subscribe)
220 {
221         assert(ctl);
222         return ctl->ops->subscribe_events(ctl, subscribe);
223 }
224
225
226 /**
227  * \brief Get card related information
228  * \param ctl CTL handle
229  * \param info Card info pointer
230  * \return 0 on success otherwise a negative error code
231  */
232 int snd_ctl_card_info(snd_ctl_t *ctl, snd_ctl_card_info_t *info)
233 {
234         assert(ctl && info);
235         return ctl->ops->card_info(ctl, info);
236 }
237
238 /**
239  * \brief Get a list of element identifiers
240  * \param ctl CTL handle
241  * \param list CTL element identifiers list pointer
242  * \return 0 on success otherwise a negative error code
243  */
244 int snd_ctl_elem_list(snd_ctl_t *ctl, snd_ctl_elem_list_t *list)
245 {
246         assert(ctl && list);
247         assert(list->space == 0 || list->pids);
248         return ctl->ops->element_list(ctl, list);
249 }
250
251 /**
252  * \brief Get CTL element information
253  * \param ctl CTL handle
254  * \param info CTL element id/information pointer
255  * \return 0 on success otherwise a negative error code
256  */
257 int snd_ctl_elem_info(snd_ctl_t *ctl, snd_ctl_elem_info_t *info)
258 {
259         assert(ctl && info && (info->id.name[0] || info->id.numid));
260         return ctl->ops->element_info(ctl, info);
261 }
262
263 /**
264  * \brief Create and add an user INTEGER CTL element
265  * \param ctl CTL handle
266  * \param id CTL element id to add
267  * \param count number of elements
268  * \param min minimum value
269  * \param max maximum value
270  * \param step value step
271  * \return 0 on success otherwise a negative error code
272  */
273 int snd_ctl_elem_add_integer(snd_ctl_t *ctl, const snd_ctl_elem_id_t *id,
274                              unsigned int count, long min, long max, long step)
275 {
276         snd_ctl_elem_info_t *info;
277         snd_ctl_elem_value_t *val;
278         unsigned int i;
279         int err;
280
281         assert(ctl && id && id->name[0]);
282         snd_ctl_elem_info_alloca(&info);
283         info->id = *id;
284         info->type = SND_CTL_ELEM_TYPE_INTEGER;
285         info->access = SNDRV_CTL_ELEM_ACCESS_READWRITE |
286                 SNDRV_CTL_ELEM_ACCESS_TLV_READWRITE;
287         info->count = count;
288         info->value.integer.min = min;
289         info->value.integer.max = max;
290         info->value.integer.step = step;
291         err = ctl->ops->element_add(ctl, info);
292         if (err < 0)
293                 return err;
294         snd_ctl_elem_value_alloca(&val);
295         val->id = *id;
296         for (i = 0; i < count; i++)
297                 val->value.integer.value[i] = min;
298         err = ctl->ops->element_write(ctl, val);
299         return err;
300 }
301
302 /**
303  * \brief Create and add an user INTEGER64 CTL element
304  * \param ctl CTL handle
305  * \param id CTL element id to add
306  * \param count number of elements
307  * \param min minimum value
308  * \param max maximum value
309  * \param step value step
310  * \return 0 on success otherwise a negative error code
311  */
312 int snd_ctl_elem_add_integer64(snd_ctl_t *ctl, const snd_ctl_elem_id_t *id,
313                                unsigned int count, long long min, long long max,
314                                long long step)
315 {
316         snd_ctl_elem_info_t *info;
317         snd_ctl_elem_value_t *val;
318         unsigned int i;
319         int err;
320
321         assert(ctl && id && id->name[0]);
322         snd_ctl_elem_info_alloca(&info);
323         info->id = *id;
324         info->type = SND_CTL_ELEM_TYPE_INTEGER64;
325         info->count = count;
326         info->value.integer64.min = min;
327         info->value.integer64.max = max;
328         info->value.integer64.step = step;
329         err = ctl->ops->element_add(ctl, info);
330         if (err < 0)
331                 return err;
332         snd_ctl_elem_value_alloca(&val);
333         val->id = *id;
334         for (i = 0; i < count; i++)
335                 val->value.integer64.value[i] = min;
336         err = ctl->ops->element_write(ctl, val);
337         return err;
338 }
339
340 /**
341  * \brief Create and add an user BOOLEAN CTL element
342  * \param ctl CTL handle
343  * \param id CTL element id to add
344  * \param count number of elements
345  * \return 0 on success otherwise a negative error code
346  */
347 int snd_ctl_elem_add_boolean(snd_ctl_t *ctl, const snd_ctl_elem_id_t *id,
348                              unsigned int count)
349 {
350         snd_ctl_elem_info_t *info;
351
352         assert(ctl && id && id->name[0]);
353         snd_ctl_elem_info_alloca(&info);
354         info->id = *id;
355         info->type = SND_CTL_ELEM_TYPE_BOOLEAN;
356         info->count = count;
357         info->value.integer.min = 0;
358         info->value.integer.max = 1;
359         return ctl->ops->element_add(ctl, info);
360 }
361
362 /**
363  * \brief Create and add a user-defined control element of type enumerated.
364  * \param[in] ctl Control device handle.
365  * \param[in] id ID of the new control element.
366  * \param[in] count Number of element values.
367  * \param[in] items Range of possible values (0 ... \a items - 1).
368  * \param[in] names An array containing \a items strings.
369  * \return Zero on success, otherwise a negative error code.
370  *
371  * This function creates a user element, i.e., a control element that is not
372  * controlled by the control device's driver but that is just stored together
373  * with the other elements of \a ctl.
374  *
375  * The fields of \a id, except numid, must be set to unique values that
376  * identify the new element.
377  *
378  * The new element is locked; its value is initialized as zero.
379  *
380  * \par Errors:
381  * <dl>
382  * <dt>-EBUSY<dd>A control element with ID \a id already exists.
383  * <dt>-EINVAL<dd>\a count is not at least one or greater than 128, or \a items
384  *      is not at least one, or a string in \a names is empty or longer than 63
385  *      bytes, or the strings in \a names require more than 64 KB storage.
386  * <dt>-ENOMEM<dd>Out of memory, or there are too many user control elements.
387  * <dt>-ENXIO<dd>This driver does not support (enumerated) user controls.
388  * <dt>-ENODEV<dd>Device unplugged.
389  * </dl>
390  *
391  * \par Compatibility:
392  * snd_ctl_elem_add_enumerated() was introduced in ALSA 1.0.25.
393  */
394 int snd_ctl_elem_add_enumerated(snd_ctl_t *ctl, const snd_ctl_elem_id_t *id,
395                                 unsigned int count, unsigned int items,
396                                 const char *const names[])
397 {
398         snd_ctl_elem_info_t *info;
399         unsigned int i, bytes;
400         char *buf, *p;
401         int err;
402
403         assert(ctl && id && id->name[0] && names);
404
405         snd_ctl_elem_info_alloca(&info);
406         info->id = *id;
407         info->type = SND_CTL_ELEM_TYPE_ENUMERATED;
408         info->count = count;
409         info->value.enumerated.items = items;
410
411         bytes = 0;
412         for (i = 0; i < items; ++i)
413                 bytes += strlen(names[i]) + 1;
414         buf = malloc(bytes);
415         if (!buf)
416                 return -ENOMEM;
417         info->value.enumerated.names_ptr = (uintptr_t)buf;
418         info->value.enumerated.names_length = bytes;
419         p = buf;
420         for (i = 0; i < items; ++i)
421                 p = stpcpy(p, names[i]) + 1;
422
423         err = ctl->ops->element_add(ctl, info);
424
425         free(buf);
426
427         return err;
428 }
429
430 /**
431  * \brief Create and add an user IEC958 CTL element
432  * \param ctl CTL handle
433  * \param id CTL element info to add
434  * \return 0 on success otherwise a negative error code
435  */
436 int snd_ctl_elem_add_iec958(snd_ctl_t *ctl, const snd_ctl_elem_id_t *id)
437 {
438         snd_ctl_elem_info_t *info;
439
440         assert(ctl && id && id->name[0]);
441         snd_ctl_elem_info_alloca(&info);
442         info->id = *id;
443         info->type = SND_CTL_ELEM_TYPE_IEC958;
444         info->count = 1;
445         return ctl->ops->element_add(ctl, info);
446 }
447
448 /**
449  * \brief Remove an user CTL element
450  * \param ctl CTL handle
451  * \param id CTL element identification
452  * \return 0 on success otherwise a negative error code
453  */
454 int snd_ctl_elem_remove(snd_ctl_t *ctl, snd_ctl_elem_id_t *id)
455 {
456         assert(ctl && id && (id->name[0] || id->numid));
457         return ctl->ops->element_remove(ctl, id);
458 }
459
460 /**
461  * \brief Get CTL element value
462  * \param ctl CTL handle
463  * \param control CTL element id/value pointer
464  * \return 0 on success otherwise a negative error code
465  */
466 int snd_ctl_elem_read(snd_ctl_t *ctl, snd_ctl_elem_value_t *control)
467 {
468         assert(ctl && control && (control->id.name[0] || control->id.numid));
469         return ctl->ops->element_read(ctl, control);
470 }
471
472 /**
473  * \brief Set CTL element value
474  * \param ctl CTL handle
475  * \param control CTL element id/value pointer
476  * \retval 0 on success
477  * \retval >0 on success when value was changed
478  * \retval <0 a negative error code
479  */
480 int snd_ctl_elem_write(snd_ctl_t *ctl, snd_ctl_elem_value_t *control)
481 {
482         assert(ctl && control && (control->id.name[0] || control->id.numid));
483         return ctl->ops->element_write(ctl, control);
484 }
485
486 static int snd_ctl_tlv_do(snd_ctl_t *ctl, int op_flag,
487                           const snd_ctl_elem_id_t *id,
488                           unsigned int *tlv, unsigned int tlv_size)
489 {
490         snd_ctl_elem_info_t *info = NULL;
491         int err;
492
493         if (id->numid == 0) {
494                 info = calloc(1, sizeof(*info));
495                 if (info == NULL)
496                         return -ENOMEM;
497                 info->id = *id;
498                 id = &info->id;
499                 err = snd_ctl_elem_info(ctl, info);
500                 if (err < 0)
501                         goto __err;
502                 if (id->numid == 0) {
503                         err = -ENOENT;
504                         goto __err;
505                 }
506         }
507         err = ctl->ops->element_tlv(ctl, op_flag, id->numid, tlv, tlv_size);
508       __err:
509         if (info)
510                 free(info);
511         return err;
512 }
513
514
515
516 /**
517  * \brief Get CTL element TLV value
518  * \param ctl CTL handle
519  * \param id CTL element id pointer
520  * \param tlv TLV array pointer to store 
521  * \param tlv_size TLV array size in bytes
522  * \return 0 on success otherwise a negative error code
523  */
524 int snd_ctl_elem_tlv_read(snd_ctl_t *ctl, const snd_ctl_elem_id_t *id,
525                           unsigned int *tlv, unsigned int tlv_size)
526 {
527         int err;
528         assert(ctl && id && (id->name[0] || id->numid) && tlv);
529         if (tlv_size < 2 * sizeof(int))
530                 return -EINVAL;
531         /* 1.0.12 driver doesn't return the error even if the user TLV
532          * is empty.  So, initialize TLV here with an invalid type
533          * and compare the returned value after ioctl for checking
534          * the validity of TLV.
535          */
536         tlv[0] = -1;
537         tlv[1] = 0;
538         err = snd_ctl_tlv_do(ctl, 0, id, tlv, tlv_size);
539         if (err >= 0 && tlv[0] == (unsigned int)-1)
540                 err = -ENXIO;
541         return err;
542 }
543
544 /**
545  * \brief Set CTL element TLV value
546  * \param ctl CTL handle
547  * \param id CTL element id pointer
548  * \param tlv TLV array pointer to store 
549  * \retval 0 on success
550  * \retval >0 on success when value was changed
551  * \retval <0 a negative error code
552  */
553 int snd_ctl_elem_tlv_write(snd_ctl_t *ctl, const snd_ctl_elem_id_t *id,
554                            const unsigned int *tlv)
555 {
556         assert(ctl && id && (id->name[0] || id->numid) && tlv);
557         return snd_ctl_tlv_do(ctl, 1, id, (unsigned int *)tlv, tlv[1] + 2 * sizeof(unsigned int));
558 }
559
560 /**
561  * \brief Process CTL element TLV command
562  * \param ctl CTL handle
563  * \param id CTL element id pointer
564  * \param tlv TLV array pointer to process
565  * \retval 0 on success
566  * \retval >0 on success when value was changed
567  * \retval <0 a negative error code
568  */
569 int snd_ctl_elem_tlv_command(snd_ctl_t *ctl, const snd_ctl_elem_id_t *id,
570                              const unsigned int *tlv)
571 {
572         assert(ctl && id && (id->name[0] || id->numid) && tlv);
573         return snd_ctl_tlv_do(ctl, -1, id, (unsigned int *)tlv, tlv[1] + 2 * sizeof(unsigned int));
574 }
575
576 /**
577  * \brief Lock CTL element
578  * \param ctl CTL handle
579  * \param id CTL element id pointer
580  * \return 0 on success otherwise a negative error code
581  */
582 int snd_ctl_elem_lock(snd_ctl_t *ctl, snd_ctl_elem_id_t *id)
583 {
584         assert(ctl && id);
585         return ctl->ops->element_lock(ctl, id);
586 }
587
588 /**
589  * \brief Unlock CTL element
590  * \param ctl CTL handle
591  * \param id CTL element id pointer
592  * \return 0 on success otherwise a negative error code
593  */
594 int snd_ctl_elem_unlock(snd_ctl_t *ctl, snd_ctl_elem_id_t *id)
595 {
596         assert(ctl && id);
597         return ctl->ops->element_unlock(ctl, id);
598 }
599
600 /**
601  * \brief Get next hardware dependent device number
602  * \param ctl CTL handle
603  * \param device current device on entry and next device on return
604  * \return 0 on success otherwise a negative error code
605  */
606 int snd_ctl_hwdep_next_device(snd_ctl_t *ctl, int *device)
607 {
608         assert(ctl && device);
609         return ctl->ops->hwdep_next_device(ctl, device);
610 }
611
612 /**
613  * \brief Get info about a hardware dependent device
614  * \param ctl CTL handle
615  * \param info Hardware dependent device id/info pointer
616  * \return 0 on success otherwise a negative error code
617  */
618 int snd_ctl_hwdep_info(snd_ctl_t *ctl, snd_hwdep_info_t * info)
619 {
620         assert(ctl && info);
621         return ctl->ops->hwdep_info(ctl, info);
622 }
623
624 /**
625  * \brief Get next PCM device number
626  * \param ctl CTL handle
627  * \param device current device on entry and next device on return
628  * \return 0 on success otherwise a negative error code
629  */
630 int snd_ctl_pcm_next_device(snd_ctl_t *ctl, int * device)
631 {
632         assert(ctl && device);
633         return ctl->ops->pcm_next_device(ctl, device);
634 }
635
636 /**
637  * \brief Get info about a PCM device
638  * \param ctl CTL handle
639  * \param info PCM device id/info pointer
640  * \return 0 on success otherwise a negative error code
641  */
642 int snd_ctl_pcm_info(snd_ctl_t *ctl, snd_pcm_info_t * info)
643 {
644         assert(ctl && info);
645         return ctl->ops->pcm_info(ctl, info);
646 }
647
648 /**
649  * \brief Set preferred PCM subdevice number of successive PCM open
650  * \param ctl CTL handle
651  * \param subdev Preferred PCM subdevice number
652  * \return 0 on success otherwise a negative error code
653  */
654 int snd_ctl_pcm_prefer_subdevice(snd_ctl_t *ctl, int subdev)
655 {
656         assert(ctl);
657         return ctl->ops->pcm_prefer_subdevice(ctl, subdev);
658 }
659
660 /**
661  * \brief Get next RawMidi device number
662  * \param ctl CTL handle
663  * \param device current device on entry and next device on return
664  * \return 0 on success otherwise a negative error code
665  */
666 int snd_ctl_rawmidi_next_device(snd_ctl_t *ctl, int * device)
667 {
668         assert(ctl && device);
669         return ctl->ops->rawmidi_next_device(ctl, device);
670 }
671
672 /**
673  * \brief Get info about a RawMidi device
674  * \param ctl CTL handle
675  * \param info RawMidi device id/info pointer
676  * \return 0 on success otherwise a negative error code
677  */
678 int snd_ctl_rawmidi_info(snd_ctl_t *ctl, snd_rawmidi_info_t * info)
679 {
680         assert(ctl && info);
681         return ctl->ops->rawmidi_info(ctl, info);
682 }
683
684 /**
685  * \brief Set preferred RawMidi subdevice number of successive RawMidi open
686  * \param ctl CTL handle
687  * \param subdev Preferred RawMidi subdevice number
688  * \return 0 on success otherwise a negative error code
689  */
690 int snd_ctl_rawmidi_prefer_subdevice(snd_ctl_t *ctl, int subdev)
691 {
692         assert(ctl);
693         return ctl->ops->rawmidi_prefer_subdevice(ctl, subdev);
694 }
695
696 /**
697  * \brief Set Power State to given SND_CTL_POWER_* value and do the power management
698  * \param ctl CTL handle
699  * \param state Desired Power State
700  * \return 0 on success otherwise a negative error code
701  */
702 int snd_ctl_set_power_state(snd_ctl_t *ctl, unsigned int state)
703 {
704         assert(ctl);
705         if (ctl->ops->set_power_state)
706                 return ctl->ops->set_power_state(ctl, state);
707         return -ENXIO;
708 }
709
710 /**
711  * \brief Get actual Power State
712  * \param ctl CTL handle
713  * \param state Destination value
714  * \return 0 on success otherwise a negative error code
715  */
716 int snd_ctl_get_power_state(snd_ctl_t *ctl, unsigned int *state)
717 {
718         assert(ctl);
719         if (ctl->ops->get_power_state)
720                 return ctl->ops->get_power_state(ctl, state);
721         return -ENXIO;
722 }
723
724 /**
725  * \brief Read an event
726  * \param ctl CTL handle
727  * \param event Event pointer
728  * \return number of events read otherwise a negative error code on failure
729  */
730 int snd_ctl_read(snd_ctl_t *ctl, snd_ctl_event_t *event)
731 {
732         assert(ctl && event);
733         return (ctl->ops->read)(ctl, event);
734 }
735
736 /**
737  * \brief Wait for a CTL to become ready (i.e. at least one event pending)
738  * \param ctl CTL handle
739  * \param timeout maximum time in milliseconds to wait
740  * \return 0 otherwise a negative error code on failure
741  */
742 int snd_ctl_wait(snd_ctl_t *ctl, int timeout)
743 {
744         struct pollfd *pfd;
745         unsigned short revents;
746         int npfds, err, err_poll;
747
748         npfds = snd_ctl_poll_descriptors_count(ctl);
749         if (npfds <= 0 || npfds >= 16) {
750                 SNDERR("Invalid poll_fds %d\n", npfds);
751                 return -EIO;
752         }
753         pfd = alloca(sizeof(*pfd) * npfds);
754         err = snd_ctl_poll_descriptors(ctl, pfd, npfds);
755         if (err < 0)
756                 return err;
757         if (err != npfds) {
758                 SNDMSG("invalid poll descriptors %d\n", err);
759                 return -EIO;
760         }
761         for (;;) {
762                 err_poll = poll(pfd, npfds, timeout);
763                 if (err_poll < 0)
764                         return -errno;
765                 if (! err_poll)
766                         return 0;
767                 err = snd_ctl_poll_descriptors_revents(ctl, pfd, npfds, &revents);
768                 if (err < 0)
769                         return err;
770                 if (revents & (POLLERR | POLLNVAL))
771                         return -EIO;
772                 if (revents & (POLLIN | POLLOUT))
773                         return 1;
774         }
775 }
776
777 /**
778  * \brief Add an async handler for a CTL
779  * \param handler Returned handler handle
780  * \param ctl CTL handle
781  * \param callback Callback function
782  * \param private_data Callback private data
783  * \return 0 otherwise a negative error code on failure
784  */
785 int snd_async_add_ctl_handler(snd_async_handler_t **handler, snd_ctl_t *ctl, 
786                               snd_async_callback_t callback, void *private_data)
787 {
788         int err;
789         int was_empty;
790         snd_async_handler_t *h;
791         err = snd_async_add_handler(&h, _snd_ctl_async_descriptor(ctl),
792                                     callback, private_data);
793         if (err < 0)
794                 return err;
795         h->type = SND_ASYNC_HANDLER_CTL;
796         h->u.ctl = ctl;
797         was_empty = list_empty(&ctl->async_handlers);
798         list_add_tail(&h->hlist, &ctl->async_handlers);
799         if (was_empty) {
800                 err = snd_ctl_async(ctl, snd_async_handler_get_signo(h), getpid());
801                 if (err < 0) {
802                         snd_async_del_handler(h);
803                         return err;
804                 }
805         }
806         *handler = h;
807         return 0;
808 }
809
810 /**
811  * \brief Return CTL handle related to an async handler
812  * \param handler Async handler handle
813  * \return CTL handle
814  */
815 snd_ctl_t *snd_async_handler_get_ctl(snd_async_handler_t *handler)
816 {
817         assert(handler->type == SND_ASYNC_HANDLER_CTL);
818         return handler->u.ctl;
819 }
820
821 static const char *const build_in_ctls[] = {
822         "hw", "shm", NULL
823 };
824
825 static int snd_ctl_open_conf(snd_ctl_t **ctlp, const char *name,
826                              snd_config_t *ctl_root, snd_config_t *ctl_conf, int mode)
827 {
828         const char *str;
829         char *buf = NULL, *buf1 = NULL;
830         int err;
831         snd_config_t *conf, *type_conf = NULL;
832         snd_config_iterator_t i, next;
833         const char *lib = NULL, *open_name = NULL;
834         const char *id;
835         int (*open_func)(snd_ctl_t **, const char *, snd_config_t *, snd_config_t *, int) = NULL;
836 #ifndef PIC
837         extern void *snd_control_open_symbols(void);
838 #endif
839         if (snd_config_get_type(ctl_conf) != SND_CONFIG_TYPE_COMPOUND) {
840                 if (name)
841                         SNDERR("Invalid type for CTL %s definition", name);
842                 else
843                         SNDERR("Invalid type for CTL definition");
844                 return -EINVAL;
845         }
846         err = snd_config_search(ctl_conf, "type", &conf);
847         if (err < 0) {
848                 SNDERR("type is not defined");
849                 return err;
850         }
851         err = snd_config_get_id(conf, &id);
852         if (err < 0) {
853                 SNDERR("unable to get id");
854                 return err;
855         }
856         err = snd_config_get_string(conf, &str);
857         if (err < 0) {
858                 SNDERR("Invalid type for %s", id);
859                 return err;
860         }
861         err = snd_config_search_definition(ctl_root, "ctl_type", str, &type_conf);
862         if (err >= 0) {
863                 if (snd_config_get_type(type_conf) != SND_CONFIG_TYPE_COMPOUND) {
864                         SNDERR("Invalid type for CTL type %s definition", str);
865                         goto _err;
866                 }
867                 snd_config_for_each(i, next, type_conf) {
868                         snd_config_t *n = snd_config_iterator_entry(i);
869                         const char *id;
870                         if (snd_config_get_id(n, &id) < 0)
871                                 continue;
872                         if (strcmp(id, "comment") == 0)
873                                 continue;
874                         if (strcmp(id, "lib") == 0) {
875                                 err = snd_config_get_string(n, &lib);
876                                 if (err < 0) {
877                                         SNDERR("Invalid type for %s", id);
878                                         goto _err;
879                                 }
880                                 continue;
881                         }
882                         if (strcmp(id, "open") == 0) {
883                                 err = snd_config_get_string(n, &open_name);
884                                 if (err < 0) {
885                                         SNDERR("Invalid type for %s", id);
886                                         goto _err;
887                                 }
888                                 continue;
889                         }
890                         SNDERR("Unknown field %s", id);
891                         err = -EINVAL;
892                         goto _err;
893                 }
894         }
895         if (!open_name) {
896                 buf = malloc(strlen(str) + 32);
897                 if (buf == NULL) {
898                         err = -ENOMEM;
899                         goto _err;
900                 }
901                 open_name = buf;
902                 sprintf(buf, "_snd_ctl_%s_open", str);
903         }
904         if (!lib) {
905                 const char *const *build_in = build_in_ctls;
906                 while (*build_in) {
907                         if (!strcmp(*build_in, str))
908                                 break;
909                         build_in++;
910                 }
911                 if (*build_in == NULL) {
912                         buf1 = malloc(strlen(str) + sizeof(ALSA_PLUGIN_DIR) + 32);
913                         if (buf1 == NULL) {
914                                 err = -ENOMEM;
915                                 goto _err;
916                         }
917                         lib = buf1;
918                         sprintf(buf1, "%s/libasound_module_ctl_%s.so", ALSA_PLUGIN_DIR, str);
919                 }
920         }
921 #ifndef PIC
922         snd_control_open_symbols();
923 #endif
924         open_func = snd_dlobj_cache_get(lib, open_name,
925                         SND_DLSYM_VERSION(SND_CONTROL_DLSYM_VERSION), 1);
926         if (open_func) {
927                 err = open_func(ctlp, name, ctl_root, ctl_conf, mode);
928                 if (err >= 0) {
929                         (*ctlp)->open_func = open_func;
930                         err = 0;
931                 } else {
932                         snd_dlobj_cache_put(open_func);
933                 }
934         } else {
935                 err = -ENXIO;
936         }
937        _err:
938         if (type_conf)
939                 snd_config_delete(type_conf);
940         free(buf);
941         free(buf1);
942         return err;
943 }
944
945 static int snd_ctl_open_noupdate(snd_ctl_t **ctlp, snd_config_t *root, const char *name, int mode)
946 {
947         int err;
948         snd_config_t *ctl_conf;
949         err = snd_config_search_definition(root, "ctl", name, &ctl_conf);
950         if (err < 0) {
951                 SNDERR("Invalid CTL %s", name);
952                 return err;
953         }
954         err = snd_ctl_open_conf(ctlp, name, root, ctl_conf, mode);
955         snd_config_delete(ctl_conf);
956         return err;
957 }
958
959 /**
960  * \brief Opens a CTL
961  * \param ctlp Returned CTL handle
962  * \param name ASCII identifier of the CTL handle
963  * \param mode Open mode (see #SND_CTL_NONBLOCK, #SND_CTL_ASYNC)
964  * \return 0 on success otherwise a negative error code
965  */
966 int snd_ctl_open(snd_ctl_t **ctlp, const char *name, int mode)
967 {
968         int err;
969         assert(ctlp && name);
970         err = snd_config_update();
971         if (err < 0)
972                 return err;
973         return snd_ctl_open_noupdate(ctlp, snd_config, name, mode);
974 }
975
976 /**
977  * \brief Opens a CTL using local configuration
978  * \param ctlp Returned CTL handle
979  * \param name ASCII identifier of the CTL handle
980  * \param mode Open mode (see #SND_CTL_NONBLOCK, #SND_CTL_ASYNC)
981  * \param lconf Local configuration
982  * \return 0 on success otherwise a negative error code
983  */
984 int snd_ctl_open_lconf(snd_ctl_t **ctlp, const char *name,
985                        int mode, snd_config_t *lconf)
986 {
987         assert(ctlp && name && lconf);
988         return snd_ctl_open_noupdate(ctlp, lconf, name, mode);
989 }
990
991 /**
992  * \brief Opens a fallback CTL
993  * \param ctlp Returned CTL handle
994  * \param root Configuration root
995  * \param name ASCII identifier of the CTL handle used as fallback
996  * \param orig_name The original ASCII name
997  * \param mode Open mode (see #SND_CTL_NONBLOCK, #SND_CTL_ASYNC)
998  * \return 0 on success otherwise a negative error code
999  */
1000 int snd_ctl_open_fallback(snd_ctl_t **ctlp, snd_config_t *root,
1001                           const char *name, const char *orig_name, int mode)
1002 {
1003         int err;
1004         assert(ctlp && name && root);
1005         err = snd_ctl_open_noupdate(ctlp, root, name, mode);
1006         if (err >= 0) {
1007                 free((*ctlp)->name);
1008                 (*ctlp)->name = orig_name ? strdup(orig_name) : NULL;
1009         }
1010         return err;
1011 }
1012
1013 #ifndef DOC_HIDDEN
1014 #define TYPE(v) [SND_CTL_ELEM_TYPE_##v] = #v
1015 #define IFACE(v) [SND_CTL_ELEM_IFACE_##v] = #v
1016 #define IFACE1(v, n) [SND_CTL_ELEM_IFACE_##v] = #n
1017 #define EVENT(v) [SND_CTL_EVENT_##v] = #v
1018
1019 static const char *const snd_ctl_elem_type_names[] = {
1020         TYPE(NONE),
1021         TYPE(BOOLEAN),
1022         TYPE(INTEGER),
1023         TYPE(ENUMERATED),
1024         TYPE(BYTES),
1025         TYPE(IEC958),
1026         TYPE(INTEGER64),
1027 };
1028
1029 static const char *const snd_ctl_elem_iface_names[] = {
1030         IFACE(CARD),
1031         IFACE(HWDEP),
1032         IFACE(MIXER),
1033         IFACE(PCM),
1034         IFACE(RAWMIDI),
1035         IFACE(TIMER),
1036         IFACE(SEQUENCER),
1037 };
1038
1039 static const char *const snd_ctl_event_type_names[] = {
1040         EVENT(ELEM),
1041 };
1042 #endif
1043
1044 /**
1045  * \brief get name of a CTL element type
1046  * \param type CTL element type
1047  * \return ascii name of CTL element type
1048  */
1049 const char *snd_ctl_elem_type_name(snd_ctl_elem_type_t type)
1050 {
1051         assert(type <= SND_CTL_ELEM_TYPE_LAST);
1052         return snd_ctl_elem_type_names[type];
1053 }
1054
1055 /**
1056  * \brief get name of a CTL element related interface
1057  * \param iface CTL element related interface
1058  * \return ascii name of CTL element related interface
1059  */
1060 const char *snd_ctl_elem_iface_name(snd_ctl_elem_iface_t iface)
1061 {
1062         assert(iface <= SND_CTL_ELEM_IFACE_LAST);
1063         return snd_ctl_elem_iface_names[iface];
1064 }
1065
1066 /**
1067  * \brief get name of a CTL event type
1068  * \param type CTL event type
1069  * \return ascii name of CTL event type
1070  */
1071 const char *snd_ctl_event_type_name(snd_ctl_event_type_t type)
1072 {
1073         assert(type <= SND_CTL_EVENT_LAST);
1074         return snd_ctl_event_type_names[type];
1075 }
1076
1077 /**
1078  * \brief allocate space for CTL element identifiers list
1079  * \param obj CTL element identifiers list
1080  * \param entries Entries to allocate
1081  * \return 0 on success otherwise a negative error code
1082  */
1083 int snd_ctl_elem_list_alloc_space(snd_ctl_elem_list_t *obj, unsigned int entries)
1084 {
1085         free(obj->pids);
1086         obj->pids = calloc(entries, sizeof(*obj->pids));
1087         if (!obj->pids) {
1088                 obj->space = 0;
1089                 return -ENOMEM;
1090         }
1091         obj->space = entries;
1092         return 0;
1093 }  
1094
1095 /**
1096  * \brief free previously allocated space for CTL element identifiers list
1097  * \param obj CTL element identifiers list
1098  */
1099 void snd_ctl_elem_list_free_space(snd_ctl_elem_list_t *obj)
1100 {
1101         free(obj->pids);
1102         obj->pids = NULL;
1103         obj->space = 0;
1104 }
1105
1106 /**
1107  * \brief Get event mask for an element related event
1108  * \param obj CTL event
1109  * \return event mask for element related event
1110  */
1111 unsigned int snd_ctl_event_elem_get_mask(const snd_ctl_event_t *obj)
1112 {
1113         assert(obj);
1114         assert(obj->type == SND_CTL_EVENT_ELEM);
1115         return obj->data.elem.mask;
1116 }
1117
1118 /**
1119  * \brief Get CTL element identifier for an element related event
1120  * \param obj CTL event
1121  * \param ptr Pointer to returned CTL element identifier
1122  */
1123 void snd_ctl_event_elem_get_id(const snd_ctl_event_t *obj, snd_ctl_elem_id_t *ptr)
1124 {
1125         assert(obj && ptr);
1126         assert(obj->type == SND_CTL_EVENT_ELEM);
1127         *ptr = obj->data.elem.id;
1128 }
1129
1130 /**
1131  * \brief Get element numeric identifier for an element related event
1132  * \param obj CTL event
1133  * \return element numeric identifier
1134  */
1135 unsigned int snd_ctl_event_elem_get_numid(const snd_ctl_event_t *obj)
1136 {
1137         assert(obj);
1138         assert(obj->type == SND_CTL_EVENT_ELEM);
1139         return obj->data.elem.id.numid;
1140 }
1141
1142 /**
1143  * \brief Get interface part of CTL element identifier for an element related event
1144  * \param obj CTL event
1145  * \return interface part of element identifier
1146  */
1147 snd_ctl_elem_iface_t snd_ctl_event_elem_get_interface(const snd_ctl_event_t *obj)
1148 {
1149         assert(obj);
1150         assert(obj->type == SND_CTL_EVENT_ELEM);
1151         return obj->data.elem.id.iface;
1152 }
1153
1154 /**
1155  * \brief Get device part of CTL element identifier for an element related event
1156  * \param obj CTL event
1157  * \return device part of element identifier
1158  */
1159 unsigned int snd_ctl_event_elem_get_device(const snd_ctl_event_t *obj)
1160 {
1161         assert(obj);
1162         assert(obj->type == SND_CTL_EVENT_ELEM);
1163         return obj->data.elem.id.device;
1164 }
1165
1166 /**
1167  * \brief Get subdevice part of CTL element identifier for an element related event
1168  * \param obj CTL event
1169  * \return subdevice part of element identifier
1170  */
1171 unsigned int snd_ctl_event_elem_get_subdevice(const snd_ctl_event_t *obj)
1172 {
1173         assert(obj);
1174         assert(obj->type == SND_CTL_EVENT_ELEM);
1175         return obj->data.elem.id.subdevice;
1176 }
1177
1178 /**
1179  * \brief Get name part of CTL element identifier for an element related event
1180  * \param obj CTL event
1181  * \return name part of element identifier
1182  */
1183 const char *snd_ctl_event_elem_get_name(const snd_ctl_event_t *obj)
1184 {
1185         assert(obj);
1186         assert(obj->type == SND_CTL_EVENT_ELEM);
1187         return (const char *)obj->data.elem.id.name;
1188 }
1189
1190 /**
1191  * \brief Get index part of CTL element identifier for an element related event
1192  * \param obj CTL event
1193  * \return index part of element identifier
1194  */
1195 unsigned int snd_ctl_event_elem_get_index(const snd_ctl_event_t *obj)
1196 {
1197         assert(obj);
1198         assert(obj->type == SND_CTL_EVENT_ELEM);
1199         return obj->data.elem.id.index;
1200 }
1201
1202 #ifndef DOC_HIDDEN
1203 int _snd_ctl_poll_descriptor(snd_ctl_t *ctl)
1204 {
1205         assert(ctl);
1206         return ctl->poll_fd;
1207 }
1208 #endif
1209
1210 /**
1211  * \brief get size of #snd_ctl_elem_id_t
1212  * \return size in bytes
1213  */
1214 size_t snd_ctl_elem_id_sizeof()
1215 {
1216         return sizeof(snd_ctl_elem_id_t);
1217 }
1218
1219 /**
1220  * \brief allocate an invalid #snd_ctl_elem_id_t using standard malloc
1221  * \param ptr returned pointer
1222  * \return 0 on success otherwise negative error code
1223  */
1224 int snd_ctl_elem_id_malloc(snd_ctl_elem_id_t **ptr)
1225 {
1226         assert(ptr);
1227         *ptr = calloc(1, sizeof(snd_ctl_elem_id_t));
1228         if (!*ptr)
1229                 return -ENOMEM;
1230         return 0;
1231 }
1232
1233 /**
1234  * \brief frees a previously allocated #snd_ctl_elem_id_t
1235  * \param obj pointer to object to free
1236  */
1237 void snd_ctl_elem_id_free(snd_ctl_elem_id_t *obj)
1238 {
1239         free(obj);
1240 }
1241
1242 /**
1243  * \brief clear given #snd_ctl_elem_id_t object
1244  * \param obj pointer to object to clear
1245  */
1246 void snd_ctl_elem_id_clear(snd_ctl_elem_id_t *obj)
1247 {
1248         memset(obj, 0, sizeof(snd_ctl_elem_id_t));
1249 }
1250
1251 /**
1252  * \brief copy one #snd_ctl_elem_id_t to another
1253  * \param dst pointer to destination
1254  * \param src pointer to source
1255  */
1256 void snd_ctl_elem_id_copy(snd_ctl_elem_id_t *dst, const snd_ctl_elem_id_t *src)
1257 {
1258         assert(dst && src);
1259         *dst = *src;
1260 }
1261
1262 /**
1263  * \brief Get numeric identifier from a CTL element identifier
1264  * \param obj CTL element identifier
1265  * \return CTL element numeric identifier
1266  */
1267 unsigned int snd_ctl_elem_id_get_numid(const snd_ctl_elem_id_t *obj)
1268 {
1269         assert(obj);
1270         return obj->numid;
1271 }
1272
1273 /**
1274  * \brief Get interface part of a CTL element identifier
1275  * \param obj CTL element identifier
1276  * \return CTL element related interface
1277  */
1278 snd_ctl_elem_iface_t snd_ctl_elem_id_get_interface(const snd_ctl_elem_id_t *obj)
1279 {
1280         assert(obj);
1281         return obj->iface;
1282 }
1283
1284 /**
1285  * \brief Get device part of a CTL element identifier
1286  * \param obj CTL element identifier
1287  * \return CTL element related device
1288  */
1289 unsigned int snd_ctl_elem_id_get_device(const snd_ctl_elem_id_t *obj)
1290 {
1291         assert(obj);
1292         return obj->device;
1293 }
1294
1295 /**
1296  * \brief Get subdevice part of a CTL element identifier
1297  * \param obj CTL element identifier
1298  * \return CTL element related subdevice
1299  */
1300 unsigned int snd_ctl_elem_id_get_subdevice(const snd_ctl_elem_id_t *obj)
1301 {
1302         assert(obj);
1303         return obj->subdevice;
1304 }
1305
1306 /**
1307  * \brief Get name part of a CTL element identifier
1308  * \param obj CTL element identifier
1309  * \return CTL element name
1310  */
1311 const char *snd_ctl_elem_id_get_name(const snd_ctl_elem_id_t *obj)
1312 {
1313         assert(obj);
1314         return (const char *)obj->name;
1315 }
1316
1317 /**
1318  * \brief Get index part of a CTL element identifier
1319  * \param obj CTL element identifier
1320  * \return CTL element index
1321  */
1322 unsigned int snd_ctl_elem_id_get_index(const snd_ctl_elem_id_t *obj)
1323 {
1324         assert(obj);
1325         return obj->index;
1326 }
1327
1328 /**
1329  * \brief Set numeric identifier for a CTL element identifier
1330  * \param obj CTL element identifier
1331  * \param val CTL element numeric identifier
1332  */
1333 void snd_ctl_elem_id_set_numid(snd_ctl_elem_id_t *obj, unsigned int val)
1334 {
1335         assert(obj);
1336         obj->numid = val;
1337 }
1338
1339 /**
1340  * \brief Set interface part for a CTL element identifier
1341  * \param obj CTL element identifier
1342  * \param val CTL element related interface
1343  */
1344 void snd_ctl_elem_id_set_interface(snd_ctl_elem_id_t *obj, snd_ctl_elem_iface_t val)
1345 {
1346         assert(obj);
1347         obj->iface = val;
1348 }
1349
1350 /**
1351  * \brief Set device part for a CTL element identifier
1352  * \param obj CTL element identifier
1353  * \param val CTL element related device
1354  */
1355 void snd_ctl_elem_id_set_device(snd_ctl_elem_id_t *obj, unsigned int val)
1356 {
1357         assert(obj);
1358         obj->device = val;
1359 }
1360
1361 /**
1362  * \brief Set subdevice part for a CTL element identifier
1363  * \param obj CTL element identifier
1364  * \param val CTL element related subdevice
1365  */
1366 void snd_ctl_elem_id_set_subdevice(snd_ctl_elem_id_t *obj, unsigned int val)
1367 {
1368         assert(obj);
1369         obj->subdevice = val;
1370 }
1371
1372 /**
1373  * \brief Set name part for a CTL element identifier
1374  * \param obj CTL element identifier
1375  * \param val CTL element name
1376  */
1377 void snd_ctl_elem_id_set_name(snd_ctl_elem_id_t *obj, const char *val)
1378 {
1379         assert(obj);
1380         strncpy((char *)obj->name, val, sizeof(obj->name));
1381 }
1382
1383 /**
1384  * \brief Set index part for a CTL element identifier
1385  * \param obj CTL element identifier
1386  * \param val CTL element index
1387  */
1388 void snd_ctl_elem_id_set_index(snd_ctl_elem_id_t *obj, unsigned int val)
1389 {
1390         assert(obj);
1391         obj->index = val;
1392 }
1393
1394 /**
1395  * \brief get size of #snd_ctl_card_info_t
1396  * \return size in bytes
1397  */
1398 size_t snd_ctl_card_info_sizeof()
1399 {
1400         return sizeof(snd_ctl_card_info_t);
1401 }
1402
1403 /**
1404  * \brief allocate an invalid #snd_ctl_card_info_t using standard malloc
1405  * \param ptr returned pointer
1406  * \return 0 on success otherwise negative error code
1407  */
1408 int snd_ctl_card_info_malloc(snd_ctl_card_info_t **ptr)
1409 {
1410         assert(ptr);
1411         *ptr = calloc(1, sizeof(snd_ctl_card_info_t));
1412         if (!*ptr)
1413                 return -ENOMEM;
1414         return 0;
1415 }
1416
1417 /**
1418  * \brief frees a previously allocated #snd_ctl_card_info_t
1419  * \param obj pointer to object to free
1420  */
1421 void snd_ctl_card_info_free(snd_ctl_card_info_t *obj)
1422 {
1423         free(obj);
1424 }
1425
1426 /**
1427  * \brief clear given #snd_ctl_card_info_t object
1428  * \param obj pointer to object to clear
1429  */
1430 void snd_ctl_card_info_clear(snd_ctl_card_info_t *obj)
1431 {
1432         memset(obj, 0, sizeof(snd_ctl_card_info_t));
1433 }
1434
1435 /**
1436  * \brief copy one #snd_ctl_card_info_t to another
1437  * \param dst pointer to destination
1438  * \param src pointer to source
1439  */
1440 void snd_ctl_card_info_copy(snd_ctl_card_info_t *dst, const snd_ctl_card_info_t *src)
1441 {
1442         assert(dst && src);
1443         *dst = *src;
1444 }
1445
1446 /**
1447  * \brief Get card number from a CTL card info
1448  * \param obj CTL card info
1449  * \return card number
1450  */
1451 int snd_ctl_card_info_get_card(const snd_ctl_card_info_t *obj)
1452 {
1453         assert(obj);
1454         return obj->card;
1455 }
1456
1457 /**
1458  * \brief Get card identifier from a CTL card info
1459  * \param obj CTL card info
1460  * \return card identifier
1461  */
1462 const char *snd_ctl_card_info_get_id(const snd_ctl_card_info_t *obj)
1463 {
1464         assert(obj);
1465         return (const char *)obj->id;
1466 }
1467
1468 /**
1469  * \brief Get card driver name from a CTL card info
1470  * \param obj CTL card info
1471  * \return card driver name
1472  */
1473 const char *snd_ctl_card_info_get_driver(const snd_ctl_card_info_t *obj)
1474 {
1475         assert(obj);
1476         return (const char *)obj->driver;
1477 }
1478
1479 /**
1480  * \brief Get card name from a CTL card info
1481  * \param obj CTL card info
1482  * \return card name
1483  */
1484 const char *snd_ctl_card_info_get_name(const snd_ctl_card_info_t *obj)
1485 {
1486         assert(obj);
1487         return (const char *)obj->name;
1488 }
1489
1490 /**
1491  * \brief Get card long name from a CTL card info
1492  * \param obj CTL card info
1493  * \return card long name
1494  */
1495 const char *snd_ctl_card_info_get_longname(const snd_ctl_card_info_t *obj)
1496 {
1497         assert(obj);
1498         return (const char *)obj->longname;
1499 }
1500
1501 /**
1502  * \brief Get card mixer name from a CTL card info
1503  * \param obj CTL card info
1504  * \return card mixer name
1505  */
1506 const char *snd_ctl_card_info_get_mixername(const snd_ctl_card_info_t *obj)
1507 {
1508         assert(obj);
1509         return (const char *)obj->mixername;
1510 }
1511
1512 /**
1513  * \brief Get card component list from a CTL card info
1514  * \param obj CTL card info
1515  * \return card mixer identifier
1516  */
1517 const char *snd_ctl_card_info_get_components(const snd_ctl_card_info_t *obj)
1518 {
1519         assert(obj);
1520         return (const char *)obj->components;
1521 }
1522
1523 /**
1524  * \brief get size of #snd_ctl_event_t
1525  * \return size in bytes
1526  */
1527 size_t snd_ctl_event_sizeof()
1528 {
1529         return sizeof(snd_ctl_event_t);
1530 }
1531
1532 /**
1533  * \brief allocate an invalid #snd_ctl_event_t using standard malloc
1534  * \param ptr returned pointer
1535  * \return 0 on success otherwise negative error code
1536  */
1537 int snd_ctl_event_malloc(snd_ctl_event_t **ptr)
1538 {
1539         assert(ptr);
1540         *ptr = calloc(1, sizeof(snd_ctl_event_t));
1541         if (!*ptr)
1542                 return -ENOMEM;
1543         return 0;
1544 }
1545
1546 /**
1547  * \brief frees a previously allocated #snd_ctl_event_t
1548  * \param obj pointer to object to free
1549  */
1550 void snd_ctl_event_free(snd_ctl_event_t *obj)
1551 {
1552         free(obj);
1553 }
1554
1555 /**
1556  * \brief clear given #snd_ctl_event_t object
1557  * \param obj pointer to object to clear
1558  */
1559 void snd_ctl_event_clear(snd_ctl_event_t *obj)
1560 {
1561         memset(obj, 0, sizeof(snd_ctl_event_t));
1562 }
1563
1564 /**
1565  * \brief copy one #snd_ctl_event_t to another
1566  * \param dst pointer to destination
1567  * \param src pointer to source
1568  */
1569 void snd_ctl_event_copy(snd_ctl_event_t *dst, const snd_ctl_event_t *src)
1570 {
1571         assert(dst && src);
1572         *dst = *src;
1573 }
1574
1575 /**
1576  * \brief Get type of a CTL event
1577  * \param obj CTL event
1578  * \return CTL event type
1579  */
1580 snd_ctl_event_type_t snd_ctl_event_get_type(const snd_ctl_event_t *obj)
1581 {
1582         assert(obj);
1583         return obj->type;
1584 }
1585
1586 /**
1587  * \brief get size of #snd_ctl_elem_list_t
1588  * \return size in bytes
1589  */
1590 size_t snd_ctl_elem_list_sizeof()
1591 {
1592         return sizeof(snd_ctl_elem_list_t);
1593 }
1594
1595 /**
1596  * \brief allocate an invalid #snd_ctl_elem_list_t using standard malloc
1597  * \param ptr returned pointer
1598  * \return 0 on success otherwise negative error code
1599  */
1600 int snd_ctl_elem_list_malloc(snd_ctl_elem_list_t **ptr)
1601 {
1602         assert(ptr);
1603         *ptr = calloc(1, sizeof(snd_ctl_elem_list_t));
1604         if (!*ptr)
1605                 return -ENOMEM;
1606         return 0;
1607 }
1608
1609 /**
1610  * \brief frees a previously allocated #snd_ctl_elem_list_t
1611  * \param obj pointer to object to free
1612  */
1613 void snd_ctl_elem_list_free(snd_ctl_elem_list_t *obj)
1614 {
1615         free(obj);
1616 }
1617
1618 /**
1619  * \brief clear given #snd_ctl_elem_list_t object
1620  * \param obj pointer to object to clear
1621  */
1622 void snd_ctl_elem_list_clear(snd_ctl_elem_list_t *obj)
1623 {
1624         memset(obj, 0, sizeof(snd_ctl_elem_list_t));
1625 }
1626
1627 /**
1628  * \brief copy one #snd_ctl_elem_list_t to another
1629  * \param dst pointer to destination
1630  * \param src pointer to source
1631  */
1632 void snd_ctl_elem_list_copy(snd_ctl_elem_list_t *dst, const snd_ctl_elem_list_t *src)
1633 {
1634         assert(dst && src);
1635         *dst = *src;
1636 }
1637
1638 /**
1639  * \brief Set index of first wanted CTL element identifier in a CTL element identifiers list
1640  * \param obj CTL element identifiers list
1641  * \param val index of CTL element to put at position 0 of list
1642  */
1643 void snd_ctl_elem_list_set_offset(snd_ctl_elem_list_t *obj, unsigned int val)
1644 {
1645         assert(obj);
1646         obj->offset = val;
1647 }
1648
1649 /**
1650  * \brief Get number of used entries in CTL element identifiers list
1651  * \param obj CTL element identifier list
1652  * \return number of used entries
1653  */
1654 unsigned int snd_ctl_elem_list_get_used(const snd_ctl_elem_list_t *obj)
1655 {
1656         assert(obj);
1657         return obj->used;
1658 }
1659
1660 /**
1661  * \brief Get total count of elements present in CTL device (information present in every filled CTL element identifiers list)
1662  * \param obj CTL element identifier list
1663  * \return total number of elements
1664  */
1665 unsigned int snd_ctl_elem_list_get_count(const snd_ctl_elem_list_t *obj)
1666 {
1667         assert(obj);
1668         return obj->count;
1669 }
1670
1671 /**
1672  * \brief Get CTL element identifier for an entry of a CTL element identifiers list
1673  * \param obj CTL element identifier list
1674  * \param idx Index of entry
1675  * \param ptr Pointer to returned CTL element identifier
1676  */
1677 void snd_ctl_elem_list_get_id(const snd_ctl_elem_list_t *obj, unsigned int idx, snd_ctl_elem_id_t *ptr)
1678 {
1679         assert(obj && ptr);
1680         assert(idx < obj->used);
1681         *ptr = obj->pids[idx];
1682 }
1683
1684 /**
1685  * \brief Get CTL element numeric identifier for an entry of a CTL element identifiers list
1686  * \param obj CTL element identifier list
1687  * \param idx Index of entry
1688  * \return CTL element numeric identifier
1689  */
1690 unsigned int snd_ctl_elem_list_get_numid(const snd_ctl_elem_list_t *obj, unsigned int idx)
1691 {
1692         assert(obj);
1693         assert(idx < obj->used);
1694         return obj->pids[idx].numid;
1695 }
1696
1697 /**
1698  * \brief Get interface part of CTL element identifier for an entry of a CTL element identifiers list
1699  * \param obj CTL element identifier list
1700  * \param idx Index of entry
1701  * \return CTL element related interface
1702  */
1703 snd_ctl_elem_iface_t snd_ctl_elem_list_get_interface(const snd_ctl_elem_list_t *obj, unsigned int idx)
1704 {
1705         assert(obj);
1706         assert(idx < obj->used);
1707         return obj->pids[idx].iface;
1708 }
1709
1710 /**
1711  * \brief Get device part of CTL element identifier for an entry of a CTL element identifiers list
1712  * \param obj CTL element identifier list
1713  * \param idx Index of entry
1714  * \return CTL element related device
1715  */
1716 unsigned int snd_ctl_elem_list_get_device(const snd_ctl_elem_list_t *obj, unsigned int idx)
1717 {
1718         assert(obj);
1719         assert(idx < obj->used);
1720         return obj->pids[idx].device;
1721 }
1722
1723 /**
1724  * \brief Get subdevice part of CTL element identifier for an entry of a CTL element identifiers list
1725  * \param obj CTL element identifier list
1726  * \param idx Index of entry
1727  * \return CTL element related subdevice
1728  */
1729 unsigned int snd_ctl_elem_list_get_subdevice(const snd_ctl_elem_list_t *obj, unsigned int idx)
1730 {
1731         assert(obj);
1732         assert(idx < obj->used);
1733         return obj->pids[idx].subdevice;
1734 }
1735
1736 /**
1737  * \brief Get name part of CTL element identifier for an entry of a CTL element identifiers list
1738  * \param obj CTL element identifier list
1739  * \param idx Index of entry
1740  * \return CTL element name
1741  */
1742 const char *snd_ctl_elem_list_get_name(const snd_ctl_elem_list_t *obj, unsigned int idx)
1743 {
1744         assert(obj);
1745         assert(idx < obj->used);
1746         return (const char *)obj->pids[idx].name;
1747 }
1748
1749 /**
1750  * \brief Get index part of CTL element identifier for an entry of a CTL element identifiers list
1751  * \param obj CTL element identifier list
1752  * \param idx Index of entry
1753  * \return CTL element index
1754  */
1755 unsigned int snd_ctl_elem_list_get_index(const snd_ctl_elem_list_t *obj, unsigned int idx)
1756 {
1757         assert(obj);
1758         assert(idx < obj->used);
1759         return obj->pids[idx].index;
1760 }
1761
1762 /**
1763  * \brief get size of #snd_ctl_elem_info_t
1764  * \return size in bytes
1765  */
1766 size_t snd_ctl_elem_info_sizeof()
1767 {
1768         return sizeof(snd_ctl_elem_info_t);
1769 }
1770
1771 /**
1772  * \brief allocate an invalid #snd_ctl_elem_info_t using standard malloc
1773  * \param ptr returned pointer
1774  * \return 0 on success otherwise negative error code
1775  */
1776 int snd_ctl_elem_info_malloc(snd_ctl_elem_info_t **ptr)
1777 {
1778         assert(ptr);
1779         *ptr = calloc(1, sizeof(snd_ctl_elem_info_t));
1780         if (!*ptr)
1781                 return -ENOMEM;
1782         return 0;
1783 }
1784
1785 /**
1786  * \brief frees a previously allocated #snd_ctl_elem_info_t
1787  * \param obj pointer to object to free
1788  */
1789 void snd_ctl_elem_info_free(snd_ctl_elem_info_t *obj)
1790 {
1791         free(obj);
1792 }
1793
1794 /**
1795  * \brief clear given #snd_ctl_elem_info_t object
1796  * \param obj pointer to object to clear
1797  */
1798 void snd_ctl_elem_info_clear(snd_ctl_elem_info_t *obj)
1799 {
1800         memset(obj, 0, sizeof(snd_ctl_elem_info_t));
1801 }
1802
1803 /**
1804  * \brief copy one #snd_ctl_elem_info_t to another
1805  * \param dst pointer to destination
1806  * \param src pointer to source
1807  */
1808 void snd_ctl_elem_info_copy(snd_ctl_elem_info_t *dst, const snd_ctl_elem_info_t *src)
1809 {
1810         assert(dst && src);
1811         *dst = *src;
1812 }
1813
1814 /**
1815  * \brief Get type from a CTL element id/info
1816  * \param obj CTL element id/info
1817  * \return CTL element content type
1818  */
1819 snd_ctl_elem_type_t snd_ctl_elem_info_get_type(const snd_ctl_elem_info_t *obj)
1820 {
1821         assert(obj);
1822         return obj->type;
1823 }
1824
1825 /**
1826  * \brief Get info about readability from a CTL element id/info
1827  * \param obj CTL element id/info
1828  * \return 0 if element is not readable, 1 if element is readable
1829  */
1830 int snd_ctl_elem_info_is_readable(const snd_ctl_elem_info_t *obj)
1831 {
1832         assert(obj);
1833         return !!(obj->access & SNDRV_CTL_ELEM_ACCESS_READ);
1834 }
1835
1836 /**
1837  * \brief Get info about writability from a CTL element id/info
1838  * \param obj CTL element id/info
1839  * \return 0 if element is not writable, 1 if element is not writable
1840  */
1841 int snd_ctl_elem_info_is_writable(const snd_ctl_elem_info_t *obj)
1842 {
1843         assert(obj);
1844         return !!(obj->access & SNDRV_CTL_ELEM_ACCESS_WRITE);
1845 }
1846
1847 /**
1848  * \brief Get info about notification feasibility from a CTL element id/info
1849  * \param obj CTL element id/info
1850  * \return 0 if all element value changes are notified to subscribed applications, 1 otherwise
1851  */
1852 int snd_ctl_elem_info_is_volatile(const snd_ctl_elem_info_t *obj)
1853 {
1854         assert(obj);
1855         return !!(obj->access & SNDRV_CTL_ELEM_ACCESS_VOLATILE);
1856 }
1857
1858 /**
1859  * \brief Get info about status from a CTL element id/info
1860  * \param obj CTL element id/info
1861  * \return 0 if element value is not active, 1 if is active
1862  */
1863 int snd_ctl_elem_info_is_inactive(const snd_ctl_elem_info_t *obj)
1864 {
1865         assert(obj);
1866         return !!(obj->access & SNDRV_CTL_ELEM_ACCESS_INACTIVE);
1867 }
1868
1869 /**
1870  * \brief Get info whether an element is locked
1871  * \param obj CTL element id/info
1872  * \return 0 if element value is currently changeable, 1 if it's locked by another application
1873  */
1874 int snd_ctl_elem_info_is_locked(const snd_ctl_elem_info_t *obj)
1875 {
1876         assert(obj);
1877         return !!(obj->access & SNDRV_CTL_ELEM_ACCESS_LOCK);
1878 }
1879
1880 /**
1881  * \brief Get info if I own an element
1882  * \param obj CTL element id/info
1883  * \return 0 if element value is currently changeable, 1 if it's locked by another application
1884  */
1885 int snd_ctl_elem_info_is_owner(const snd_ctl_elem_info_t *obj)
1886 {
1887         assert(obj);
1888         return !!(obj->access & SNDRV_CTL_ELEM_ACCESS_OWNER);
1889 }
1890
1891 /**
1892  * \brief Get info if it's a user element
1893  * \param obj CTL element id/info
1894  * \return 0 if element value is a system element, 1 if it's a user-created element
1895  */
1896 int snd_ctl_elem_info_is_user(const snd_ctl_elem_info_t *obj)
1897 {
1898         assert(obj);
1899         return !!(obj->access & SNDRV_CTL_ELEM_ACCESS_USER);
1900 }
1901
1902 /**
1903  * \brief Get info about TLV readability from a CTL element id/info
1904  * \param obj CTL element id/info
1905  * \return 0 if element's TLV is not readable, 1 if element's TLV is readable
1906  */
1907 int snd_ctl_elem_info_is_tlv_readable(const snd_ctl_elem_info_t *obj)
1908 {
1909         assert(obj);
1910         return !!(obj->access & SNDRV_CTL_ELEM_ACCESS_TLV_READ);
1911 }
1912
1913 /**
1914  * \brief Get info about TLV writeability from a CTL element id/info
1915  * \param obj CTL element id/info
1916  * \return 0 if element's TLV is not writable, 1 if element's TLV is writable
1917  */
1918 int snd_ctl_elem_info_is_tlv_writable(const snd_ctl_elem_info_t *obj)
1919 {
1920         assert(obj);
1921         return !!(obj->access & SNDRV_CTL_ELEM_ACCESS_TLV_WRITE);
1922 }
1923
1924 /**
1925  * \brief Get info about TLV command possibility from a CTL element id/info
1926  * \param obj CTL element id/info
1927  * \return 0 if element's TLV command is not possible, 1 if element's TLV command is supported
1928  */
1929 int snd_ctl_elem_info_is_tlv_commandable(const snd_ctl_elem_info_t *obj)
1930 {
1931         assert(obj);
1932         return !!(obj->access & SNDRV_CTL_ELEM_ACCESS_TLV_COMMAND);
1933 }
1934
1935 /**
1936  * \brief (DEPRECATED) Get info about values passing policy from a CTL element value
1937  * \param obj CTL element id/info
1938  * \return 0 if element value need to be passed by contents, 1 if need to be passed with a pointer
1939  */
1940 int snd_ctl_elem_info_is_indirect(const snd_ctl_elem_info_t *obj)
1941 {
1942         assert(obj);
1943         return 0;
1944 }
1945 link_warning(snd_ctl_elem_info_is_indirect, "Warning: snd_ctl_elem_info_is_indirect is deprecated, do not use it");
1946
1947 /**
1948  * \brief Get owner of a locked element
1949  * \param obj CTL element id/info
1950  * \return value entries count
1951  */
1952 pid_t snd_ctl_elem_info_get_owner(const snd_ctl_elem_info_t *obj)
1953 {
1954         assert(obj);
1955         return obj->owner;
1956 }
1957
1958 /**
1959  * \brief Get number of value entries from a CTL element id/info
1960  * \param obj CTL element id/info
1961  * \return value entries count
1962  */
1963 unsigned int snd_ctl_elem_info_get_count(const snd_ctl_elem_info_t *obj)
1964 {
1965         assert(obj);
1966         return obj->count;
1967 }
1968
1969 /**
1970  * \brief Get minimum value from a #SND_CTL_ELEM_TYPE_INTEGER CTL element id/info
1971  * \param obj CTL element id/info
1972  * \return Minimum value
1973  */
1974 long snd_ctl_elem_info_get_min(const snd_ctl_elem_info_t *obj)
1975 {
1976         assert(obj);
1977         assert(obj->type == SND_CTL_ELEM_TYPE_INTEGER);
1978         return obj->value.integer.min;
1979 }
1980
1981 /**
1982  * \brief Get maximum value from a #SND_CTL_ELEM_TYPE_INTEGER CTL element id/info
1983  * \param obj CTL element id/info
1984  * \return Maximum value
1985  */
1986 long snd_ctl_elem_info_get_max(const snd_ctl_elem_info_t *obj)
1987 {
1988         assert(obj);
1989         assert(obj->type == SND_CTL_ELEM_TYPE_INTEGER);
1990         return obj->value.integer.max;
1991 }
1992
1993 /**
1994  * \brief Get value step from a #SND_CTL_ELEM_TYPE_INTEGER CTL element id/info
1995  * \param obj CTL element id/info
1996  * \return Step
1997  */
1998 long snd_ctl_elem_info_get_step(const snd_ctl_elem_info_t *obj)
1999 {
2000         assert(obj);
2001         assert(obj->type == SND_CTL_ELEM_TYPE_INTEGER);
2002         return obj->value.integer.step;
2003 }
2004
2005 /**
2006  * \brief Get minimum value from a #SND_CTL_ELEM_TYPE_INTEGER64 CTL element id/info
2007  * \param obj CTL element id/info
2008  * \return Minimum value
2009  */
2010 long long snd_ctl_elem_info_get_min64(const snd_ctl_elem_info_t *obj)
2011 {
2012         assert(obj);
2013         assert(obj->type == SND_CTL_ELEM_TYPE_INTEGER64);
2014         return obj->value.integer64.min;
2015 }
2016
2017 /**
2018  * \brief Get maximum value from a #SND_CTL_ELEM_TYPE_INTEGER64 CTL element id/info
2019  * \param obj CTL element id/info
2020  * \return Maximum value
2021  */
2022 long long snd_ctl_elem_info_get_max64(const snd_ctl_elem_info_t *obj)
2023 {
2024         assert(obj);
2025         assert(obj->type == SND_CTL_ELEM_TYPE_INTEGER64);
2026         return obj->value.integer64.max;
2027 }
2028
2029 /**
2030  * \brief Get value step from a #SND_CTL_ELEM_TYPE_INTEGER64 CTL element id/info
2031  * \param obj CTL element id/info
2032  * \return Step
2033  */
2034 long long snd_ctl_elem_info_get_step64(const snd_ctl_elem_info_t *obj)
2035 {
2036         assert(obj);
2037         assert(obj->type == SND_CTL_ELEM_TYPE_INTEGER64);
2038         return obj->value.integer64.step;
2039 }
2040
2041 /**
2042  * \brief Get number of items available from a #SND_CTL_ELEM_TYPE_ENUMERATED CTL element id/info
2043  * \param obj CTL element id/info
2044  * \return items count
2045  */
2046 unsigned int snd_ctl_elem_info_get_items(const snd_ctl_elem_info_t *obj)
2047 {
2048         assert(obj);
2049         assert(obj->type == SND_CTL_ELEM_TYPE_ENUMERATED);
2050         return obj->value.enumerated.items;
2051 }
2052
2053 /**
2054  * \brief Select item in a #SND_CTL_ELEM_TYPE_ENUMERATED CTL element id/info
2055  * \param obj CTL element id/info
2056  * \param val item number
2057  */
2058 void snd_ctl_elem_info_set_item(snd_ctl_elem_info_t *obj, unsigned int val)
2059 {
2060         assert(obj);
2061         obj->value.enumerated.item = val;
2062 }
2063
2064 /**
2065  * \brief Get name for selected item in a #SND_CTL_ELEM_TYPE_ENUMERATED CTL element id/info
2066  * \param obj CTL element id/info
2067  * \return name of chosen item
2068  */
2069 const char *snd_ctl_elem_info_get_item_name(const snd_ctl_elem_info_t *obj)
2070 {
2071         assert(obj);
2072         assert(obj->type == SND_CTL_ELEM_TYPE_ENUMERATED);
2073         return obj->value.enumerated.name;
2074 }
2075
2076 /**
2077  * \brief Get count of dimensions for given element
2078  * \param obj CTL element id/info
2079  * \return zero value if no dimensions are defined, otherwise positive value with count of dimensions
2080  */
2081 #ifndef DOXYGEN
2082 int INTERNAL(snd_ctl_elem_info_get_dimensions)(const snd_ctl_elem_info_t *obj)
2083 #else
2084 int snd_ctl_elem_info_get_dimensions(const snd_ctl_elem_info_t *obj)
2085 #endif
2086 {
2087         int i;
2088
2089         assert(obj);
2090         for (i = 3; i >= 0; i--)
2091                 if (obj->dimen.d[i])
2092                         break;
2093         return i + 1;
2094 }
2095 use_default_symbol_version(__snd_ctl_elem_info_get_dimensions, snd_ctl_elem_info_get_dimensions, ALSA_0.9.3);
2096
2097 /**
2098  * \brief Get specified of dimension width for given element
2099  * \param obj CTL element id/info
2100  * \param idx The dimension index
2101  * \return zero value if no dimension width is defined, otherwise positive value with with of specified dimension
2102  */
2103 #ifndef DOXYGEN
2104 int INTERNAL(snd_ctl_elem_info_get_dimension)(const snd_ctl_elem_info_t *obj, unsigned int idx)
2105 #else
2106 int snd_ctl_elem_info_get_dimension(const snd_ctl_elem_info_t *obj, unsigned int idx)
2107 #endif
2108 {
2109         assert(obj);
2110         if (idx >= 3)
2111                 return 0;
2112         return obj->dimen.d[idx];
2113 }
2114 use_default_symbol_version(__snd_ctl_elem_info_get_dimension, snd_ctl_elem_info_get_dimension, ALSA_0.9.3);
2115
2116 /**
2117  * \brief Get CTL element identifier of a CTL element id/info
2118  * \param obj CTL element id/info
2119  * \param ptr Pointer to returned CTL element identifier
2120  */
2121 void snd_ctl_elem_info_get_id(const snd_ctl_elem_info_t *obj, snd_ctl_elem_id_t *ptr)
2122 {
2123         assert(obj && ptr);
2124         *ptr = obj->id;
2125 }
2126
2127 /**
2128  * \brief Get element numeric identifier of a CTL element id/info
2129  * \param obj CTL element id/info
2130  * \return element numeric identifier
2131  */
2132 unsigned int snd_ctl_elem_info_get_numid(const snd_ctl_elem_info_t *obj)
2133 {
2134         assert(obj);
2135         return obj->id.numid;
2136 }
2137
2138 /**
2139  * \brief Get interface part of CTL element identifier of a CTL element id/info
2140  * \param obj CTL element id/info
2141  * \return interface part of element identifier
2142  */
2143 snd_ctl_elem_iface_t snd_ctl_elem_info_get_interface(const snd_ctl_elem_info_t *obj)
2144 {
2145         assert(obj);
2146         return obj->id.iface;
2147 }
2148
2149 /**
2150  * \brief Get device part of CTL element identifier of a CTL element id/info
2151  * \param obj CTL element id/info
2152  * \return device part of element identifier
2153  */
2154 unsigned int snd_ctl_elem_info_get_device(const snd_ctl_elem_info_t *obj)
2155 {
2156         assert(obj);
2157         return obj->id.device;
2158 }
2159
2160 /**
2161  * \brief Get subdevice part of CTL element identifier of a CTL element id/info
2162  * \param obj CTL element id/info
2163  * \return subdevice part of element identifier
2164  */
2165 unsigned int snd_ctl_elem_info_get_subdevice(const snd_ctl_elem_info_t *obj)
2166 {
2167         assert(obj);
2168         return obj->id.subdevice;
2169 }
2170
2171 /**
2172  * \brief Get name part of CTL element identifier of a CTL element id/info
2173  * \param obj CTL element id/info
2174  * \return name part of element identifier
2175  */
2176 const char *snd_ctl_elem_info_get_name(const snd_ctl_elem_info_t *obj)
2177 {
2178         assert(obj);
2179         return (const char *)obj->id.name;
2180 }
2181
2182 /**
2183  * \brief Get index part of CTL element identifier of a CTL element id/info
2184  * \param obj CTL element id/info
2185  * \return index part of element identifier
2186  */
2187 unsigned int snd_ctl_elem_info_get_index(const snd_ctl_elem_info_t *obj)
2188 {
2189         assert(obj);
2190         return obj->id.index;
2191 }
2192
2193 /**
2194  * \brief Set CTL element identifier of a CTL element id/info
2195  * \param obj CTL element id/info
2196  * \param ptr CTL element identifier
2197  */
2198 void snd_ctl_elem_info_set_id(snd_ctl_elem_info_t *obj, const snd_ctl_elem_id_t *ptr)
2199 {
2200         assert(obj && ptr);
2201         obj->id = *ptr;
2202 }
2203
2204 /**
2205  * \brief Set element numeric identifier of a CTL element id/info
2206  * \param obj CTL element id/info
2207  * \param val element numeric identifier
2208  */
2209 void snd_ctl_elem_info_set_numid(snd_ctl_elem_info_t *obj, unsigned int val)
2210 {
2211         assert(obj);
2212         obj->id.numid = val;
2213 }
2214
2215 /**
2216  * \brief Set interface part of CTL element identifier of a CTL element id/info
2217  * \param obj CTL element id/info
2218  * \param val interface part of element identifier
2219  */
2220 void snd_ctl_elem_info_set_interface(snd_ctl_elem_info_t *obj, snd_ctl_elem_iface_t val)
2221 {
2222         assert(obj);
2223         obj->id.iface = val;
2224 }
2225
2226 /**
2227  * \brief Set device part of CTL element identifier of a CTL element id/info
2228  * \param obj CTL element id/info
2229  * \param val device part of element identifier
2230  */
2231 void snd_ctl_elem_info_set_device(snd_ctl_elem_info_t *obj, unsigned int val)
2232 {
2233         assert(obj);
2234         obj->id.device = val;
2235 }
2236
2237 /**
2238  * \brief Set subdevice part of CTL element identifier of a CTL element id/info
2239  * \param obj CTL element id/info
2240  * \param val subdevice part of element identifier
2241  */
2242 void snd_ctl_elem_info_set_subdevice(snd_ctl_elem_info_t *obj, unsigned int val)
2243 {
2244         assert(obj);
2245         obj->id.subdevice = val;
2246 }
2247
2248 /**
2249  * \brief Set name part of CTL element identifier of a CTL element id/info
2250  * \param obj CTL element id/info
2251  * \param val name part of element identifier
2252  */
2253 void snd_ctl_elem_info_set_name(snd_ctl_elem_info_t *obj, const char *val)
2254 {
2255         assert(obj);
2256         strncpy((char *)obj->id.name, val, sizeof(obj->id.name));
2257 }
2258
2259 /**
2260  * \brief Set index part of CTL element identifier of a CTL element id/info
2261  * \param obj CTL element id/info
2262  * \param val index part of element identifier
2263  */
2264 void snd_ctl_elem_info_set_index(snd_ctl_elem_info_t *obj, unsigned int val)
2265 {
2266         assert(obj);
2267         obj->id.index = val;
2268 }
2269
2270 /**
2271  * \brief get size of #snd_ctl_elem_value_t
2272  * \return size in bytes
2273  */
2274 size_t snd_ctl_elem_value_sizeof()
2275 {
2276         return sizeof(snd_ctl_elem_value_t);
2277 }
2278
2279 /**
2280  * \brief allocate an invalid #snd_ctl_elem_value_t using standard malloc
2281  * \param ptr returned pointer
2282  * \return 0 on success otherwise negative error code
2283  */
2284 int snd_ctl_elem_value_malloc(snd_ctl_elem_value_t **ptr)
2285 {
2286         assert(ptr);
2287         *ptr = calloc(1, sizeof(snd_ctl_elem_value_t));
2288         if (!*ptr)
2289                 return -ENOMEM;
2290         return 0;
2291 }
2292
2293 /**
2294  * \brief frees a previously allocated #snd_ctl_elem_value_t
2295  * \param obj pointer to object to free
2296  */
2297 void snd_ctl_elem_value_free(snd_ctl_elem_value_t *obj)
2298 {
2299         free(obj);
2300 }
2301
2302 /**
2303  * \brief clear given #snd_ctl_elem_value_t object
2304  * \param obj pointer to object to clear
2305  */
2306 void snd_ctl_elem_value_clear(snd_ctl_elem_value_t *obj)
2307 {
2308         memset(obj, 0, sizeof(snd_ctl_elem_value_t));
2309 }
2310
2311 /**
2312  * \brief copy one #snd_ctl_elem_value_t to another
2313  * \param dst pointer to destination
2314  * \param src pointer to source
2315  */
2316 void snd_ctl_elem_value_copy(snd_ctl_elem_value_t *dst, const snd_ctl_elem_value_t *src)
2317 {
2318         assert(dst && src);
2319         *dst = *src;
2320 }
2321
2322 /**
2323  * \brief compare one #snd_ctl_elem_value_t to another
2324  * \param dst pointer to destination
2325  * \param src pointer to source
2326  * \return 0 on match, less than or greater than otherwise, see memcmp
2327  */
2328 int snd_ctl_elem_value_compare(snd_ctl_elem_value_t *left, const snd_ctl_elem_value_t *right)
2329 {
2330         assert(left && right);
2331         return memcmp(left, right, sizeof(*left));
2332 }
2333
2334 /**
2335  * \brief Get CTL element identifier of a CTL element id/value
2336  * \param obj CTL element id/value
2337  * \param ptr Pointer to returned CTL element identifier
2338  */
2339 void snd_ctl_elem_value_get_id(const snd_ctl_elem_value_t *obj, snd_ctl_elem_id_t *ptr)
2340 {
2341         assert(obj && ptr);
2342         *ptr = obj->id;
2343 }
2344
2345 /**
2346  * \brief Get element numeric identifier of a CTL element id/value
2347  * \param obj CTL element id/value
2348  * \return element numeric identifier
2349  */
2350 unsigned int snd_ctl_elem_value_get_numid(const snd_ctl_elem_value_t *obj)
2351 {
2352         assert(obj);
2353         return obj->id.numid;
2354 }
2355
2356 /**
2357  * \brief Get interface part of CTL element identifier of a CTL element id/value
2358  * \param obj CTL element id/value
2359  * \return interface part of element identifier
2360  */
2361 snd_ctl_elem_iface_t snd_ctl_elem_value_get_interface(const snd_ctl_elem_value_t *obj)
2362 {
2363         assert(obj);
2364         return obj->id.iface;
2365 }
2366
2367 /**
2368  * \brief Get device part of CTL element identifier of a CTL element id/value
2369  * \param obj CTL element id/value
2370  * \return device part of element identifier
2371  */
2372 unsigned int snd_ctl_elem_value_get_device(const snd_ctl_elem_value_t *obj)
2373 {
2374         assert(obj);
2375         return obj->id.device;
2376 }
2377
2378 /**
2379  * \brief Get subdevice part of CTL element identifier of a CTL element id/value
2380  * \param obj CTL element id/value
2381  * \return subdevice part of element identifier
2382  */
2383 unsigned int snd_ctl_elem_value_get_subdevice(const snd_ctl_elem_value_t *obj)
2384 {
2385         assert(obj);
2386         return obj->id.subdevice;
2387 }
2388
2389 /**
2390  * \brief Get name part of CTL element identifier of a CTL element id/value
2391  * \param obj CTL element id/value
2392  * \return name part of element identifier
2393  */
2394 const char *snd_ctl_elem_value_get_name(const snd_ctl_elem_value_t *obj)
2395 {
2396         assert(obj);
2397         return (const char *)obj->id.name;
2398 }
2399
2400 /**
2401  * \brief Get index part of CTL element identifier of a CTL element id/value
2402  * \param obj CTL element id/value
2403  * \return index part of element identifier
2404  */
2405 unsigned int snd_ctl_elem_value_get_index(const snd_ctl_elem_value_t *obj)
2406 {
2407         assert(obj);
2408         return obj->id.index;
2409 }
2410
2411 /**
2412  * \brief Set CTL element identifier of a CTL element id/value
2413  * \param obj CTL element id/value
2414  * \param ptr CTL element identifier
2415  */
2416 void snd_ctl_elem_value_set_id(snd_ctl_elem_value_t *obj, const snd_ctl_elem_id_t *ptr)
2417 {
2418         assert(obj && ptr);
2419         obj->id = *ptr;
2420 }
2421
2422 /**
2423  * \brief Set element numeric identifier of a CTL element id/value
2424  * \param obj CTL element id/value
2425  * \param val element numeric identifier
2426  */
2427 void snd_ctl_elem_value_set_numid(snd_ctl_elem_value_t *obj, unsigned int val)
2428 {
2429         assert(obj);
2430         obj->id.numid = val;
2431 }
2432
2433 /**
2434  * \brief Set interface part of CTL element identifier of a CTL element id/value
2435  * \param obj CTL element id/value
2436  * \param val interface part of element identifier
2437  */
2438 void snd_ctl_elem_value_set_interface(snd_ctl_elem_value_t *obj, snd_ctl_elem_iface_t val)
2439 {
2440         assert(obj);
2441         obj->id.iface = val;
2442 }
2443
2444 /**
2445  * \brief Set device part of CTL element identifier of a CTL element id/value
2446  * \param obj CTL element id/value
2447  * \param val device part of element identifier
2448  */
2449 void snd_ctl_elem_value_set_device(snd_ctl_elem_value_t *obj, unsigned int val)
2450 {
2451         assert(obj);
2452         obj->id.device = val;
2453 }
2454
2455 /**
2456  * \brief Set subdevice part of CTL element identifier of a CTL element id/value
2457  * \param obj CTL element id/value
2458  * \param val subdevice part of element identifier
2459  */
2460 void snd_ctl_elem_value_set_subdevice(snd_ctl_elem_value_t *obj, unsigned int val)
2461 {
2462         assert(obj);
2463         obj->id.subdevice = val;
2464 }
2465
2466 /**
2467  * \brief Set name part of CTL element identifier of a CTL element id/value
2468  * \param obj CTL element id/value
2469  * \param val name part of element identifier
2470  */
2471 void snd_ctl_elem_value_set_name(snd_ctl_elem_value_t *obj, const char *val)
2472 {
2473         assert(obj);
2474         strncpy((char *)obj->id.name, val, sizeof(obj->id.name));
2475 }
2476
2477 /**
2478  * \brief Set index part of CTL element identifier of a CTL element id/value
2479  * \param obj CTL element id/value
2480  * \param val index part of element identifier
2481  */
2482 void snd_ctl_elem_value_set_index(snd_ctl_elem_value_t *obj, unsigned int val)
2483 {
2484         assert(obj);
2485         obj->id.index = val;
2486 }
2487
2488 /**
2489  * \brief Get value for an entry of a #SND_CTL_ELEM_TYPE_BOOLEAN CTL element id/value 
2490  * \param obj CTL element id/value
2491  * \param idx Entry index
2492  * \return value for the entry
2493  */ 
2494 int snd_ctl_elem_value_get_boolean(const snd_ctl_elem_value_t *obj, unsigned int idx)
2495 {
2496         assert(obj);
2497         assert(idx < sizeof(obj->value.integer.value) / sizeof(obj->value.integer.value[0]));
2498         return obj->value.integer.value[idx];
2499 }
2500
2501 /**
2502  * \brief Get value for an entry of a #SND_CTL_ELEM_TYPE_INTEGER CTL element id/value 
2503  * \param obj CTL element id/value
2504  * \param idx Entry index
2505  * \return value for the entry
2506  */ 
2507 long snd_ctl_elem_value_get_integer(const snd_ctl_elem_value_t *obj, unsigned int idx)
2508 {
2509         assert(obj);
2510         assert(idx < sizeof(obj->value.integer.value) / sizeof(obj->value.integer.value[0]));
2511         return obj->value.integer.value[idx];
2512 }
2513
2514 /**
2515  * \brief Get value for an entry of a #SND_CTL_ELEM_TYPE_INTEGER64 CTL element id/value 
2516  * \param obj CTL element id/value
2517  * \param idx Entry index
2518  * \return value for the entry
2519  */ 
2520 long long snd_ctl_elem_value_get_integer64(const snd_ctl_elem_value_t *obj, unsigned int idx)
2521 {
2522         assert(obj);
2523         assert(idx < sizeof(obj->value.integer64.value) / sizeof(obj->value.integer64.value[0]));
2524         return obj->value.integer64.value[idx];
2525 }
2526
2527 /**
2528  * \brief Get value for an entry of a #SND_CTL_ELEM_TYPE_ENUMERATED CTL element id/value 
2529  * \param obj CTL element id/value
2530  * \param idx Entry index
2531  * \return value for the entry
2532  */ 
2533 unsigned int snd_ctl_elem_value_get_enumerated(const snd_ctl_elem_value_t *obj, unsigned int idx)
2534 {
2535         assert(obj);
2536         assert(idx < sizeof(obj->value.enumerated.item) / sizeof(obj->value.enumerated.item[0]));
2537         return obj->value.enumerated.item[idx];
2538 }
2539
2540 /**
2541  * \brief Get value for an entry of a #SND_CTL_ELEM_TYPE_BYTES CTL element id/value 
2542  * \param obj CTL element id/value
2543  * \param idx Entry index
2544  * \return value for the entry
2545  */ 
2546 unsigned char snd_ctl_elem_value_get_byte(const snd_ctl_elem_value_t *obj, unsigned int idx)
2547 {
2548         assert(obj);
2549         assert(idx < sizeof(obj->value.bytes.data));
2550         return obj->value.bytes.data[idx];
2551 }
2552
2553 /**
2554  * \brief Set value for an entry of a #SND_CTL_ELEM_TYPE_BOOLEAN CTL element id/value 
2555  * \param obj CTL element id/value
2556  * \param idx Entry index
2557  * \param val value for the entry
2558  */ 
2559 void snd_ctl_elem_value_set_boolean(snd_ctl_elem_value_t *obj, unsigned int idx, long val)
2560 {
2561         assert(obj);
2562         obj->value.integer.value[idx] = val;
2563 }
2564
2565 /**
2566  * \brief Set value for an entry of a #SND_CTL_ELEM_TYPE_INTEGER CTL element id/value 
2567  * \param obj CTL element id/value
2568  * \param idx Entry index
2569  * \param val value for the entry
2570  */ 
2571 void snd_ctl_elem_value_set_integer(snd_ctl_elem_value_t *obj, unsigned int idx, long val)
2572 {
2573         assert(obj);
2574         obj->value.integer.value[idx] = val;
2575 }
2576
2577 /**
2578  * \brief Set value for an entry of a #SND_CTL_ELEM_TYPE_INTEGER64 CTL element id/value 
2579  * \param obj CTL element id/value
2580  * \param idx Entry index
2581  * \param val value for the entry
2582  */ 
2583 void snd_ctl_elem_value_set_integer64(snd_ctl_elem_value_t *obj, unsigned int idx, long long val)
2584 {
2585         assert(obj);
2586         obj->value.integer64.value[idx] = val;
2587 }
2588
2589 /**
2590  * \brief Set value for an entry of a #SND_CTL_ELEM_TYPE_ENUMERATED CTL element id/value 
2591  * \param obj CTL element id/value
2592  * \param idx Entry index
2593  * \param val value for the entry
2594  */ 
2595 void snd_ctl_elem_value_set_enumerated(snd_ctl_elem_value_t *obj, unsigned int idx, unsigned int val)
2596 {
2597         assert(obj);
2598         obj->value.enumerated.item[idx] = val;
2599 }
2600
2601 /**
2602  * \brief Set value for an entry of a #SND_CTL_ELEM_TYPE_BYTES CTL element id/value 
2603  * \param obj CTL element id/value
2604  * \param idx Entry index
2605  * \param val value for the entry
2606  */ 
2607 void snd_ctl_elem_value_set_byte(snd_ctl_elem_value_t *obj, unsigned int idx, unsigned char val)
2608 {
2609         assert(obj);
2610         obj->value.bytes.data[idx] = val;
2611 }
2612
2613 /**
2614  * \brief Set CTL element #SND_CTL_ELEM_TYPE_BYTES value
2615  * \param obj CTL handle
2616  * \param data Bytes value
2617  * \param size Size in bytes
2618  */
2619 void snd_ctl_elem_set_bytes(snd_ctl_elem_value_t *obj, void *data, size_t size)
2620 {
2621         assert(obj);
2622         if (size >= sizeof(obj->value.bytes.data)) {
2623                 assert(0);
2624                 return;
2625         }
2626         memcpy(obj->value.bytes.data, data, size);
2627 }
2628
2629 /**
2630  * \brief Get value for a #SND_CTL_ELEM_TYPE_BYTES CTL element id/value 
2631  * \param obj CTL element id/value
2632  * \return Pointer to CTL element value
2633  */ 
2634 const void * snd_ctl_elem_value_get_bytes(const snd_ctl_elem_value_t *obj)
2635 {
2636         assert(obj);
2637         return obj->value.bytes.data;
2638 }
2639
2640 /**
2641  * \brief Get value for a #SND_CTL_ELEM_TYPE_IEC958 CTL element id/value 
2642  * \param obj CTL element id/value
2643  * \param ptr Pointer to returned CTL element value
2644  */ 
2645 void snd_ctl_elem_value_get_iec958(const snd_ctl_elem_value_t *obj, snd_aes_iec958_t *ptr)
2646 {
2647         assert(obj && ptr);
2648         memcpy(ptr, &obj->value.iec958, sizeof(*ptr));
2649 }
2650
2651 /**
2652  * \brief Set value for a #SND_CTL_ELEM_TYPE_IEC958 CTL element id/value 
2653  * \param obj CTL element id/value
2654  * \param ptr Pointer to CTL element value
2655  */ 
2656 void snd_ctl_elem_value_set_iec958(snd_ctl_elem_value_t *obj, const snd_aes_iec958_t *ptr)
2657 {
2658         assert(obj && ptr);
2659         memcpy(&obj->value.iec958, ptr, sizeof(obj->value.iec958));
2660 }
2661