]> code.delx.au - pulseaudio/blob - src/pulse/introspect.c
bump API and protocol version. Return PA_ERR_NOTSUPPORTED if pa_context_move_sink_inp...
[pulseaudio] / src / pulse / introspect.c
1 /* $Id$ */
2
3 /***
4 This file is part of PulseAudio.
5
6 PulseAudio is free software; you can redistribute it and/or modify
7 it under the terms of the GNU Lesser General Public License as published
8 by the Free Software Foundation; either version 2 of the License,
9 or (at your option) any later version.
10
11 PulseAudio is distributed in the hope that it will be useful, but
12 WITHOUT ANY WARRANTY; without even the implied warranty of
13 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14 General Public License for more details.
15
16 You should have received a copy of the GNU Lesser General Public License
17 along with PulseAudio; if not, write to the Free Software
18 Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307
19 USA.
20 ***/
21
22 #ifdef HAVE_CONFIG_H
23 #include <config.h>
24 #endif
25
26 #include <assert.h>
27
28 #include <pulse/context.h>
29
30 #include <pulsecore/gccmacro.h>
31 #include <pulsecore/pstream-util.h>
32
33 #include "internal.h"
34
35 #include "introspect.h"
36
37 /*** Statistics ***/
38
39 static void context_stat_callback(pa_pdispatch *pd, uint32_t command, PA_GCC_UNUSED uint32_t tag, pa_tagstruct *t, void *userdata) {
40 pa_operation *o = userdata;
41 pa_stat_info i, *p = &i;
42
43 assert(pd);
44 assert(o);
45 assert(o->ref >= 1);
46
47 if (!o->context)
48 goto finish;
49
50 if (command != PA_COMMAND_REPLY) {
51 if (pa_context_handle_error(o->context, command, t) < 0)
52 goto finish;
53
54 p = NULL;
55 } else if (pa_tagstruct_getu32(t, &i.memblock_total) < 0 ||
56 pa_tagstruct_getu32(t, &i.memblock_total_size) < 0 ||
57 pa_tagstruct_getu32(t, &i.memblock_allocated) < 0 ||
58 pa_tagstruct_getu32(t, &i.memblock_allocated_size) < 0 ||
59 pa_tagstruct_getu32(t, &i.scache_size) < 0 ||
60 !pa_tagstruct_eof(t)) {
61 pa_context_fail(o->context, PA_ERR_PROTOCOL);
62 goto finish;
63 }
64
65 if (o->callback) {
66 pa_stat_info_cb_t cb = (pa_stat_info_cb_t) o->callback;
67 cb(o->context, p, o->userdata);
68 }
69
70 finish:
71 pa_operation_done(o);
72 pa_operation_unref(o);
73 }
74
75 pa_operation* pa_context_stat(pa_context *c, pa_stat_info_cb_t cb, void *userdata) {
76 return pa_context_send_simple_command(c, PA_COMMAND_STAT, context_stat_callback, (pa_operation_cb_t) cb, userdata);
77 }
78
79 /*** Server Info ***/
80
81 static void context_get_server_info_callback(pa_pdispatch *pd, uint32_t command, PA_GCC_UNUSED uint32_t tag, pa_tagstruct *t, void *userdata) {
82 pa_operation *o = userdata;
83 pa_server_info i, *p = &i;
84
85 assert(pd);
86 assert(o);
87 assert(o->ref >= 1);
88
89 if (!o->context)
90 goto finish;
91
92 if (command != PA_COMMAND_REPLY) {
93 if (pa_context_handle_error(o->context, command, t) < 0)
94 goto finish;
95
96 p = NULL;
97 } else if (pa_tagstruct_gets(t, &i.server_name) < 0 ||
98 pa_tagstruct_gets(t, &i.server_version) < 0 ||
99 pa_tagstruct_gets(t, &i.user_name) < 0 ||
100 pa_tagstruct_gets(t, &i.host_name) < 0 ||
101 pa_tagstruct_get_sample_spec(t, &i.sample_spec) < 0 ||
102 pa_tagstruct_gets(t, &i.default_sink_name) < 0 ||
103 pa_tagstruct_gets(t, &i.default_source_name) < 0 ||
104 pa_tagstruct_getu32(t, &i.cookie) < 0 ||
105 !pa_tagstruct_eof(t)) {
106
107 pa_context_fail(o->context, PA_ERR_PROTOCOL);
108 goto finish;
109 }
110
111 if (o->callback) {
112 pa_server_info_cb_t cb = (pa_server_info_cb_t) o->callback;
113 cb(o->context, p, o->userdata);
114 }
115
116 finish:
117 pa_operation_done(o);
118 pa_operation_unref(o);
119 }
120
121 pa_operation* pa_context_get_server_info(pa_context *c, pa_server_info_cb_t cb, void *userdata) {
122 return pa_context_send_simple_command(c, PA_COMMAND_GET_SERVER_INFO, context_get_server_info_callback, (pa_operation_cb_t) cb, userdata);
123 }
124
125 /*** Sink Info ***/
126
127 static void context_get_sink_info_callback(pa_pdispatch *pd, uint32_t command, PA_GCC_UNUSED uint32_t tag, pa_tagstruct *t, void *userdata) {
128 pa_operation *o = userdata;
129 int eol = 1;
130
131 assert(pd);
132 assert(o);
133 assert(o->ref >= 1);
134
135 if (!o->context)
136 goto finish;
137
138 if (command != PA_COMMAND_REPLY) {
139 if (pa_context_handle_error(o->context, command, t) < 0)
140 goto finish;
141
142 eol = -1;
143 } else {
144 uint32_t flags;
145
146 while (!pa_tagstruct_eof(t)) {
147 pa_sink_info i;
148
149 if (pa_tagstruct_getu32(t, &i.index) < 0 ||
150 pa_tagstruct_gets(t, &i.name) < 0 ||
151 pa_tagstruct_gets(t, &i.description) < 0 ||
152 pa_tagstruct_get_sample_spec(t, &i.sample_spec) < 0 ||
153 pa_tagstruct_get_channel_map(t, &i.channel_map) < 0 ||
154 pa_tagstruct_getu32(t, &i.owner_module) < 0 ||
155 pa_tagstruct_get_cvolume(t, &i.volume) < 0 ||
156 pa_tagstruct_get_boolean(t, &i.mute) < 0 ||
157 pa_tagstruct_getu32(t, &i.monitor_source) < 0 ||
158 pa_tagstruct_gets(t, &i.monitor_source_name) < 0 ||
159 pa_tagstruct_get_usec(t, &i.latency) < 0 ||
160 pa_tagstruct_gets(t, &i.driver) < 0 ||
161 pa_tagstruct_getu32(t, &flags) < 0) {
162
163 pa_context_fail(o->context, PA_ERR_PROTOCOL);
164 goto finish;
165 }
166
167 i.flags = (pa_sink_flags_t) flags;
168
169 if (o->callback) {
170 pa_sink_info_cb_t cb = (pa_sink_info_cb_t) o->callback;
171 cb(o->context, &i, 0, o->userdata);
172 }
173 }
174 }
175
176 if (o->callback) {
177 pa_sink_info_cb_t cb = (pa_sink_info_cb_t) o->callback;
178 cb(o->context, NULL, eol, o->userdata);
179 }
180
181 finish:
182 pa_operation_done(o);
183 pa_operation_unref(o);
184 }
185
186 pa_operation* pa_context_get_sink_info_list(pa_context *c, pa_sink_info_cb_t cb, void *userdata) {
187 return pa_context_send_simple_command(c, PA_COMMAND_GET_SINK_INFO_LIST, context_get_sink_info_callback, (pa_operation_cb_t) cb, userdata);
188 }
189
190 pa_operation* pa_context_get_sink_info_by_index(pa_context *c, uint32_t idx, pa_sink_info_cb_t cb, void *userdata) {
191 pa_tagstruct *t;
192 pa_operation *o;
193 uint32_t tag;
194
195 assert(c);
196 assert(c->ref >= 1);
197 assert(cb);
198
199 PA_CHECK_VALIDITY_RETURN_NULL(c, c->state == PA_CONTEXT_READY, PA_ERR_BADSTATE);
200
201 o = pa_operation_new(c, NULL, (pa_operation_cb_t) cb, userdata);
202
203 t = pa_tagstruct_command(c, PA_COMMAND_GET_SINK_INFO, &tag);
204 pa_tagstruct_putu32(t, idx);
205 pa_tagstruct_puts(t, NULL);
206 pa_pstream_send_tagstruct(c->pstream, t);
207 pa_pdispatch_register_reply(c->pdispatch, tag, DEFAULT_TIMEOUT, context_get_sink_info_callback, pa_operation_ref(o), (pa_free_cb_t) pa_operation_unref);
208
209 return o;
210 }
211
212 pa_operation* pa_context_get_sink_info_by_name(pa_context *c, const char *name, pa_sink_info_cb_t cb, void *userdata) {
213 pa_tagstruct *t;
214 pa_operation *o;
215 uint32_t tag;
216
217 assert(c);
218 assert(c->ref >= 1);
219 assert(cb);
220
221 PA_CHECK_VALIDITY_RETURN_NULL(c, c->state == PA_CONTEXT_READY, PA_ERR_BADSTATE);
222 PA_CHECK_VALIDITY_RETURN_NULL(c, !name || *name, PA_ERR_INVALID);
223
224 o = pa_operation_new(c, NULL, (pa_operation_cb_t) cb, userdata);
225
226 t = pa_tagstruct_command(c, PA_COMMAND_GET_SINK_INFO, &tag);
227 pa_tagstruct_putu32(t, PA_INVALID_INDEX);
228 pa_tagstruct_puts(t, name);
229 pa_pstream_send_tagstruct(c->pstream, t);
230 pa_pdispatch_register_reply(c->pdispatch, tag, DEFAULT_TIMEOUT, context_get_sink_info_callback, pa_operation_ref(o), (pa_free_cb_t) pa_operation_unref);
231
232 return o;
233 }
234
235 /*** Source info ***/
236
237 static void context_get_source_info_callback(pa_pdispatch *pd, uint32_t command, PA_GCC_UNUSED uint32_t tag, pa_tagstruct *t, void *userdata) {
238 pa_operation *o = userdata;
239 int eol = 1;
240
241 assert(pd);
242 assert(o);
243 assert(o->ref >= 1);
244
245 if (!o->context)
246 goto finish;
247
248 if (command != PA_COMMAND_REPLY) {
249 if (pa_context_handle_error(o->context, command, t) < 0)
250 goto finish;
251
252 eol = -1;
253 } else {
254
255 while (!pa_tagstruct_eof(t)) {
256 pa_source_info i;
257 uint32_t flags;
258
259 if (pa_tagstruct_getu32(t, &i.index) < 0 ||
260 pa_tagstruct_gets(t, &i.name) < 0 ||
261 pa_tagstruct_gets(t, &i.description) < 0 ||
262 pa_tagstruct_get_sample_spec(t, &i.sample_spec) < 0 ||
263 pa_tagstruct_get_channel_map(t, &i.channel_map) < 0 ||
264 pa_tagstruct_getu32(t, &i.owner_module) < 0 ||
265 pa_tagstruct_get_cvolume(t, &i.volume) < 0 ||
266 pa_tagstruct_get_boolean(t, &i.mute) < 0 ||
267 pa_tagstruct_getu32(t, &i.monitor_of_sink) < 0 ||
268 pa_tagstruct_gets(t, &i.monitor_of_sink_name) < 0 ||
269 pa_tagstruct_get_usec(t, &i.latency) < 0 ||
270 pa_tagstruct_gets(t, &i.driver) < 0 ||
271 pa_tagstruct_getu32(t, &flags) < 0) {
272
273 pa_context_fail(o->context, PA_ERR_PROTOCOL);
274 goto finish;
275 }
276
277 i.flags = (pa_source_flags_t) flags;
278
279 if (o->callback) {
280 pa_source_info_cb_t cb = (pa_source_info_cb_t) o->callback;
281 cb(o->context, &i, 0, o->userdata);
282 }
283 }
284 }
285
286 if (o->callback) {
287 pa_source_info_cb_t cb = (pa_source_info_cb_t) o->callback;
288 cb(o->context, NULL, eol, o->userdata);
289 }
290
291 finish:
292 pa_operation_done(o);
293 pa_operation_unref(o);
294 }
295
296 pa_operation* pa_context_get_source_info_list(pa_context *c, pa_source_info_cb_t cb, void *userdata) {
297 return pa_context_send_simple_command(c, PA_COMMAND_GET_SOURCE_INFO_LIST, context_get_source_info_callback, (pa_operation_cb_t) cb, userdata);
298 }
299
300 pa_operation* pa_context_get_source_info_by_index(pa_context *c, uint32_t idx, pa_source_info_cb_t cb, void *userdata) {
301 pa_tagstruct *t;
302 pa_operation *o;
303 uint32_t tag;
304
305 assert(c);
306 assert(c->ref >= 1);
307 assert(cb);
308
309 PA_CHECK_VALIDITY_RETURN_NULL(c, c->state == PA_CONTEXT_READY, PA_ERR_BADSTATE);
310
311 o = pa_operation_new(c, NULL, (pa_operation_cb_t) cb, userdata);
312
313 t = pa_tagstruct_command(c, PA_COMMAND_GET_SOURCE_INFO, &tag);
314 pa_tagstruct_putu32(t, idx);
315 pa_tagstruct_puts(t, NULL);
316 pa_pstream_send_tagstruct(c->pstream, t);
317 pa_pdispatch_register_reply(c->pdispatch, tag, DEFAULT_TIMEOUT, context_get_source_info_callback, pa_operation_ref(o), (pa_free_cb_t) pa_operation_unref);
318
319 return o;
320 }
321
322 pa_operation* pa_context_get_source_info_by_name(pa_context *c, const char *name, pa_source_info_cb_t cb, void *userdata) {
323 pa_tagstruct *t;
324 pa_operation *o;
325 uint32_t tag;
326
327 assert(c);
328 assert(c->ref >= 1);
329 assert(cb);
330
331 PA_CHECK_VALIDITY_RETURN_NULL(c, c->state == PA_CONTEXT_READY, PA_ERR_BADSTATE);
332 PA_CHECK_VALIDITY_RETURN_NULL(c, !name || *name, PA_ERR_INVALID);
333
334 o = pa_operation_new(c, NULL, (pa_operation_cb_t) cb, userdata);
335
336 t = pa_tagstruct_command(c, PA_COMMAND_GET_SOURCE_INFO, &tag);
337 pa_tagstruct_putu32(t, PA_INVALID_INDEX);
338 pa_tagstruct_puts(t, name);
339 pa_pstream_send_tagstruct(c->pstream, t);
340 pa_pdispatch_register_reply(c->pdispatch, tag, DEFAULT_TIMEOUT, context_get_source_info_callback, pa_operation_ref(o), (pa_free_cb_t) pa_operation_unref);
341
342 return o;
343 }
344
345 /*** Client info ***/
346
347 static void context_get_client_info_callback(pa_pdispatch *pd, uint32_t command, PA_GCC_UNUSED uint32_t tag, pa_tagstruct *t, void *userdata) {
348 pa_operation *o = userdata;
349 int eol = 1;
350
351 assert(pd);
352 assert(o);
353 assert(o->ref >= 1);
354
355 if (!o->context)
356 goto finish;
357
358 if (command != PA_COMMAND_REPLY) {
359 if (pa_context_handle_error(o->context, command, t) < 0)
360 goto finish;
361
362 eol = -1;
363 } else {
364
365 while (!pa_tagstruct_eof(t)) {
366 pa_client_info i;
367
368 if (pa_tagstruct_getu32(t, &i.index) < 0 ||
369 pa_tagstruct_gets(t, &i.name) < 0 ||
370 pa_tagstruct_getu32(t, &i.owner_module) < 0 ||
371 pa_tagstruct_gets(t, &i.driver) < 0 ) {
372 pa_context_fail(o->context, PA_ERR_PROTOCOL);
373 goto finish;
374 }
375
376 if (o->callback) {
377 pa_client_info_cb_t cb = (pa_client_info_cb_t) o->callback;
378 cb(o->context, &i, 0, o->userdata);
379 }
380 }
381 }
382
383 if (o->callback) {
384 pa_client_info_cb_t cb = (pa_client_info_cb_t) o->callback;
385 cb(o->context, NULL, eol, o->userdata);
386 }
387
388 finish:
389 pa_operation_done(o);
390 pa_operation_unref(o);
391 }
392
393 pa_operation* pa_context_get_client_info(pa_context *c, uint32_t idx, pa_client_info_cb_t cb, void *userdata) {
394 pa_tagstruct *t;
395 pa_operation *o;
396 uint32_t tag;
397
398 assert(c);
399 assert(c->ref >= 1);
400 assert(cb);
401
402 PA_CHECK_VALIDITY_RETURN_NULL(c, c->state == PA_CONTEXT_READY, PA_ERR_BADSTATE);
403 PA_CHECK_VALIDITY_RETURN_NULL(c, idx != PA_INVALID_INDEX, PA_ERR_INVALID);
404
405 o = pa_operation_new(c, NULL, (pa_operation_cb_t) cb, userdata);
406
407 t = pa_tagstruct_command(c, PA_COMMAND_GET_CLIENT_INFO, &tag);
408 pa_tagstruct_putu32(t, idx);
409 pa_pstream_send_tagstruct(c->pstream, t);
410 pa_pdispatch_register_reply(c->pdispatch, tag, DEFAULT_TIMEOUT, context_get_client_info_callback, pa_operation_ref(o), (pa_free_cb_t) pa_operation_unref);
411
412 return o;
413 }
414
415 pa_operation* pa_context_get_client_info_list(pa_context *c, pa_client_info_cb_t cb, void *userdata) {
416 return pa_context_send_simple_command(c, PA_COMMAND_GET_CLIENT_INFO_LIST, context_get_client_info_callback, (pa_operation_cb_t) cb, userdata);
417 }
418
419 /*** Module info ***/
420
421 static void context_get_module_info_callback(pa_pdispatch *pd, uint32_t command, PA_GCC_UNUSED uint32_t tag, pa_tagstruct *t, void *userdata) {
422 pa_operation *o = userdata;
423 int eol = 1;
424
425 assert(pd);
426 assert(o);
427 assert(o->ref >= 1);
428
429 if (!o->context)
430 goto finish;
431
432 if (command != PA_COMMAND_REPLY) {
433 if (pa_context_handle_error(o->context, command, t) < 0)
434 goto finish;
435
436 eol = -1;
437 } else {
438
439 while (!pa_tagstruct_eof(t)) {
440 pa_module_info i;
441
442 if (pa_tagstruct_getu32(t, &i.index) < 0 ||
443 pa_tagstruct_gets(t, &i.name) < 0 ||
444 pa_tagstruct_gets(t, &i.argument) < 0 ||
445 pa_tagstruct_getu32(t, &i.n_used) < 0 ||
446 pa_tagstruct_get_boolean(t, &i.auto_unload) < 0) {
447 pa_context_fail(o->context, PA_ERR_PROTOCOL);
448 goto finish;
449 }
450
451 if (o->callback) {
452 pa_module_info_cb_t cb = (pa_module_info_cb_t) o->callback;
453 cb(o->context, &i, 0, o->userdata);
454 }
455 }
456 }
457
458 if (o->callback) {
459 pa_module_info_cb_t cb = (pa_module_info_cb_t) o->callback;
460 cb(o->context, NULL, eol, o->userdata);
461 }
462
463 finish:
464 pa_operation_done(o);
465 pa_operation_unref(o);
466 }
467
468 pa_operation* pa_context_get_module_info(pa_context *c, uint32_t idx, pa_module_info_cb_t cb, void *userdata) {
469 pa_tagstruct *t;
470 pa_operation *o;
471 uint32_t tag;
472
473 assert(c);
474 assert(c->ref >= 1);
475 assert(cb);
476
477 PA_CHECK_VALIDITY_RETURN_NULL(c, c->state == PA_CONTEXT_READY, PA_ERR_BADSTATE);
478 PA_CHECK_VALIDITY_RETURN_NULL(c, idx != PA_INVALID_INDEX, PA_ERR_INVALID);
479
480 o = pa_operation_new(c, NULL, (pa_operation_cb_t) cb, userdata);
481
482 t = pa_tagstruct_command(c, PA_COMMAND_GET_MODULE_INFO, &tag);
483 pa_tagstruct_putu32(t, idx);
484 pa_pstream_send_tagstruct(c->pstream, t);
485 pa_pdispatch_register_reply(c->pdispatch, tag, DEFAULT_TIMEOUT, context_get_module_info_callback, pa_operation_ref(o), (pa_free_cb_t) pa_operation_unref);
486
487 return o;
488 }
489
490 pa_operation* pa_context_get_module_info_list(pa_context *c, pa_module_info_cb_t cb, void *userdata) {
491 return pa_context_send_simple_command(c, PA_COMMAND_GET_MODULE_INFO_LIST, context_get_module_info_callback, (pa_operation_cb_t) cb, userdata);
492 }
493
494 /*** Sink input info ***/
495
496 static void context_get_sink_input_info_callback(pa_pdispatch *pd, uint32_t command, PA_GCC_UNUSED uint32_t tag, pa_tagstruct *t, void *userdata) {
497 pa_operation *o = userdata;
498 int eol = 1;
499
500 assert(pd);
501 assert(o);
502 assert(o->ref >= 1);
503
504 if (!o->context)
505 goto finish;
506
507 if (command != PA_COMMAND_REPLY) {
508 if (pa_context_handle_error(o->context, command, t) < 0)
509 goto finish;
510
511 eol = -1;
512 } else {
513
514 while (!pa_tagstruct_eof(t)) {
515 pa_sink_input_info i;
516
517 if (pa_tagstruct_getu32(t, &i.index) < 0 ||
518 pa_tagstruct_gets(t, &i.name) < 0 ||
519 pa_tagstruct_getu32(t, &i.owner_module) < 0 ||
520 pa_tagstruct_getu32(t, &i.client) < 0 ||
521 pa_tagstruct_getu32(t, &i.sink) < 0 ||
522 pa_tagstruct_get_sample_spec(t, &i.sample_spec) < 0 ||
523 pa_tagstruct_get_channel_map(t, &i.channel_map) < 0 ||
524 pa_tagstruct_get_cvolume(t, &i.volume) < 0 ||
525 pa_tagstruct_get_usec(t, &i.buffer_usec) < 0 ||
526 pa_tagstruct_get_usec(t, &i.sink_usec) < 0 ||
527 pa_tagstruct_gets(t, &i.resample_method) < 0 ||
528 pa_tagstruct_gets(t, &i.driver) < 0) {
529
530 pa_context_fail(o->context, PA_ERR_PROTOCOL);
531 goto finish;
532 }
533
534 if (o->callback) {
535 pa_sink_input_info_cb_t cb = (pa_sink_input_info_cb_t) o->callback;
536 cb(o->context, &i, 0, o->userdata);
537 }
538 }
539 }
540
541 if (o->callback) {
542 pa_sink_input_info_cb_t cb = (pa_sink_input_info_cb_t) o->callback;
543 cb(o->context, NULL, eol, o->userdata);
544 }
545
546 finish:
547 pa_operation_done(o);
548 pa_operation_unref(o);
549 }
550
551 pa_operation* pa_context_get_sink_input_info(pa_context *c, uint32_t idx, pa_sink_input_info_cb_t cb, void *userdata) {
552 pa_tagstruct *t;
553 pa_operation *o;
554 uint32_t tag;
555
556 assert(c);
557 assert(c->ref >= 1);
558 assert(cb);
559
560 PA_CHECK_VALIDITY_RETURN_NULL(c, c->state == PA_CONTEXT_READY, PA_ERR_BADSTATE);
561 PA_CHECK_VALIDITY_RETURN_NULL(c, idx != PA_INVALID_INDEX, PA_ERR_INVALID);
562
563 o = pa_operation_new(c, NULL, (pa_operation_cb_t) cb, userdata);
564
565 t = pa_tagstruct_command(c, PA_COMMAND_GET_SINK_INPUT_INFO, &tag);
566 pa_tagstruct_putu32(t, idx);
567 pa_pstream_send_tagstruct(c->pstream, t);
568 pa_pdispatch_register_reply(c->pdispatch, tag, DEFAULT_TIMEOUT, context_get_sink_input_info_callback, pa_operation_ref(o), (pa_free_cb_t) pa_operation_unref);
569
570 return o;
571 }
572
573 pa_operation* pa_context_get_sink_input_info_list(pa_context *c, void (*cb)(pa_context *c, const pa_sink_input_info*i, int is_last, void *userdata), void *userdata) {
574 return pa_context_send_simple_command(c, PA_COMMAND_GET_SINK_INPUT_INFO_LIST, context_get_sink_input_info_callback, (pa_operation_cb_t) cb, userdata);
575 }
576
577 /*** Source output info ***/
578
579 static void context_get_source_output_info_callback(pa_pdispatch *pd, uint32_t command, PA_GCC_UNUSED uint32_t tag, pa_tagstruct *t, void *userdata) {
580 pa_operation *o = userdata;
581 int eol = 1;
582
583 assert(pd);
584 assert(o);
585 assert(o->ref >= 1);
586
587 if (!o->context)
588 goto finish;
589
590 if (command != PA_COMMAND_REPLY) {
591 if (pa_context_handle_error(o->context, command, t) < 0)
592 goto finish;
593
594 eol = -1;
595 } else {
596
597 while (!pa_tagstruct_eof(t)) {
598 pa_source_output_info i;
599
600 if (pa_tagstruct_getu32(t, &i.index) < 0 ||
601 pa_tagstruct_gets(t, &i.name) < 0 ||
602 pa_tagstruct_getu32(t, &i.owner_module) < 0 ||
603 pa_tagstruct_getu32(t, &i.client) < 0 ||
604 pa_tagstruct_getu32(t, &i.source) < 0 ||
605 pa_tagstruct_get_sample_spec(t, &i.sample_spec) < 0 ||
606 pa_tagstruct_get_channel_map(t, &i.channel_map) < 0 ||
607 pa_tagstruct_get_usec(t, &i.buffer_usec) < 0 ||
608 pa_tagstruct_get_usec(t, &i.source_usec) < 0 ||
609 pa_tagstruct_gets(t, &i.resample_method) < 0 ||
610 pa_tagstruct_gets(t, &i.driver) < 0) {
611
612 pa_context_fail(o->context, PA_ERR_PROTOCOL);
613 goto finish;
614 }
615
616 if (o->callback) {
617 pa_source_output_info_cb_t cb = (pa_source_output_info_cb_t) o->callback;
618 cb(o->context, &i, 0, o->userdata);
619 }
620 }
621 }
622
623 if (o->callback) {
624 pa_source_output_info_cb_t cb = (pa_source_output_info_cb_t) o->callback;
625 cb(o->context, NULL, eol, o->userdata);
626 }
627
628 finish:
629 pa_operation_done(o);
630 pa_operation_unref(o);
631 }
632
633 pa_operation* pa_context_get_source_output_info(pa_context *c, uint32_t idx, pa_source_output_info_cb_t cb, void *userdata) {
634 pa_tagstruct *t;
635 pa_operation *o;
636 uint32_t tag;
637
638 assert(c);
639 assert(c->ref >= 1);
640 assert(cb);
641
642 PA_CHECK_VALIDITY_RETURN_NULL(c, c->state == PA_CONTEXT_READY, PA_ERR_BADSTATE);
643 PA_CHECK_VALIDITY_RETURN_NULL(c, idx != PA_INVALID_INDEX, PA_ERR_INVALID);
644
645 o = pa_operation_new(c, NULL, (pa_operation_cb_t) cb, userdata);
646
647 t = pa_tagstruct_command(c, PA_COMMAND_GET_SOURCE_OUTPUT_INFO, &tag);
648 pa_tagstruct_putu32(t, idx);
649 pa_pstream_send_tagstruct(c->pstream, t);
650 pa_pdispatch_register_reply(c->pdispatch, tag, DEFAULT_TIMEOUT, context_get_source_output_info_callback, pa_operation_ref(o), (pa_free_cb_t) pa_operation_unref);
651
652 return o;
653 }
654
655 pa_operation* pa_context_get_source_output_info_list(pa_context *c, pa_source_output_info_cb_t cb, void *userdata) {
656 return pa_context_send_simple_command(c, PA_COMMAND_GET_SOURCE_OUTPUT_INFO_LIST, context_get_source_output_info_callback, (pa_operation_cb_t) cb, userdata);
657 }
658
659 /*** Volume manipulation ***/
660
661 pa_operation* pa_context_set_sink_volume_by_index(pa_context *c, uint32_t idx, const pa_cvolume *volume, pa_context_success_cb_t cb, void *userdata) {
662 pa_operation *o;
663 pa_tagstruct *t;
664 uint32_t tag;
665
666 assert(c);
667 assert(c->ref >= 1);
668 assert(volume);
669
670 PA_CHECK_VALIDITY_RETURN_NULL(c, c->state == PA_CONTEXT_READY, PA_ERR_BADSTATE);
671 PA_CHECK_VALIDITY_RETURN_NULL(c, pa_cvolume_valid(volume), PA_ERR_INVALID);
672
673 o = pa_operation_new(c, NULL, (pa_operation_cb_t) cb, userdata);
674
675 t = pa_tagstruct_command(c, PA_COMMAND_SET_SINK_VOLUME, &tag);
676 pa_tagstruct_putu32(t, idx);
677 pa_tagstruct_puts(t, NULL);
678 pa_tagstruct_put_cvolume(t, volume);
679 pa_pstream_send_tagstruct(c->pstream, t);
680 pa_pdispatch_register_reply(c->pdispatch, tag, DEFAULT_TIMEOUT, pa_context_simple_ack_callback, pa_operation_ref(o), (pa_free_cb_t) pa_operation_unref);
681
682 return o;
683 }
684
685 pa_operation* pa_context_set_sink_volume_by_name(pa_context *c, const char *name, const pa_cvolume *volume, pa_context_success_cb_t cb, void *userdata) {
686 pa_operation *o;
687 pa_tagstruct *t;
688 uint32_t tag;
689
690 assert(c);
691 assert(c->ref >= 1);
692 assert(name);
693 assert(volume);
694
695 PA_CHECK_VALIDITY_RETURN_NULL(c, c->state == PA_CONTEXT_READY, PA_ERR_BADSTATE);
696 PA_CHECK_VALIDITY_RETURN_NULL(c, pa_cvolume_valid(volume), PA_ERR_INVALID);
697 PA_CHECK_VALIDITY_RETURN_NULL(c, !name || *name, PA_ERR_INVALID);
698
699 o = pa_operation_new(c, NULL, (pa_operation_cb_t) cb, userdata);
700
701 t = pa_tagstruct_command(c, PA_COMMAND_SET_SINK_VOLUME, &tag);
702 pa_tagstruct_putu32(t, PA_INVALID_INDEX);
703 pa_tagstruct_puts(t, name);
704 pa_tagstruct_put_cvolume(t, volume);
705 pa_pstream_send_tagstruct(c->pstream, t);
706 pa_pdispatch_register_reply(c->pdispatch, tag, DEFAULT_TIMEOUT, pa_context_simple_ack_callback, pa_operation_ref(o), (pa_free_cb_t) pa_operation_unref);
707
708 return o;
709 }
710
711 pa_operation* pa_context_set_sink_mute_by_index(pa_context *c, uint32_t idx, int mute, pa_context_success_cb_t cb, void *userdata) {
712 pa_operation *o;
713 pa_tagstruct *t;
714 uint32_t tag;
715
716 assert(c);
717 assert(c->ref >= 1);
718
719 PA_CHECK_VALIDITY_RETURN_NULL(c, c->state == PA_CONTEXT_READY, PA_ERR_BADSTATE);
720
721 o = pa_operation_new(c, NULL, (pa_operation_cb_t) cb, userdata);
722
723 t = pa_tagstruct_command(c, PA_COMMAND_SET_SINK_MUTE, &tag);
724 pa_tagstruct_putu32(t, idx);
725 pa_tagstruct_puts(t, NULL);
726 pa_tagstruct_put_boolean(t, mute);
727 pa_pstream_send_tagstruct(c->pstream, t);
728 pa_pdispatch_register_reply(c->pdispatch, tag, DEFAULT_TIMEOUT, pa_context_simple_ack_callback, pa_operation_ref(o), (pa_free_cb_t) pa_operation_unref);
729
730 return o;
731 }
732
733 pa_operation* pa_context_set_sink_mute_by_name(pa_context *c, const char *name, int mute, pa_context_success_cb_t cb, void *userdata) {
734 pa_operation *o;
735 pa_tagstruct *t;
736 uint32_t tag;
737
738 assert(c);
739 assert(c->ref >= 1);
740 assert(name);
741
742 PA_CHECK_VALIDITY_RETURN_NULL(c, c->state == PA_CONTEXT_READY, PA_ERR_BADSTATE);
743 PA_CHECK_VALIDITY_RETURN_NULL(c, !name || *name, PA_ERR_INVALID);
744
745 o = pa_operation_new(c, NULL, (pa_operation_cb_t) cb, userdata);
746
747 t = pa_tagstruct_command(c, PA_COMMAND_SET_SINK_MUTE, &tag);
748 pa_tagstruct_putu32(t, PA_INVALID_INDEX);
749 pa_tagstruct_puts(t, name);
750 pa_tagstruct_put_boolean(t, mute);
751 pa_pstream_send_tagstruct(c->pstream, t);
752 pa_pdispatch_register_reply(c->pdispatch, tag, DEFAULT_TIMEOUT, pa_context_simple_ack_callback, pa_operation_ref(o), (pa_free_cb_t) pa_operation_unref);
753
754 return o;
755 }
756
757 pa_operation* pa_context_set_sink_input_volume(pa_context *c, uint32_t idx, const pa_cvolume *volume, pa_context_success_cb_t cb, void *userdata) {
758 pa_operation *o;
759 pa_tagstruct *t;
760 uint32_t tag;
761
762 assert(c);
763 assert(c->ref >= 1);
764 assert(volume);
765
766 PA_CHECK_VALIDITY_RETURN_NULL(c, c->state == PA_CONTEXT_READY, PA_ERR_BADSTATE);
767 PA_CHECK_VALIDITY_RETURN_NULL(c, idx != PA_INVALID_INDEX, PA_ERR_INVALID);
768 PA_CHECK_VALIDITY_RETURN_NULL(c, pa_cvolume_valid(volume), PA_ERR_INVALID);
769
770 o = pa_operation_new(c, NULL, (pa_operation_cb_t) cb, userdata);
771
772 t = pa_tagstruct_command(c, PA_COMMAND_SET_SINK_INPUT_VOLUME, &tag);
773 pa_tagstruct_putu32(t, idx);
774 pa_tagstruct_put_cvolume(t, volume);
775 pa_pstream_send_tagstruct(c->pstream, t);
776 pa_pdispatch_register_reply(c->pdispatch, tag, DEFAULT_TIMEOUT, pa_context_simple_ack_callback, pa_operation_ref(o), (pa_free_cb_t) pa_operation_unref);
777
778 return o;
779 }
780
781 pa_operation* pa_context_set_source_volume_by_index(pa_context *c, uint32_t idx, const pa_cvolume *volume, pa_context_success_cb_t cb, void *userdata) {
782 pa_operation *o;
783 pa_tagstruct *t;
784 uint32_t tag;
785
786 assert(c);
787 assert(c->ref >= 1);
788 assert(volume);
789
790 PA_CHECK_VALIDITY_RETURN_NULL(c, c->state == PA_CONTEXT_READY, PA_ERR_BADSTATE);
791 PA_CHECK_VALIDITY_RETURN_NULL(c, pa_cvolume_valid(volume), PA_ERR_INVALID);
792
793 o = pa_operation_new(c, NULL, (pa_operation_cb_t) cb, userdata);
794
795 t = pa_tagstruct_command(c, PA_COMMAND_SET_SOURCE_VOLUME, &tag);
796 pa_tagstruct_putu32(t, idx);
797 pa_tagstruct_puts(t, NULL);
798 pa_tagstruct_put_cvolume(t, volume);
799 pa_pstream_send_tagstruct(c->pstream, t);
800 pa_pdispatch_register_reply(c->pdispatch, tag, DEFAULT_TIMEOUT, pa_context_simple_ack_callback, pa_operation_ref(o), (pa_free_cb_t) pa_operation_unref);
801
802 return o;
803 }
804
805 pa_operation* pa_context_set_source_volume_by_name(pa_context *c, const char *name, const pa_cvolume *volume, pa_context_success_cb_t cb, void *userdata) {
806 pa_operation *o;
807 pa_tagstruct *t;
808 uint32_t tag;
809
810 assert(c);
811 assert(c->ref >= 1);
812 assert(name);
813 assert(volume);
814
815 PA_CHECK_VALIDITY_RETURN_NULL(c, c->state == PA_CONTEXT_READY, PA_ERR_BADSTATE);
816 PA_CHECK_VALIDITY_RETURN_NULL(c, pa_cvolume_valid(volume), PA_ERR_INVALID);
817 PA_CHECK_VALIDITY_RETURN_NULL(c, !name || *name, PA_ERR_INVALID);
818
819 o = pa_operation_new(c, NULL, (pa_operation_cb_t) cb, userdata);
820
821 t = pa_tagstruct_command(c, PA_COMMAND_SET_SOURCE_VOLUME, &tag);
822 pa_tagstruct_putu32(t, PA_INVALID_INDEX);
823 pa_tagstruct_puts(t, name);
824 pa_tagstruct_put_cvolume(t, volume);
825 pa_pstream_send_tagstruct(c->pstream, t);
826 pa_pdispatch_register_reply(c->pdispatch, tag, DEFAULT_TIMEOUT, pa_context_simple_ack_callback, pa_operation_ref(o), (pa_free_cb_t) pa_operation_unref);
827
828 return o;
829 }
830
831 pa_operation* pa_context_set_source_mute_by_index(pa_context *c, uint32_t idx, int mute, pa_context_success_cb_t cb, void *userdata) {
832 pa_operation *o;
833 pa_tagstruct *t;
834 uint32_t tag;
835
836 assert(c);
837 assert(c->ref >= 1);
838
839 PA_CHECK_VALIDITY_RETURN_NULL(c, c->state == PA_CONTEXT_READY, PA_ERR_BADSTATE);
840
841 o = pa_operation_new(c, NULL, (pa_operation_cb_t) cb, userdata);
842
843 t = pa_tagstruct_command(c, PA_COMMAND_SET_SOURCE_MUTE, &tag);
844 pa_tagstruct_putu32(t, idx);
845 pa_tagstruct_puts(t, NULL);
846 pa_tagstruct_put_boolean(t, mute);
847 pa_pstream_send_tagstruct(c->pstream, t);
848 pa_pdispatch_register_reply(c->pdispatch, tag, DEFAULT_TIMEOUT, pa_context_simple_ack_callback, pa_operation_ref(o), (pa_free_cb_t) pa_operation_unref);
849
850 return o;
851 }
852
853 pa_operation* pa_context_set_source_mute_by_name(pa_context *c, const char *name, int mute, pa_context_success_cb_t cb, void *userdata) {
854 pa_operation *o;
855 pa_tagstruct *t;
856 uint32_t tag;
857
858 assert(c);
859 assert(c->ref >= 1);
860 assert(name);
861
862 PA_CHECK_VALIDITY_RETURN_NULL(c, c->state == PA_CONTEXT_READY, PA_ERR_BADSTATE);
863 PA_CHECK_VALIDITY_RETURN_NULL(c, !name || *name, PA_ERR_INVALID);
864
865 o = pa_operation_new(c, NULL, (pa_operation_cb_t) cb, userdata);
866
867 t = pa_tagstruct_command(c, PA_COMMAND_SET_SOURCE_MUTE, &tag);
868 pa_tagstruct_putu32(t, PA_INVALID_INDEX);
869 pa_tagstruct_puts(t, name);
870 pa_tagstruct_put_boolean(t, mute);
871 pa_pstream_send_tagstruct(c->pstream, t);
872 pa_pdispatch_register_reply(c->pdispatch, tag, DEFAULT_TIMEOUT, pa_context_simple_ack_callback, pa_operation_ref(o), (pa_free_cb_t) pa_operation_unref);
873
874 return o;
875 }
876
877 /** Sample Cache **/
878
879 static void context_get_sample_info_callback(pa_pdispatch *pd, uint32_t command, PA_GCC_UNUSED uint32_t tag, pa_tagstruct *t, void *userdata) {
880 pa_operation *o = userdata;
881 int eol = 1;
882
883 assert(pd);
884 assert(o);
885 assert(o->ref >= 1);
886
887 if (!o->context)
888 goto finish;
889
890 if (command != PA_COMMAND_REPLY) {
891 if (pa_context_handle_error(o->context, command, t) < 0)
892 goto finish;
893
894 eol = -1;
895 } else {
896
897 while (!pa_tagstruct_eof(t)) {
898 pa_sample_info i;
899
900 if (pa_tagstruct_getu32(t, &i.index) < 0 ||
901 pa_tagstruct_gets(t, &i.name) < 0 ||
902 pa_tagstruct_get_cvolume(t, &i.volume) < 0 ||
903 pa_tagstruct_get_usec(t, &i.duration) < 0 ||
904 pa_tagstruct_get_sample_spec(t, &i.sample_spec) < 0 ||
905 pa_tagstruct_get_channel_map(t, &i.channel_map) < 0 ||
906 pa_tagstruct_getu32(t, &i.bytes) < 0 ||
907 pa_tagstruct_get_boolean(t, &i.lazy) < 0 ||
908 pa_tagstruct_gets(t, &i.filename) < 0) {
909
910 pa_context_fail(o->context, PA_ERR_PROTOCOL);
911 goto finish;
912 }
913
914 if (o->callback) {
915 pa_sample_info_cb_t cb = (pa_sample_info_cb_t) o->callback;
916 cb(o->context, &i, 0, o->userdata);
917 }
918 }
919 }
920
921 if (o->callback) {
922 pa_sample_info_cb_t cb = (pa_sample_info_cb_t) o->callback;
923 cb(o->context, NULL, eol, o->userdata);
924 }
925
926 finish:
927 pa_operation_done(o);
928 pa_operation_unref(o);
929 }
930
931 pa_operation* pa_context_get_sample_info_by_name(pa_context *c, const char *name, pa_sample_info_cb_t cb, void *userdata) {
932 pa_tagstruct *t;
933 pa_operation *o;
934 uint32_t tag;
935
936 assert(c);
937 assert(c->ref >= 1);
938 assert(cb);
939
940 PA_CHECK_VALIDITY_RETURN_NULL(c, c->state == PA_CONTEXT_READY, PA_ERR_BADSTATE);
941 PA_CHECK_VALIDITY_RETURN_NULL(c, name && *name, PA_ERR_INVALID);
942
943 o = pa_operation_new(c, NULL, (pa_operation_cb_t) cb, userdata);
944
945 t = pa_tagstruct_command(c, PA_COMMAND_GET_SAMPLE_INFO, &tag);
946 pa_tagstruct_putu32(t, PA_INVALID_INDEX);
947 pa_tagstruct_puts(t, name);
948 pa_pstream_send_tagstruct(c->pstream, t);
949 pa_pdispatch_register_reply(c->pdispatch, tag, DEFAULT_TIMEOUT, context_get_sample_info_callback, pa_operation_ref(o), (pa_free_cb_t) pa_operation_unref);
950
951 return o;
952 }
953
954 pa_operation* pa_context_get_sample_info_by_index(pa_context *c, uint32_t idx, pa_sample_info_cb_t cb, void *userdata) {
955 pa_tagstruct *t;
956 pa_operation *o;
957 uint32_t tag;
958
959 assert(c);
960 assert(c->ref >= 1);
961 assert(cb);
962
963 PA_CHECK_VALIDITY_RETURN_NULL(c, c->state == PA_CONTEXT_READY, PA_ERR_BADSTATE);
964 PA_CHECK_VALIDITY_RETURN_NULL(c, idx != PA_INVALID_INDEX, PA_ERR_INVALID);
965
966 o = pa_operation_new(c, NULL, (pa_operation_cb_t) cb, userdata);
967
968 t = pa_tagstruct_command(c, PA_COMMAND_GET_SAMPLE_INFO, &tag);
969 pa_tagstruct_putu32(t, idx);
970 pa_tagstruct_puts(t, NULL);
971 pa_pstream_send_tagstruct(c->pstream, t);
972 pa_pdispatch_register_reply(c->pdispatch, tag, DEFAULT_TIMEOUT, context_get_sample_info_callback, pa_operation_ref(o), (pa_free_cb_t) pa_operation_unref);
973
974 return o;
975 }
976
977 pa_operation* pa_context_get_sample_info_list(pa_context *c, pa_sample_info_cb_t cb, void *userdata) {
978 return pa_context_send_simple_command(c, PA_COMMAND_GET_SAMPLE_INFO_LIST, context_get_sample_info_callback, (pa_operation_cb_t) cb, userdata);
979 }
980
981 static pa_operation* command_kill(pa_context *c, uint32_t command, uint32_t idx, pa_context_success_cb_t cb, void *userdata) {
982 pa_operation *o;
983 pa_tagstruct *t;
984 uint32_t tag;
985
986 assert(c);
987 assert(c->ref >= 1);
988
989 PA_CHECK_VALIDITY_RETURN_NULL(c, c->state == PA_CONTEXT_READY, PA_ERR_BADSTATE);
990 PA_CHECK_VALIDITY_RETURN_NULL(c, idx != PA_INVALID_INDEX, PA_ERR_INVALID);
991
992 o = pa_operation_new(c, NULL, (pa_operation_cb_t) cb, userdata);
993
994 t = pa_tagstruct_command(c, command, &tag);
995 pa_tagstruct_putu32(t, idx);
996 pa_pstream_send_tagstruct(c->pstream, t);
997 pa_pdispatch_register_reply(c->pdispatch, tag, DEFAULT_TIMEOUT, pa_context_simple_ack_callback, pa_operation_ref(o), (pa_free_cb_t) pa_operation_unref);
998
999 return o;
1000 }
1001
1002 pa_operation* pa_context_kill_client(pa_context *c, uint32_t idx, pa_context_success_cb_t cb, void *userdata) {
1003 return command_kill(c, PA_COMMAND_KILL_CLIENT, idx, cb, userdata);
1004 }
1005
1006 pa_operation* pa_context_kill_sink_input(pa_context *c, uint32_t idx, pa_context_success_cb_t cb, void *userdata) {
1007 return command_kill(c, PA_COMMAND_KILL_SINK_INPUT, idx, cb, userdata);
1008 }
1009
1010 pa_operation* pa_context_kill_source_output(pa_context *c, uint32_t idx, pa_context_success_cb_t cb, void *userdata) {
1011 return command_kill(c, PA_COMMAND_KILL_SOURCE_OUTPUT, idx, cb, userdata);
1012 }
1013
1014 static void context_index_callback(pa_pdispatch *pd, uint32_t command, PA_GCC_UNUSED uint32_t tag, pa_tagstruct *t, void *userdata) {
1015 pa_operation *o = userdata;
1016 uint32_t idx;
1017
1018 assert(pd);
1019 assert(o);
1020 assert(o->ref >= 1);
1021
1022 if (!o->context)
1023 goto finish;
1024
1025 if (command != PA_COMMAND_REPLY) {
1026 if (pa_context_handle_error(o->context, command, t) < 0)
1027 goto finish;
1028
1029 idx = PA_INVALID_INDEX;
1030 } else if (pa_tagstruct_getu32(t, &idx) ||
1031 !pa_tagstruct_eof(t)) {
1032 pa_context_fail(o->context, PA_ERR_PROTOCOL);
1033 goto finish;
1034 }
1035
1036 if (o->callback) {
1037 pa_context_index_cb_t cb = (pa_context_index_cb_t) o->callback;
1038 cb(o->context, idx, o->userdata);
1039 }
1040
1041
1042 finish:
1043 pa_operation_done(o);
1044 pa_operation_unref(o);
1045 }
1046
1047 pa_operation* pa_context_load_module(pa_context *c, const char*name, const char *argument, pa_context_index_cb_t cb, void *userdata) {
1048 pa_operation *o;
1049 pa_tagstruct *t;
1050 uint32_t tag;
1051
1052 assert(c);
1053 assert(c->ref >= 1);
1054
1055 PA_CHECK_VALIDITY_RETURN_NULL(c, c->state == PA_CONTEXT_READY, PA_ERR_BADSTATE);
1056 PA_CHECK_VALIDITY_RETURN_NULL(c, name && *name, PA_ERR_INVALID);
1057
1058 o = pa_operation_new(c, NULL, (pa_operation_cb_t) cb, userdata);
1059
1060 t = pa_tagstruct_command(c, PA_COMMAND_LOAD_MODULE, &tag);
1061 pa_tagstruct_puts(t, name);
1062 pa_tagstruct_puts(t, argument);
1063 pa_pstream_send_tagstruct(c->pstream, t);
1064 pa_pdispatch_register_reply(c->pdispatch, tag, DEFAULT_TIMEOUT, context_index_callback, pa_operation_ref(o), (pa_free_cb_t) pa_operation_unref);
1065
1066 return o;
1067 }
1068
1069 pa_operation* pa_context_unload_module(pa_context *c, uint32_t idx, pa_context_success_cb_t cb, void *userdata) {
1070 return command_kill(c, PA_COMMAND_UNLOAD_MODULE, idx, cb, userdata);
1071 }
1072
1073 /*** Autoload stuff ***/
1074
1075 static void context_get_autoload_info_callback(pa_pdispatch *pd, uint32_t command, PA_GCC_UNUSED uint32_t tag, pa_tagstruct *t, void *userdata) {
1076 pa_operation *o = userdata;
1077 int eol = 1;
1078
1079 assert(pd);
1080 assert(o);
1081 assert(o->ref >= 1);
1082
1083 if (!o->context)
1084 goto finish;
1085
1086 if (command != PA_COMMAND_REPLY) {
1087 if (pa_context_handle_error(o->context, command, t) < 0)
1088 goto finish;
1089
1090 eol = -1;
1091 } else {
1092
1093 while (!pa_tagstruct_eof(t)) {
1094 pa_autoload_info i;
1095
1096 if (pa_tagstruct_getu32(t, &i.index) < 0 ||
1097 pa_tagstruct_gets(t, &i.name) < 0 ||
1098 pa_tagstruct_getu32(t, &i.type) < 0 ||
1099 pa_tagstruct_gets(t, &i.module) < 0 ||
1100 pa_tagstruct_gets(t, &i.argument) < 0) {
1101 pa_context_fail(o->context, PA_ERR_PROTOCOL);
1102 goto finish;
1103 }
1104
1105 if (o->callback) {
1106 pa_autoload_info_cb_t cb = (pa_autoload_info_cb_t) o->callback;
1107 cb(o->context, &i, 0, o->userdata);
1108 }
1109 }
1110 }
1111
1112 if (o->callback) {
1113 pa_autoload_info_cb_t cb = (pa_autoload_info_cb_t) o->callback;
1114 cb(o->context, NULL, eol, o->userdata);
1115 }
1116
1117 finish:
1118 pa_operation_done(o);
1119 pa_operation_unref(o);
1120 }
1121
1122 pa_operation* pa_context_get_autoload_info_by_name(pa_context *c, const char *name, pa_autoload_type_t type, pa_autoload_info_cb_t cb, void *userdata) {
1123 pa_tagstruct *t;
1124 pa_operation *o;
1125 uint32_t tag;
1126
1127 assert(c);
1128 assert(c->ref >= 1);
1129 assert(cb);
1130
1131 PA_CHECK_VALIDITY_RETURN_NULL(c, c->state == PA_CONTEXT_READY, PA_ERR_BADSTATE);
1132 PA_CHECK_VALIDITY_RETURN_NULL(c, name && *name, PA_ERR_INVALID);
1133 PA_CHECK_VALIDITY_RETURN_NULL(c, type == PA_AUTOLOAD_SINK || type == PA_AUTOLOAD_SOURCE, PA_ERR_INVALID);
1134
1135 o = pa_operation_new(c, NULL, (pa_operation_cb_t) cb, userdata);
1136
1137 t = pa_tagstruct_command(c, PA_COMMAND_GET_AUTOLOAD_INFO, &tag);
1138 pa_tagstruct_puts(t, name);
1139 pa_tagstruct_putu32(t, type);
1140 pa_pstream_send_tagstruct(c->pstream, t);
1141 pa_pdispatch_register_reply(c->pdispatch, tag, DEFAULT_TIMEOUT, context_get_autoload_info_callback, pa_operation_ref(o), (pa_free_cb_t) pa_operation_unref);
1142
1143 return o;
1144 }
1145
1146 pa_operation* pa_context_get_autoload_info_by_index(pa_context *c, uint32_t idx, pa_autoload_info_cb_t cb, void *userdata) {
1147 pa_tagstruct *t;
1148 pa_operation *o;
1149 uint32_t tag;
1150
1151 assert(c);
1152 assert(c->ref >= 1);
1153 assert(cb);
1154
1155 PA_CHECK_VALIDITY_RETURN_NULL(c, c->state == PA_CONTEXT_READY, PA_ERR_BADSTATE);
1156 PA_CHECK_VALIDITY_RETURN_NULL(c, idx != PA_INVALID_INDEX, PA_ERR_INVALID);
1157
1158 o = pa_operation_new(c, NULL, (pa_operation_cb_t) cb, userdata);
1159
1160 t = pa_tagstruct_command(c, PA_COMMAND_GET_AUTOLOAD_INFO, &tag);
1161 pa_tagstruct_putu32(t, idx);
1162 pa_pstream_send_tagstruct(c->pstream, t);
1163 pa_pdispatch_register_reply(c->pdispatch, tag, DEFAULT_TIMEOUT, context_get_autoload_info_callback, pa_operation_ref(o), (pa_free_cb_t) pa_operation_unref);
1164
1165 return o;
1166 }
1167
1168 pa_operation* pa_context_get_autoload_info_list(pa_context *c, pa_autoload_info_cb_t cb, void *userdata) {
1169 return pa_context_send_simple_command(c, PA_COMMAND_GET_AUTOLOAD_INFO_LIST, context_get_autoload_info_callback, (pa_operation_cb_t) cb, userdata);
1170 }
1171
1172 pa_operation* pa_context_add_autoload(pa_context *c, const char *name, pa_autoload_type_t type, const char *module, const char*argument, pa_context_index_cb_t cb, void* userdata) {
1173 pa_operation *o;
1174 pa_tagstruct *t;
1175 uint32_t tag;
1176
1177 assert(c);
1178 assert(c->ref >= 1);
1179
1180 PA_CHECK_VALIDITY_RETURN_NULL(c, c->state == PA_CONTEXT_READY, PA_ERR_BADSTATE);
1181 PA_CHECK_VALIDITY_RETURN_NULL(c, name && *name, PA_ERR_INVALID);
1182 PA_CHECK_VALIDITY_RETURN_NULL(c, type == PA_AUTOLOAD_SINK || type == PA_AUTOLOAD_SOURCE, PA_ERR_INVALID);
1183 PA_CHECK_VALIDITY_RETURN_NULL(c, module && *module, PA_ERR_INVALID);
1184
1185 o = pa_operation_new(c, NULL, (pa_operation_cb_t) cb, userdata);
1186
1187 t = pa_tagstruct_command(c, PA_COMMAND_ADD_AUTOLOAD, &tag);
1188 pa_tagstruct_puts(t, name);
1189 pa_tagstruct_putu32(t, type);
1190 pa_tagstruct_puts(t, module);
1191 pa_tagstruct_puts(t, argument);
1192 pa_pstream_send_tagstruct(c->pstream, t);
1193 pa_pdispatch_register_reply(c->pdispatch, tag, DEFAULT_TIMEOUT, context_index_callback, pa_operation_ref(o), (pa_free_cb_t) pa_operation_unref);
1194
1195 return o;
1196 }
1197
1198 pa_operation* pa_context_remove_autoload_by_name(pa_context *c, const char *name, pa_autoload_type_t type, pa_context_success_cb_t cb, void* userdata) {
1199 pa_operation *o;
1200 pa_tagstruct *t;
1201 uint32_t tag;
1202
1203 assert(c);
1204 assert(c->ref >= 1);
1205
1206 PA_CHECK_VALIDITY_RETURN_NULL(c, c->state == PA_CONTEXT_READY, PA_ERR_BADSTATE);
1207 PA_CHECK_VALIDITY_RETURN_NULL(c, name && *name, PA_ERR_INVALID);
1208 PA_CHECK_VALIDITY_RETURN_NULL(c, type == PA_AUTOLOAD_SINK || type == PA_AUTOLOAD_SOURCE, PA_ERR_INVALID);
1209
1210 o = pa_operation_new(c, NULL, (pa_operation_cb_t) cb, userdata);
1211
1212 t = pa_tagstruct_command(c, PA_COMMAND_REMOVE_AUTOLOAD, &tag);
1213 pa_tagstruct_puts(t, name);
1214 pa_tagstruct_putu32(t, type);
1215 pa_pstream_send_tagstruct(c->pstream, t);
1216 pa_pdispatch_register_reply(c->pdispatch, tag, DEFAULT_TIMEOUT, pa_context_simple_ack_callback, pa_operation_ref(o), (pa_free_cb_t) pa_operation_unref);
1217
1218 return o;
1219 }
1220
1221 pa_operation* pa_context_remove_autoload_by_index(pa_context *c, uint32_t idx, pa_context_success_cb_t cb, void* userdata) {
1222 pa_operation *o;
1223 pa_tagstruct *t;
1224 uint32_t tag;
1225
1226 assert(c);
1227 assert(c->ref >= 1);
1228
1229 PA_CHECK_VALIDITY_RETURN_NULL(c, c->state == PA_CONTEXT_READY, PA_ERR_BADSTATE);
1230 PA_CHECK_VALIDITY_RETURN_NULL(c, idx != PA_INVALID_INDEX, PA_ERR_INVALID);
1231
1232 o = pa_operation_new(c, NULL, (pa_operation_cb_t) cb, userdata);
1233
1234 t = pa_tagstruct_command(c, PA_COMMAND_REMOVE_AUTOLOAD, &tag);
1235 pa_tagstruct_putu32(t, idx);
1236 pa_pstream_send_tagstruct(c->pstream, t);
1237 pa_pdispatch_register_reply(c->pdispatch, tag, DEFAULT_TIMEOUT, pa_context_simple_ack_callback, pa_operation_ref(o), (pa_free_cb_t) pa_operation_unref);
1238
1239 return o;
1240 }
1241
1242 pa_operation* pa_context_move_sink_input_by_name(pa_context *c, uint32_t idx, char *sink_name, pa_context_success_cb_t cb, void* userdata) {
1243 pa_operation *o;
1244 pa_tagstruct *t;
1245 uint32_t tag;
1246
1247 assert(c);
1248 assert(c->ref >= 1);
1249
1250 PA_CHECK_VALIDITY_RETURN_NULL(c, c->state == PA_CONTEXT_READY, PA_ERR_BADSTATE);
1251 PA_CHECK_VALIDITY_RETURN_NULL(c, c->version >= 10, PA_ERR_NOTSUPPORTED);
1252 PA_CHECK_VALIDITY_RETURN_NULL(c, idx != PA_INVALID_INDEX, PA_ERR_INVALID);
1253 PA_CHECK_VALIDITY_RETURN_NULL(c, sink_name && *sink_name, PA_ERR_INVALID);
1254
1255 o = pa_operation_new(c, NULL, (pa_operation_cb_t) cb, userdata);
1256
1257 t = pa_tagstruct_command(c, PA_COMMAND_MOVE_SINK_INPUT, &tag);
1258 pa_tagstruct_putu32(t, idx);
1259 pa_tagstruct_putu32(t, PA_INVALID_INDEX);
1260 pa_tagstruct_puts(t, sink_name);
1261 pa_pstream_send_tagstruct(c->pstream, t);
1262 pa_pdispatch_register_reply(c->pdispatch, tag, DEFAULT_TIMEOUT, pa_context_simple_ack_callback, pa_operation_ref(o), (pa_free_cb_t) pa_operation_unref);
1263
1264 return o;
1265 }
1266
1267 pa_operation* pa_context_move_sink_input_by_index(pa_context *c, uint32_t idx, uint32_t sink_idx, pa_context_success_cb_t cb, void* userdata) {
1268 pa_operation *o;
1269 pa_tagstruct *t;
1270 uint32_t tag;
1271
1272 assert(c);
1273 assert(c->ref >= 1);
1274
1275 PA_CHECK_VALIDITY_RETURN_NULL(c, c->state == PA_CONTEXT_READY, PA_ERR_BADSTATE);
1276 PA_CHECK_VALIDITY_RETURN_NULL(c, c->version >= 10, PA_ERR_NOTSUPPORTED);
1277 PA_CHECK_VALIDITY_RETURN_NULL(c, idx != PA_INVALID_INDEX, PA_ERR_INVALID);
1278 PA_CHECK_VALIDITY_RETURN_NULL(c, sink_idx != PA_INVALID_INDEX, PA_ERR_INVALID);
1279
1280 o = pa_operation_new(c, NULL, (pa_operation_cb_t) cb, userdata);
1281
1282 t = pa_tagstruct_command(c, PA_COMMAND_MOVE_SINK_INPUT, &tag);
1283 pa_tagstruct_putu32(t, idx);
1284 pa_tagstruct_putu32(t, sink_idx);
1285 pa_tagstruct_puts(t, NULL);
1286 pa_pstream_send_tagstruct(c->pstream, t);
1287 pa_pdispatch_register_reply(c->pdispatch, tag, DEFAULT_TIMEOUT, pa_context_simple_ack_callback, pa_operation_ref(o), (pa_free_cb_t) pa_operation_unref);
1288
1289 return o;
1290 }