2 * Copyright (c) 2016 Samsung Electronics Co., Ltd All Rights Reserved
4 * Licensed under the Apache License, Version 2.0 (the License);
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
8 * http://www.apache.org/licenses/LICENSE-2.0
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an AS IS BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
25 #define DEFAULT_MAX_STREAMS_PER_POOL_CNT 25U
26 #define DEFAULT_STREAM_PRIORITY_RANK 255U
27 #define MICROSECS_PER_MILLISEC 1000
29 #define MAX_POOL_CNT 100
30 static sound_pool_h pools[MAX_POOL_CNT] = { NULL };
32 /* Messages to be used for callbacks output (for pool state changing) */
33 static char *messages[MAX_POOL_CNT] = { NULL };
34 /* Scripts will be launched from callbacks (for stream state changing) */
35 static char *scripts[MAX_POOL_CNT] = { NULL };
37 #define MAX_STREAM_CNT 1000
39 static const char *__stringify_sound_pool_error(sound_pool_error_e error);
40 static int __proxy_sound_pool_execute_script(const char *pars);
42 static const char *__stringify_sound_pool_error(sound_pool_error_e error)
45 case SOUND_POOL_ERROR_NONE:
46 return "SOUND_POOL_ERROR_NONE";
48 case SOUND_POOL_ERROR_KEY_NOT_AVAILABLE:
49 return "SOUND_POOL_ERROR_KEY_NOT_AVAILABLE";
51 case SOUND_POOL_ERROR_OUT_OF_MEMORY:
52 return "SOUND_POOL_ERROR_OUT_OF_MEMORY";
54 case SOUND_POOL_ERROR_INVALID_PARAMETER:
55 return "SOUND_POOL_ERROR_INVALID_PARAMETER";
57 case SOUND_POOL_ERROR_INVALID_OPERATION:
58 return "SOUND_POOL_ERROR_INVALID_OPERATION";
60 case SOUND_POOL_ERROR_NOT_PERMITTED:
61 return "SOUND_POOL_ERROR_NOT_PERMITTED";
63 case SOUND_POOL_ERROR_NO_SUCH_FILE:
64 return "SOUND_POOL_ERROR_NO_SUCH_FILE";
74 const char *__stringify_stream_state(sound_pool_stream_state_e state)
77 case SOUND_POOL_STREAM_STATE_NONE:
78 return "SOUND_POOL_STREAM_STATE_NONE";
80 case SOUND_POOL_STREAM_STATE_PLAYING:
81 return "SOUND_POOL_STREAM_STATE_PLAYING";
83 case SOUND_POOL_STREAM_STATE_PAUSED:
84 return "SOUND_POOL_STREAM_STATE_PAUSED";
86 case SOUND_POOL_STREAM_STATE_SUSPENDED:
87 return "SOUND_POOL_STREAM_STATE_SUSPENDED";
89 case SOUND_POOL_STREAM_STATE_STOPPED:
90 return "SOUND_POOL_STREAM_STATE_STOPPED";
92 case SOUND_POOL_STREAM_STATE_FINISHED:
93 return "SOUND_POOL_STREAM_STATE_FINISHED";
103 static void __sp_cb_msg(sound_pool_h pool, sound_pool_state_e prev_state,
104 sound_pool_state_e cur_state, void *data)
106 const char *msg = (const char *)data;
107 _logger_log_info("Sound pool state was changing from %s to %s: %s",
108 prev_state == SOUND_POOL_STATE_ACTIVE ?
109 "SOUND_POOL_STATE_ACTIVE" : "SOUND_POOL_STATE_INACTIVE",
110 cur_state == SOUND_POOL_STATE_ACTIVE ?
111 "SOUND_POOL_STATE_ACTIVE" : "SOUND_POOL_STATE_INACTIVE",
112 msg ? msg : "No message");
115 static void __sp_cb_scr(sound_pool_h pool, sound_pool_state_e prev_state,
116 sound_pool_state_e cur_state, void *data)
118 const char *scr = (const char *)data;
119 _logger_log_info("Sound pool state was changing from %s to %s; "
121 prev_state == SOUND_POOL_STATE_ACTIVE ? "SOUND_POOL_STATE_ACTIVE" :
122 "SOUND_POOL_STATE_INACTIVE",
123 cur_state == SOUND_POOL_STATE_ACTIVE ? "SOUND_POOL_STATE_ACTIVE" :
124 "SOUND_POOL_STATE_INACTIVE",
125 scr ? scr : "No script");
126 __proxy_sound_pool_execute_script(scr);
129 static void __s_cb_msg(sound_pool_h pool, unsigned id,
130 sound_pool_stream_state_e prev_state,
131 sound_pool_stream_state_e cur_state, void *data)
133 const char *msg = (const char *)data;
134 _logger_log_info("Stream state was changing from %s to %s: %s",
135 __stringify_stream_state(prev_state),
136 __stringify_stream_state(cur_state),
137 msg ? msg : "No message");
147 static int __print_cmd_help_msg()
149 printf("\nTest suite usage help:\n");
151 printf(CMD_HELP "\n");
152 printf("\t- Shows this help.\n");
154 printf(CMD_CREATE_POOL "\n");
155 printf("\t- creates pool with specific identifier.\n");
157 printf(CMD_DESTROY_POOL "\n");
158 printf("\t- destroys pool with specific identifier.\n");
160 printf(CMD_ACTIVATE_POOL "\n");
161 printf("\t- activates pool with specific identifier.\n");
163 printf(CMD_DEACTIVATE_POOL "\n");
164 printf("\t- deactivates pool with specific identifier.\n");
166 printf(CMD_GET_POOL_STATE "\n");
167 printf("\t- shows state of the pool with specific identifier.\n");
169 printf(CMD_SET_POOL_VOLUME "\n");
170 printf("\t- use this command to set volume for the specific sound pool.\n");
172 printf(CMD_GET_POOL_VOLUME "\n");
173 printf("\t- shows volume of the sound pool with specific identifier.\n");
175 printf(CMD_SET_POOL_CB_MSG "\n");
176 printf("\t- sets callback which will show the message when sound pool "
177 "state is changed.\n");
179 printf(CMD_UNSET_POOL_CB "\n");
180 printf("\t- unsets the callback for the sound pool.\n");
182 printf(CMD_LIST_POOL "\n");
183 printf("\t- shows ids of all pools had been created and their states.\n");
185 printf(CMD_LOAD_SOURCE "\n");
186 printf("\t- loads the source with specific source tag.\n");
188 printf(CMD_UNLOAD_SOURCE "\n");
189 printf("\t- unloads the source with specific source tag.\n");
191 printf(CMD_PLAY_STREAM "\n");
192 printf("\t- creates the stream with unique identifier and starts playback.\n"
193 "\t Source tag to be used for stream creation should be specified.\n");
195 printf(CMD_STOP_STREAM "\n");
196 printf("\t- stops the stream playback. Stream unique identifier should be\n"
197 "\t specified after command. After stopping the stream became invalid.\n");
199 printf(CMD_PAUSE_STREAM "\n");
200 printf("\t- pauses the stream playback. Stream unique identifier should be\n"
201 "\t specified after command.\n");
203 printf(CMD_RESUME_STREAM "\n");
204 printf("\t- resumes the stream was paused before. Stream unique identifier\n"
205 "\t should be specified after command.\n");
207 printf(CMD_SET_STREAM_VOLUME "\n");
208 printf("\t- use this command to set volume parameter of the stream.\n");
210 printf(CMD_GET_STREAM_VOLUME "\n");
211 printf("\t- shows volume of the stream in the pool with specified "
214 printf(CMD_SET_STREAM_PRIORITY "\n");
215 printf("\t- use this command to set priority parameter of the stream. "
216 "0 is the lowest priority.\n");
218 printf(CMD_GET_STREAM_PRIORITY "\n");
219 printf("\t- shows priority rank of the stream in the pool with specified "
220 "identifiers. 0 is the lowest priority.\n");
222 printf(CMD_GET_STREAM_STATE "\n");
223 printf("\t- shows state of the stream in the pool with specified "
226 printf(CMD_EXECUTE_SCRIPT "\n");
227 printf("\t- executes the script from the file in filesystem. Script has to\n"
228 "\t be compiled with commands supported by testsuite, one command\n"
229 "\t per single line.\n");
231 printf(CMD_SLEEP "\n");
232 printf("\t- suspends execution of the main thread for the specific amount "
233 "of milleseconds.\n");
235 printf(CMD_EXIT "\n");
236 printf("\t- exits from the test suite.\n");
243 /* CMD_CREATE_POOL */
244 static int __proxy_sound_pool_create()
246 _logger_log_info(CMD_CREATE_POOL " command was called");
247 _logger_log_info("Creating the pool...");
249 sound_pool_h pool = NULL;
250 int ret = sound_pool_create(&pool);
252 if (ret == SOUND_POOL_ERROR_NONE) {
253 _logger_log_info("sound_pool_create(pool) returned %s value",
254 __stringify_sound_pool_error(ret));
257 while (idx < MAX_POOL_CNT) {
258 if (pools[idx++] == NULL) {
264 if (idx == MAX_POOL_CNT) {
265 _printf(CMD_COLOR_RED, "Limit of possible pools is exceeded. Destroy "
266 "some pools before creating of new ones.\n");
268 _logger_log_warn("Pool can't be created due to test suite "
269 "restrictions. Destroying the pool...");
271 ret = sound_pool_destroy(pool);
273 PRINT_INFO_OR_ERROR_INFO(ret == SOUND_POOL_ERROR_NONE,
274 "sound_pool_destroy(pool) returned %s value",
275 __stringify_sound_pool_error(ret));
277 return (ret == SOUND_POOL_ERROR_NONE ? OK : FAIL);
281 _logger_log_warn("Created pool is NULL");
283 _logger_log_info("Identifier of the pool has been created is %zu", idx);
285 _logger_log_err("sound_pool_create(pool) returned %s value",
286 __stringify_sound_pool_error(ret));
289 return (ret == SOUND_POOL_ERROR_NONE ? OK : FAIL);
292 /* CMD_DESTROY_POOL */
293 static int __proxy_sound_pool_destroy(const char *pars)
295 int ret = SOUND_POOL_ERROR_NONE;
297 if ((pars == NULL) || (sscanf(pars, " %zu", &idx) < 1)) {
298 _printf(CMD_COLOR_RED, "You have to specify identifier of the pool to be "
299 "destroyed after command! Format: " CMD_DESTROY_POOL " <id>\n");
303 if (idx > (MAX_POOL_CNT - 1)) {
304 _printf(CMD_COLOR_RED, "Pool identifier value can't be greater than %d\n",
309 _logger_log_info(CMD_DESTROY_POOL " command was called");
310 _logger_log_info("Destroying the pool by %zu identifier...", idx);
312 if (pools[idx] == NULL)
313 _logger_log_warn("Pool to be destroyed is NULL");
315 ret = sound_pool_destroy(pools[idx]);
317 PRINT_INFO_OR_ERROR_INFO(ret == SOUND_POOL_ERROR_NONE,
318 "sound_pool_destroy(pool) returned %s value",
319 __stringify_sound_pool_error(ret));
323 return (ret == SOUND_POOL_ERROR_NONE ? OK : FAIL);
326 /* CMD_ACTIVATE_POOL */
327 static int __proxy_sound_pool_activate(const char *pars)
329 int ret = SOUND_POOL_ERROR_NONE;
331 if ((pars == NULL) || (sscanf(pars, " %zu", &idx) < 1)) {
332 _printf(CMD_COLOR_RED, "You have to specify identifier of the pool "
333 "to be activated after command name! Format: "
334 CMD_ACTIVATE_POOL " <id>\n");
338 if (idx > (MAX_POOL_CNT - 1)) {
339 _printf(CMD_COLOR_RED, "Pool identifier value can't be greater than %d\n",
344 _logger_log_info(CMD_ACTIVATE_POOL " command was called");
345 _logger_log_info("Activating the pool by %zu identifier...", idx);
347 if (pools[idx] == NULL)
348 _logger_log_warn("Pool to be activated is NULL");
350 ret = sound_pool_activate(pools[idx]);
352 PRINT_INFO_OR_ERROR_INFO(ret == SOUND_POOL_ERROR_NONE,
353 "sound_pool_set_state(pool, SOUND_POOL_STATE_ACTIVE) returned "
354 "%s value", __stringify_sound_pool_error(ret));
356 return (ret == SOUND_POOL_ERROR_NONE ? OK : FAIL);
359 /* CMD_DEACTIVATE_POOL */
360 static int __proxy_sound_pool_deactivate(const char *pars)
363 if ((pars == NULL) || (sscanf(pars, " %zu", &idx) < 1)) {
364 _printf(CMD_COLOR_RED, "You have to specify identifier of the pool "
365 "to be deactivated after command name! Format: "
366 CMD_DEACTIVATE_POOL " <id>\n");
370 if (idx > (MAX_POOL_CNT - 1)) {
371 _printf(CMD_COLOR_RED, "Pool identifier value can't be greater than %d\n",
376 _logger_log_info(CMD_DEACTIVATE_POOL " command was called");
377 _logger_log_info("Deactivating the pool by %zu identifier...", idx);
379 if (pools[idx] == NULL)
380 _logger_log_warn("Pool to be deactivated is NULL");
382 int ret = sound_pool_deactivate(pools[idx]);
384 PRINT_INFO_OR_ERROR_INFO(ret == SOUND_POOL_ERROR_NONE,
385 "sound_pool_set_state(pool, SOUND_POOL_STATE_INACTIVE) returned "
386 "%s value", __stringify_sound_pool_error(ret));
388 return (ret == SOUND_POOL_ERROR_NONE ? OK : FAIL);
391 /* CMD_GET_POOL_STATE */
392 static int __proxy_sound_pool_get_state(const char *pars)
395 if ((pars == NULL) || (sscanf(pars, " %zu", &idx) < 1)) {
396 _printf(CMD_COLOR_RED, "You have to specify identifier of the pool "
397 "to get state for, after command name! Format: "
398 CMD_GET_POOL_STATE " <id>\n");
402 if (idx > (MAX_POOL_CNT - 1)) {
403 _printf(CMD_COLOR_RED, "Pool identifier value can't be greater than %d\n",
408 _logger_log_info(CMD_GET_POOL_STATE " command was called");
409 _logger_log_info("Getting the pool state by %zu identifier...", idx);
411 if (pools[idx] == NULL)
412 _logger_log_warn("Pool to get state for is NULL");
414 sound_pool_state_e state = SOUND_POOL_STATE_INACTIVE;
415 int ret = sound_pool_get_state(pools[idx], &state);
417 const char *str_state = (state == SOUND_POOL_STATE_ACTIVE ?
418 "SOUND_POOL_STATE_ACTIVE" : "SOUND_POOL_STATE_INACTIVE");
420 PRINT_INFO_OR_ERROR_INFO(ret == SOUND_POOL_ERROR_NONE,
421 "sound_pool_get_state(pool, state) returned %s value,"
422 " state is %s", __stringify_sound_pool_error(ret), str_state);
424 return (ret == SOUND_POOL_ERROR_NONE ? OK : FAIL);
427 /* CMD_SET_POOL_VOLUME */
428 static int __proxy_sound_pool_set_volume(const char *pars)
432 if ((pars == NULL) || (sscanf(pars, " %zu %f", &idx, &volume) < 2)) {
433 _printf(CMD_COLOR_RED, "You have to specify both identifier of the "
434 "pool and new volume float value to set volume for whole pool! "
435 "Format: " CMD_SET_POOL_VOLUME " <id> <volume>\n");
439 if (idx > (MAX_POOL_CNT - 1)) {
440 _printf(CMD_COLOR_RED, "Pool identifier value can't be greater than %d\n",
445 _logger_log_info(CMD_SET_POOL_VOLUME " command was called");
446 _logger_log_info("Set %f volume value for pool with %zu identifier...",
449 if (pools[idx] == NULL)
450 _logger_log_warn("Pool to get state for is NULL");
452 if (volume < .0f || volume > 1.0f)
453 _logger_log_warn("Volume is set as %f, not in [0, 1.0] range", volume);
455 int ret = sound_pool_set_volume(pools[idx], volume);
457 PRINT_INFO_OR_ERROR_INFO(ret == SOUND_POOL_ERROR_NONE,
458 "sound_pool_set_global_volume(pool, %f) returned %s value",
459 volume, __stringify_sound_pool_error(ret));
461 return (ret == SOUND_POOL_ERROR_NONE ? OK : FAIL);
464 /* CMD_GET_POOL_VOLUME */
465 static int __proxy_sound_pool_get_volume(const char *pars)
468 if ((pars == NULL) || (sscanf(pars, " %zu", &idx) < 1)) {
469 _printf(CMD_COLOR_RED, "You have to specify identifier of the pool "
470 "to get volume for, after command name! Format: "
471 CMD_GET_POOL_VOLUME " <id>\n");
475 if (idx > (MAX_POOL_CNT - 1)) {
476 _printf(CMD_COLOR_RED, "Pool identifier value can't be greater than %d\n",
481 _logger_log_info(CMD_GET_POOL_VOLUME " command was called");
482 _logger_log_info("Getting the pool global volume for pool with %zu "
483 "identifier...", idx);
485 if (pools[idx] == NULL)
486 _logger_log_warn("Pool to get state for is NULL");
489 int ret = sound_pool_get_volume(pools[idx], &volume);
491 PRINT_INFO_OR_ERROR_INFO(ret == SOUND_POOL_ERROR_NONE,
492 "sound_pool_get_global_volume(pool, volume) returned %s value, "
493 "volume is %f", __stringify_sound_pool_error(ret), volume);
495 return (ret == SOUND_POOL_ERROR_NONE ? OK : FAIL);
498 /* CMD_SET_POOL_CB_MSG */
499 static int __proxy_sound_pool_set_state_changed_cb_message(const char *pars)
503 char msg[MAX_MSG_LEN] = { '\0' };
505 if ((pars == NULL) || (sscanf(pars, " %zu %"MAX_MSG_LEN_STR"[^ ]", &idx, msg) < 2)) {
506 _printf(CMD_COLOR_RED, "You have to specify both identifier of the "
507 "pool and message to be shown each time when state of the pool "
508 " is changed! Message should be a single word. Format: "
509 CMD_SET_POOL_CB_MSG " <id> <message>\n");
513 if (idx > (MAX_POOL_CNT - 1)) {
514 _printf(CMD_COLOR_RED, "Pool identifier value can't be greater than %d\n",
519 _logger_log_info(CMD_SET_POOL_CB_MSG " command was called");
520 _logger_log_info("Set state changing callback (%s message) for pool with "
521 "%zu identifier...", msg, idx);
523 if (pools[idx] == NULL)
524 _logger_log_warn("Pool to set callback for is NULL");
528 messages[idx] = strndup(msg, MAX_MSG_LEN);
530 int ret = sound_pool_set_state_changed_cb(pools[idx], __sp_cb_msg,
533 PRINT_INFO_OR_ERROR_INFO(ret == SOUND_POOL_ERROR_NONE,
534 "sound_pool_set_state_change_callback(pool, cb, \"%s\") "
535 "returned %s value", msg, __stringify_sound_pool_error(ret));
537 return (ret == SOUND_POOL_ERROR_NONE ? OK : FAIL);
540 /* CMD_SET_POOL_CB_SCRIPT */
541 static int __proxy_sound_pool_set_state_changed_cb_script(const char *pars)
545 char scr[MAX_MSG_LEN] = { '\0' };
547 if ((pars == NULL) || (sscanf(pars, " %zu %"MAX_MSG_LEN_STR"[^ ]", &idx, scr) < 2)) {
548 _printf(CMD_COLOR_RED, "You have to specify both identifier of the "
549 "pool and script file name to be executed each time when state "
550 "of the pool will be changed! Format: "
551 CMD_SET_POOL_CB_SCRIPT " <id> <script file>\n");
555 if (idx > (MAX_POOL_CNT - 1)) {
556 _printf(CMD_COLOR_RED, "Pool identifier value can't be greater than %d\n",
561 _logger_log_info(CMD_SET_POOL_CB_SCRIPT " command was called");
562 _logger_log_info("Set state changing callback (%s script) for pool with "
563 "%zu identifier...", scr, idx);
565 if (pools[idx] == NULL)
566 _logger_log_warn("Pool to set callback for is NULL");
570 scripts[idx] = strndup(scr, MAX_MSG_LEN);
572 int ret = sound_pool_set_state_changed_cb(pools[idx], __sp_cb_scr,
575 PRINT_INFO_OR_ERROR_INFO(ret == SOUND_POOL_ERROR_NONE,
576 "sound_pool_set_state_change_callback(pool, cb, \"%s\") "
577 "returned %s value", scr, __stringify_sound_pool_error(ret));
579 return (ret == SOUND_POOL_ERROR_NONE ? OK : FAIL);
582 /* CMD_UNSET_POOL_CB */
583 static int __proxy_sound_pool_unset_state_changed_cb(const char *pars)
586 if ((pars == NULL) || (sscanf(pars, " %zu", &idx) < 1)) {
587 _printf(CMD_COLOR_RED, "You have to specify identifier of the pool! "
588 "Format: " CMD_UNSET_POOL_CB " <id>\n");
592 if (idx > (MAX_POOL_CNT - 1)) {
593 _printf(CMD_COLOR_RED, "Pool identifier value can't be greater than %d\n",
598 _logger_log_info(CMD_UNSET_POOL_CB " command was called");
599 _logger_log_info("Unset state changing callback for pool with "
600 "%zu identifier...", idx);
602 if (pools[idx] == NULL)
603 _logger_log_warn("Pool to unset callback for is NULL");
605 int ret = sound_pool_unset_state_changed_cb(pools[idx]);
607 if (messages[idx] != NULL)
609 messages[idx] = NULL;
611 if (scripts[idx] != NULL)
615 PRINT_INFO_OR_ERROR_INFO(ret == SOUND_POOL_ERROR_NONE,
616 "sound_pool_unset_state_change_callback(pool) "
617 "returned %s value", __stringify_sound_pool_error(ret));
619 return (ret == SOUND_POOL_ERROR_NONE ? OK : FAIL);
623 static int __proxy_sound_pool_list()
625 _logger_log_info("Getting the pool identifiers...");
627 const size_t buffer_size = 1024;
628 char buffer[buffer_size];
633 while (idx < MAX_POOL_CNT) {
634 len = strnlen(buffer, buffer_size);
635 if (pools[idx++] != NULL) {
640 while ((id = id / 10) > 0);
642 if (len + add_len + 1 > buffer_size)
644 snprintf(buffer + len, buffer_size, "%zu ", id);
648 _printf(CMD_COLOR_GREEN, "Pools identifiers: %s\n", buffer);
649 _logger_log_info("Pools identifiers: %s", buffer);
651 _logger_log_info("Pool identifiers were retrieved...");
656 /* CMD_LOAD_SOURCE */
657 static int __proxy_sound_pool_load_source_from_file(const char *pars)
661 char fname[MAX_PATH_LEN] = {'\0'};
662 char tag[MAX_PATH_LEN] = {'\0'};
664 if ((pars == NULL) || sscanf(pars, " %zu %"MAX_PATH_LEN_STR"[^ ] "
665 "%"MAX_PATH_LEN_STR"[^ ]", &idx, fname, tag) < 2) {
666 _printf(CMD_COLOR_RED, "You have to specify at least pool identifier and "
667 "file name to be loaded! Format: " CMD_LOAD_SOURCE " <pool id> "
668 "<file name> <source tag>\n");
672 if (idx > (MAX_POOL_CNT - 1)) {
673 _printf(CMD_COLOR_RED, "Pool identifier value can't be greater than %d\n",
678 if (pools[idx] == NULL)
679 _logger_log_warn("Pool with specified identifier is NULL");
681 /* If tag wasn't specified by the user, we will use file path as a tag */
683 strncpy(tag, fname, MAX_PATH_LEN - 1);
685 _logger_log_info(CMD_LOAD_SOURCE " command was called");
686 _logger_log_info("Loading source to the pool with %zu identifier from %s file. "
687 "Tag '%s' will be assigned for the loaded source...", idx, fname, tag);
689 int ret = sound_pool_load_source_from_file(pools[idx], fname, tag);
691 PRINT_INFO_OR_ERROR_INFO(ret == SOUND_POOL_ERROR_NONE,
692 "sound_pool_load_source_from_file(pool, \"%s\", \"%s\") returned "
693 "%s value", fname, tag, __stringify_sound_pool_error(ret));
695 return (ret == SOUND_POOL_ERROR_NONE ? OK : FAIL);
698 /* CMD_UNLOAD_SOURCE */
699 static int __proxy_sound_pool_unload_source(const char *pars)
703 char tag[MAX_PATH_LEN] = {'\0'};
705 if ((pars == NULL) || sscanf(pars, " %zu %"MAX_PATH_LEN_STR"[^ ]", &idx, tag) < 2) {
706 _printf(CMD_COLOR_RED, "You have to specify both pool identifier and "
707 "source tag to be unloaded! Format: " CMD_UNLOAD_SOURCE
708 " <pool id> <source tag>\n");
712 if (idx > (MAX_POOL_CNT - 1)) {
713 _printf(CMD_COLOR_RED, "Pool identifier value can't be greater than %d\n",
718 if (pools[idx] == NULL)
719 _logger_log_warn("Pool with specified identifier is NULL");
721 _logger_log_info(CMD_UNLOAD_SOURCE " command was called");
722 _logger_log_info("Unloading source by '%s' tag from the pool with %zu "
723 "identifier...", tag, idx);
725 int ret = sound_pool_unload_source(pools[idx], tag);
727 PRINT_INFO_OR_ERROR_INFO(ret == SOUND_POOL_ERROR_NONE,
728 "sound_pool_unload_source(pool, \"%s\") returned "
729 "%s value", tag, __stringify_sound_pool_error(ret));
731 return (ret == SOUND_POOL_ERROR_NONE ? OK : FAIL);
734 /* CMD_PLAY_STREAM */
735 static int __proxy_sound_pool_play_stream(const char *pars)
740 unsigned rank = DEFAULT_STREAM_PRIORITY_RANK;
741 sound_pool_stream_priority_policy_e priority_policy = SOUND_POOL_STREAM_PRIORITY_POLICY_MUTE;
743 char tag[MAX_PATH_LEN] = {'\0'};
745 if ((pars == NULL) || sscanf(pars, " %zu %"MAX_PATH_LEN_STR"[^ ] %i %f %u %u",
746 &idx, tag, &loop, &volume, &rank, &priority_policy) < 2) {
747 _printf(CMD_COLOR_RED, "You have to specify at least pool identifier and "
748 "source tag to be played in stream! Format: " CMD_PLAY_STREAM
749 " <pool id> <source tag> <loop> <volume> <priority rank> <priority_policy>... "
750 "0 'priority rank' value corresponds to the lowest priority.\n");
754 if (idx > (MAX_POOL_CNT - 1)) {
755 _printf(CMD_COLOR_RED, "Pool identifier value can't be greater than %d\n",
760 if (pools[idx] == NULL)
761 _logger_log_warn("Pool with specified identifier is NULL");
763 _logger_log_info(CMD_PLAY_STREAM " command was called");
764 _logger_log_info("Playing stream based on source with '%s' tag from the pool "
765 "with %zu identifier...", tag, idx);
767 unsigned stream_idx = 0;
768 int ret = sound_pool_stream_play(pools[idx], tag, loop, volume, rank, priority_policy, __s_cb_msg,
771 if (ret == SOUND_POOL_ERROR_NONE) {
772 _logger_log_info("sound_pool_play_stream(pool, \"%s\", %i, %f, %u,"
773 " %u, %p, NULL, &stream_idx) returned %s value. "
774 "Generated identifier is %i", tag, loop, volume, rank, priority_policy, __s_cb_msg,
775 __stringify_sound_pool_error(ret), stream_idx);
776 _printf(CMD_COLOR_GREEN, "Generated stream identifier is %i\n", stream_idx);
778 _logger_log_err("sound_pool_play_stream(pool, \"%s\", %i, %f, %u,"
779 " %u, %p, NULL, &stream_idx) returned %s value",
780 tag, loop, volume, rank, priority_policy, __s_cb_msg, __stringify_sound_pool_error(ret));
783 return (ret == SOUND_POOL_ERROR_NONE ? OK : FAIL);
786 /* CMD_PAUSE_STREAM */
787 static int __proxy_sound_pool_pause_stream(const char *pars)
790 size_t stream_idx = 0;
792 if ((pars == NULL) || (sscanf(pars, " %zu %i", &idx, &stream_idx) < 2)) {
793 _printf(CMD_COLOR_RED, "You have to specify both pool identifier and "
794 "stream to be paused identifier! Format: " CMD_PAUSE_STREAM
795 " <pool id> <stream id>\n");
799 if (idx > (MAX_POOL_CNT - 1)) {
800 _printf(CMD_COLOR_RED, "Pool identifier value can't be greater than %d\n",
805 if (pools[idx] == NULL)
806 _logger_log_warn("Pool with specified identifier is NULL");
808 _logger_log_info(CMD_PAUSE_STREAM " command was called");
810 int ret = sound_pool_stream_pause(pools[idx], stream_idx);
812 PRINT_INFO_OR_ERROR_INFO(ret == SOUND_POOL_ERROR_NONE,
813 "sound_pool_pause_stream(pool, %i) returned %s value",
814 stream_idx, __stringify_sound_pool_error(ret));
816 return (ret == SOUND_POOL_ERROR_NONE ? OK : FAIL);
819 /* CMD_RESUME_STREAM */
820 static int __proxy_sound_pool_resume_stream(const char *pars)
823 size_t stream_idx = 0;
825 if ((pars == NULL) || (sscanf(pars, " %zu %i", &idx, &stream_idx) < 2)) {
826 _printf(CMD_COLOR_RED, "You have to specify both pool identifier and "
827 "stream to be resumed identifier! Format: " CMD_RESUME_STREAM
828 " <pool id> <stream id>\n");
832 if (idx > (MAX_POOL_CNT - 1)) {
833 _printf(CMD_COLOR_RED, "Pool identifier value can't be greater than %d\n",
838 if (pools[idx] == NULL)
839 _logger_log_warn("Pool with specified identifier is NULL");
841 _logger_log_info(CMD_RESUME_STREAM " command was called");
843 int ret = sound_pool_stream_resume(pools[idx], stream_idx);
845 PRINT_INFO_OR_ERROR_INFO(ret == SOUND_POOL_ERROR_NONE,
846 "sound_pool_resume_stream(pool, %i) returned %s value",
847 stream_idx, __stringify_sound_pool_error(ret));
849 return (ret == SOUND_POOL_ERROR_NONE ? OK : FAIL);
852 /* CMD_STOP_STREAM */
853 static int __proxy_sound_pool_stop_stream(const char *pars)
856 size_t stream_idx = 0;
858 if ((pars == NULL) || (sscanf(pars, " %zu %zu", &idx, &stream_idx) < 2)) {
859 _printf(CMD_COLOR_RED, "You have to specify both pool identifier and "
860 "stream to be stopped identifier! Format: " CMD_STOP_STREAM
861 " <pool id> <stream id>\n");
865 if (idx > (MAX_POOL_CNT - 1)) {
866 _printf(CMD_COLOR_RED, "Pool identifier value can't be greater than %d\n",
871 if (pools[idx] == NULL)
872 _logger_log_warn("Pool with specified identifier is NULL");
874 _logger_log_info(CMD_STOP_STREAM " command was called");
876 int ret = sound_pool_stream_stop(pools[idx], stream_idx);
878 PRINT_INFO_OR_ERROR_INFO(ret == SOUND_POOL_ERROR_NONE,
879 "sound_pool_stop_stream(pool, %i) returned %s value",
880 stream_idx, __stringify_sound_pool_error(ret));
882 return (ret == SOUND_POOL_ERROR_NONE ? OK : FAIL);
885 /* CMD_SET_STREAM_VOLUME */
886 static int __proxy_sound_pool_stream_set_volume(const char *pars)
889 size_t stream_idx = 0;
890 float volume_val = 1.0f;
893 || (sscanf(pars, " %zu %zu %f", &idx, &stream_idx, &volume_val) < 3)) {
894 _printf(CMD_COLOR_RED, "You have to specify all following parameters: "
895 "pool identifier, stream identifier! Format: "
896 CMD_SET_STREAM_VOLUME " <pool id> <stream id> <volume>\n");
900 if (idx > (MAX_POOL_CNT - 1)) {
901 _printf(CMD_COLOR_RED, "Pool identifier value can't be greater than %d\n",
906 if (pools[idx] == NULL)
907 _logger_log_warn("Pool with specified identifier is NULL");
909 if (volume_val < .0f || volume_val > 1.0f)
910 _logger_log_warn("Volume has to be specified in 0.0~1.0 range");
912 _logger_log_info(CMD_SET_STREAM_VOLUME " command was called");
914 int ret = sound_pool_stream_set_volume(pools[idx], stream_idx, volume_val);
916 PRINT_INFO_OR_ERROR_INFO(ret == SOUND_POOL_ERROR_NONE,
917 "sound_pool_stream_set_volume(pool, %i, %f) returned %s value",
918 stream_idx, volume_val, __stringify_sound_pool_error(ret));
920 return (ret == SOUND_POOL_ERROR_NONE ? OK : FAIL);
923 /* CMD_GET_STREAM_VOLUME */
924 static int __proxy_sound_pool_stream_get_volume(const char *pars)
927 size_t stream_idx = 0;
928 if ((pars == NULL) || (sscanf(pars, " %zu %zu", &idx, &stream_idx) < 2)) {
929 _printf(CMD_COLOR_RED, "You have to specify both pool and stream "
930 "identifiers after command name! Format: "
931 CMD_GET_STREAM_VOLUME " <pool id> <stream id>\n");
935 if (idx > (MAX_POOL_CNT - 1)) {
936 _printf(CMD_COLOR_RED, "Pool identifier value can't be greater than %d\n",
941 _logger_log_info(CMD_GET_STREAM_VOLUME " command was called");
942 _logger_log_info("Getting the %zu stream from %zu pool volume value...",
945 if (pools[idx] == NULL)
946 _logger_log_warn("Pool to get state for is NULL");
949 int ret = sound_pool_stream_get_volume(pools[idx], stream_idx, &volume);
951 PRINT_INFO_OR_ERROR_INFO(ret == SOUND_POOL_ERROR_NONE,
952 "sound_pool_stream_get_volume(pool, %zu, volume) returned %s value, "
953 "volume is %f", stream_idx, __stringify_sound_pool_error(ret), volume);
955 return (ret == SOUND_POOL_ERROR_NONE ? OK : FAIL);
958 /* CMD_SET_STREAM_PRIORITY */
959 static int __proxy_sound_pool_stream_set_priority(const char *pars)
962 size_t stream_idx = 0;
966 || (sscanf(pars, " %zu %zu %u", &idx, &stream_idx, &rank) < 3)) {
967 _printf(CMD_COLOR_RED, "You have to specify all following parameters: "
968 "pool identifier, stream identifier, and priority rank! Format: "
969 CMD_SET_STREAM_PRIORITY " <pool id> <stream id> <rank>\n");
973 if (idx > (MAX_POOL_CNT - 1)) {
974 _printf(CMD_COLOR_RED, "Pool identifier value can't be greater than %d\n",
979 if (pools[idx] == NULL)
980 _logger_log_warn("Pool with specified identifier is NULL");
982 _logger_log_info(CMD_SET_STREAM_PRIORITY " command was called");
984 int ret = sound_pool_stream_set_priority(pools[idx], stream_idx, rank);
986 PRINT_INFO_OR_ERROR_INFO(ret == SOUND_POOL_ERROR_NONE,
987 "sound_pool_stream_set_priority(pool, %zu, %u) returned %s value",
988 stream_idx, rank, __stringify_sound_pool_error(ret));
990 return (ret == SOUND_POOL_ERROR_NONE ? OK : FAIL);
993 /* CMD_GET_STREAM_PRIORITY */
994 static int __proxy_sound_pool_stream_get_priority(const char *pars)
997 size_t stream_idx = 0;
998 if ((pars == NULL) || (sscanf(pars, " %zu %zu", &idx, &stream_idx) < 2)) {
999 _printf(CMD_COLOR_RED, "You have to specify both pool and stream "
1000 "identifiers after command name! Format: "
1001 CMD_GET_STREAM_PRIORITY " <pool id> <stream id>\n");
1005 if (idx > (MAX_POOL_CNT - 1)) {
1006 _printf(CMD_COLOR_RED, "Pool identifier value can't be greater than %d\n",
1011 _logger_log_info(CMD_GET_STREAM_PRIORITY " command was called");
1012 _logger_log_info("Getting the stream priority rank by %zu identifier in "
1013 "%zu pool...", stream_idx, idx);
1015 if (pools[idx] == NULL)
1016 _logger_log_warn("Pool where stream should be located is NULL");
1019 int ret = sound_pool_stream_get_priority(pools[idx], stream_idx, &rank);
1021 PRINT_INFO_OR_ERROR_INFO(ret == SOUND_POOL_ERROR_NONE,
1022 "sound_pool_stream_get_priority(pool, %u, rank) returned %s value, "
1023 "rank value is %u", stream_idx, __stringify_sound_pool_error(ret), rank);
1025 return (ret == SOUND_POOL_ERROR_NONE ? OK : FAIL);
1028 /* CMD_GET_STREAM_STATE */
1029 static int __proxy_sound_pool_get_stream_state(const char *pars)
1032 size_t stream_idx = 0;
1033 if ((pars == NULL) || (sscanf(pars, " %zu %zu", &idx, &stream_idx) < 2)) {
1034 _printf(CMD_COLOR_RED, "You have to specify both pool and stream "
1035 "identifiers after command name! Format: "
1036 CMD_GET_STREAM_STATE " <pool id> <stream id>\n");
1040 if (idx > (MAX_POOL_CNT - 1)) {
1041 _printf(CMD_COLOR_RED, "Pool identifier value can't be greater than %d\n",
1046 _logger_log_info(CMD_GET_STREAM_STATE " command was called");
1047 _logger_log_info("Getting the stream state by %zu identifier in %zu "
1048 "pool...", stream_idx, idx);
1050 if (pools[idx] == NULL)
1051 _logger_log_warn("Pool where stream should be located is NULL");
1053 sound_pool_stream_state_e state = SOUND_POOL_STREAM_STATE_NONE;
1054 int ret = sound_pool_stream_get_state(pools[idx], stream_idx, &state);
1056 PRINT_INFO_OR_ERROR_INFO(ret == SOUND_POOL_ERROR_NONE,
1057 "sound_pool_get_stream_state(pool, %zu, state) returned %s value, "
1058 "state is %s", stream_idx, __stringify_sound_pool_error(ret),
1059 __stringify_stream_state(state));
1061 return (ret == SOUND_POOL_ERROR_NONE ? OK : FAIL);
1065 static int __proxy_sleep(const char *pars)
1067 useconds_t stime = 0;
1069 if ((pars == NULL) || (sscanf(pars, " %u", &stime) < 1)) {
1070 _printf(CMD_COLOR_RED, "You have to specify number of milliseconds "
1071 "for the pause duration! Format: " CMD_SLEEP " <millisecs>\n");
1075 _logger_log_info(CMD_SLEEP " command was called");
1076 _logger_log_info("Start main thread sleep for %u milliseconds...", stime);
1077 stime *= MICROSECS_PER_MILLISEC;
1079 _logger_log_info("Main thread sleep has been finished...", stime);
1084 /* CMD_EXECUTE_SCRIPT */
1085 static int __proxy_sound_pool_execute_script(const char *pars)
1087 char script_file[MAX_PATH_LEN] = {'\0'};
1089 if ((pars == NULL) || (sscanf(pars, " %"MAX_PATH_LEN_STR"[^ ]", script_file) < 1)) {
1090 _printf(CMD_COLOR_RED, "You have to specify script file name to be "
1091 "executed after command name! Format: " CMD_EXECUTE_SCRIPT " "
1096 _logger_log_info(CMD_EXECUTE_SCRIPT " command was called");
1097 _logger_log_info("Loading script from file...");
1098 FILE *fd = fopen(script_file, "r");
1101 _logger_log_info("File has been loaded...");
1102 _logger_log_info("Reading lines...");
1103 size_t line_len = 0;
1105 while ((line_len = getline(&line, &line_len, fd)) != -1) {
1106 line[strnlen(line, MAX_COMMAND_LINE_LEN) - 1] = '\0';
1107 _logger_log_info("Executing line: %s", line);
1108 if (_exec_cmd(line) != OK)
1109 _logger_log_warn("Unknown or unsupported command! "
1110 "Line was skipped.");
1112 _logger_log_info("Lines were read...");
1116 _logger_log_err("File wasn't loaded...");
1120 _logger_log_info("Close file...");
1128 /* Number of parameters supported by each command */
1129 static int cmd_pars[MAX_COMMAND_LINE_LEN] = { /* CMD_EXIT */ 0,
1130 /* CMD_HELP */ 0, /* CMD_CREATE_POOL */ 0, /* CMD_DESTROY_POOL */ 1,
1131 /* CMD_ACTIVATE_POOL */ 1, /* CMD_DEACTIVATE_POOL */ 1,
1132 /* CMD_GET_POOL_STATE */ 1, /* CMD_SET_POOL_VOLUME */ 2,
1133 /* CMD_GET_POOL_VOLUME */ 2, /* CMD_SET_POOL_CB_MSG */ 2,
1134 /* CMD_SET_POOL_CB_SCRIPT */ 2, /* CMD_UNSET_POOL_CB */ 1,
1135 /* CMD_LIST_POOL */ 0, /* CMD_LOAD_SOURCE */ 3,
1136 /* CMD_LOAD_MEDIA_PACKAGE */ 3, /* CMD_UNLOAD_SOURCE */ 2,
1137 /* CMD_PLAY_STREAM */ 5, /* CMD_STOP_STREAM */ 2,
1138 /* CMD_PAUSE_STREAM */ 2, /* CMD_RESUME_STREAM */ 2,
1139 /* CMD_SET_STREAM_VOLUME */ 3, /* CMD_GET_STREAM_VOLUME */ 2,
1140 /* CMD_SET_STREAM_PRIORITY */ 3, /* CMD_GET_STREAM_PRIORITY */ 2,
1141 /* CMD_GET_STREAM_STATE */ 2, /* CMD_SET_STREAM_CB_MSG */ 3,
1142 /* CMD_SET_STREAM_CB_SCRIPT */ 3, /* CMD_UNSET_STREAM_CB */ 2,
1143 /* CMD_EXECUTE_SCRIPT */ 1, /* CMD_SLEEP */ 1 };
1145 /* Command -> Function mapping */
1146 static int (*cmd_fcns[MAX_COMMAND_LINE_LEN])() = {
1147 /* CMD_EXIT */ __exit,
1148 /* CMD_HELP */ __print_cmd_help_msg,
1149 /* CMD_CREATE_POOL */ __proxy_sound_pool_create,
1150 /* CMD_DESTROY_POOL */ __proxy_sound_pool_destroy,
1151 /* CMD_ACTIVATE_POOL */ __proxy_sound_pool_activate,
1152 /* CMD_DEACTIVATE_POOL */ __proxy_sound_pool_deactivate,
1153 /* CMD_GET_POOL_STATE */ __proxy_sound_pool_get_state,
1154 /* CMD_SET_POOL_VOLUME */ __proxy_sound_pool_set_volume,
1155 /* CMD_GET_POOL_VOLUME */ __proxy_sound_pool_get_volume,
1156 /* CMD_SET_POOL_CB_MSG */ __proxy_sound_pool_set_state_changed_cb_message,
1157 /* CMD_SET_POOL_CB_SCRIPT */ __proxy_sound_pool_set_state_changed_cb_script,
1158 /* CMD_UNSET_POOL_CB */ __proxy_sound_pool_unset_state_changed_cb,
1159 /* CMD_LIST_POOL */ __proxy_sound_pool_list,
1160 /* CMD_LOAD_SOURCE */ __proxy_sound_pool_load_source_from_file,
1161 /* CMD_LOAD_MEDIA_PACKAGE */ NULL,
1162 /* CMD_UNLOAD_SOURCE */ __proxy_sound_pool_unload_source,
1163 /* CMD_PLAY_STREAM */ __proxy_sound_pool_play_stream,
1164 /* CMD_STOP_STREAM */ __proxy_sound_pool_stop_stream,
1165 /* CMD_PAUSE_STREAM */ __proxy_sound_pool_pause_stream,
1166 /* CMD_RESUME_STREAM */ __proxy_sound_pool_resume_stream,
1167 /* CMD_SET_STREAM_VOLUME */ __proxy_sound_pool_stream_set_volume,
1168 /* CMD_GET_STREAM_VOLUME */ __proxy_sound_pool_stream_get_volume,
1169 /* CMD_SET_STREAM_PRIORITY */ __proxy_sound_pool_stream_set_priority,
1170 /* CMD_GET_STREAM_PRIORITY */ __proxy_sound_pool_stream_get_priority,
1171 /* CMD_GET_STREAM_STATE */ __proxy_sound_pool_get_stream_state,
1172 /* CMD_EXECUTE_SCRIPT */ __proxy_sound_pool_execute_script,
1173 /* CMD_SLEEP */ __proxy_sleep };
1175 int _exec_cmd(const char *cmd_line)
1177 /* User just pressed enter: */
1178 if (strlen(cmd_line) == 0) return OK;
1180 size_t trim_len = 0;
1181 while ((cmd_line + trim_len)[0] == ' ')
1184 const char *cmd = cmd_line + trim_len;
1186 /* Macro for checking command correctness */
1187 # define CHECK_CMD(ccmd, line) \
1188 (strncmp(ccmd, line, strnlen(ccmd, MAX_COMMAND_LINE_LEN)) == 0)
1191 for (; idx < CMD_COUNT; ++idx) {
1192 if (CHECK_CMD(cmd_list[idx], cmd)) {
1193 if (cmd_pars[idx] > 0) {
1195 return cmd_fcns[idx](cmd + strlen(cmd_list[idx]));
1197 return cmd_fcns[idx]();