source: mainline/uspace/app/mixerctl/mixerctl.c

Last change on this file was 09ab0a9a, checked in by Jiri Svoboda <jiri@…>, 7 years ago

Fix vertical spacing with new Ccheck revision.

  • Property mode set to 100644
File size: 5.0 KB
Line 
1/*
2 * Copyright (c) 2011 Jan Vesely
3 * All rights reserved.
4 *
5 * Redistribution and use in source and binary forms, with or without
6 * modification, are permitted provided that the following conditions
7 * are met:
8 *
9 * - Redistributions of source code must retain the above copyright
10 * notice, this list of conditions and the following disclaimer.
11 * - Redistributions in binary form must reproduce the above copyright
12 * notice, this list of conditions and the following disclaimer in the
13 * documentation and/or other materials provided with the distribution.
14 * - The name of the author may not be used to endorse or promote products
15 * derived from this software without specific prior written permission.
16 *
17 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
18 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
19 * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
20 * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
21 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
22 * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
23 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
24 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
25 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
26 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
27 */
28
29/** @addtogroup mixerctl
30 * @{
31 */
32/** @file Mixer control for audio devices
33 */
34
35#include <assert.h>
36#include <errno.h>
37#include <loc.h>
38#include <str_error.h>
39#include <str.h>
40#include <audio_mixer_iface.h>
41#include <stdio.h>
42
43#define DEFAULT_SERVICE "devices/\\hw\\pci0\\00:01.0\\sb16\\control"
44
45/**
46 * Print volume levels on all channels on all control items.
47 * @param exch IPC exchange
48 */
49static void print_levels(async_exch_t *exch)
50{
51 char *name = NULL;
52 unsigned count = 0;
53 errno_t ret = audio_mixer_get_info(exch, &name, &count);
54 if (ret != EOK) {
55 printf("Failed to get mixer info: %s.\n", str_error(ret));
56 return;
57 }
58 printf("MIXER %s:\n\n", name);
59
60 for (unsigned i = 0; i < count; ++i) {
61 char *name = NULL;
62 unsigned levels = 0, current = 0;
63 errno_t ret =
64 audio_mixer_get_item_info(exch, i, &name, &levels);
65 if (ret != EOK) {
66 printf("Failed to get item %u info: %s.\n",
67 i, str_error(ret));
68 continue;
69 }
70 ret = audio_mixer_get_item_level(exch, i, &current);
71 if (ret != EOK) {
72 printf("Failed to get item %u info: %s.\n",
73 i, str_error(ret));
74 continue;
75 }
76
77 printf("Control item %u `%s' : %u/%u.\n",
78 i, name, current, levels - 1);
79 free(name);
80
81 }
82}
83
84static unsigned get_number(const char *str)
85{
86 uint16_t num;
87 str_uint16_t(str, NULL, 10, false, &num);
88 return num;
89}
90
91static void set_level(async_exch_t *exch, int argc, char *argv[])
92{
93 assert(exch);
94 if (argc != 4 && argc != 5) {
95 printf("%s [device] setlevel item value\n", argv[0]);
96 return;
97 }
98 unsigned params = argc == 5 ? 3 : 2;
99 const unsigned item = get_number(argv[params++]);
100 const unsigned value = get_number(argv[params]);
101 errno_t ret = audio_mixer_set_item_level(exch, item, value);
102 if (ret != EOK) {
103 printf("Failed to set item level: %s.\n", str_error(ret));
104 return;
105 }
106 printf("Control item %u new level is %u.\n", item, value);
107}
108
109static void get_level(async_exch_t *exch, int argc, char *argv[])
110{
111 assert(exch);
112 if (argc != 3 && argc != 4) {
113 printf("%s [device] getlevel item \n", argv[0]);
114 return;
115 }
116 unsigned params = argc == 4 ? 3 : 2;
117 const unsigned item = get_number(argv[params++]);
118 unsigned value = 0;
119
120 errno_t ret = audio_mixer_get_item_level(exch, item, &value);
121 if (ret != EOK) {
122 printf("Failed to get item level: %s.\n", str_error(ret));
123 return;
124 }
125 printf("Control item %u level: %u.\n", item, value);
126}
127
128int main(int argc, char *argv[])
129{
130 const char *service = DEFAULT_SERVICE;
131 void (*command)(async_exch_t *, int, char *[]) = NULL;
132
133 if (argc >= 2 && str_cmp(argv[1], "setlevel") == 0) {
134 command = set_level;
135 if (argc == 5)
136 service = argv[1];
137 }
138
139 if (argc >= 2 && str_cmp(argv[1], "getlevel") == 0) {
140 command = get_level;
141 if (argc == 4)
142 service = argv[1];
143 }
144
145 if ((argc == 2 && command == NULL))
146 service = argv[1];
147
148 service_id_t mixer_sid;
149 errno_t rc = loc_service_get_id(service, &mixer_sid, 0);
150 if (rc != EOK) {
151 printf("Failed to resolve service '%s': %s.\n",
152 service, str_error(rc));
153 return 1;
154 }
155
156 async_sess_t *session = loc_service_connect(mixer_sid, INTERFACE_DDF, 0);
157 if (!session) {
158 printf("Failed connecting mixer service '%s'.\n", service);
159 return 1;
160 }
161
162 async_exch_t *exch = async_exchange_begin(session);
163 if (!exch) {
164 printf("Failed to start session exchange.\n");
165 async_hangup(session);
166 return 1;
167 }
168
169 if (command) {
170 command(exch, argc, argv);
171 } else {
172 print_levels(exch);
173 printf("\n%s:\n", argv[0]);
174 printf("Use '%s getlevel idx' command to read individual "
175 "settings\n", argv[0]);
176 printf("Use '%s setlevel idx' command to change "
177 "settings\n", argv[0]);
178 }
179
180 async_exchange_end(exch);
181 async_hangup(session);
182 return 0;
183}
184
185/** @}
186 */
Note: See TracBrowser for help on using the repository browser.