2 This file is part of PulseAudio.
4 Copyright 2004-2008 Lennart Poettering
5 Copyright 2006 Pierre Ossman <ossman@cendio.se> for Cendio AB
7 PulseAudio is free software; you can redistribute it and/or modify
8 it under the terms of the GNU Lesser General Public License as published
9 by the Free Software Foundation; either version 2.1 of the License,
10 or (at your option) any later version.
12 PulseAudio is distributed in the hope that it will be useful, but
13 WITHOUT ANY WARRANTY; without even the implied warranty of
14 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
15 General Public License for more details.
17 You should have received a copy of the GNU Lesser General Public License
18 along with PulseAudio; if not, write to the Free Software
19 Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307
29 #include <asoundlib.h>
31 #include <pulse/i18n.h>
32 #include <pulse/rtclock.h>
33 #include <pulse/timeval.h>
34 #include <pulse/util.h>
35 #include <pulse/xmalloc.h>
37 #include <pulsecore/core-error.h>
38 #include <pulsecore/core.h>
39 #include <pulsecore/module.h>
40 #include <pulsecore/memchunk.h>
41 #include <pulsecore/sink.h>
42 #include <pulsecore/modargs.h>
43 #include <pulsecore/core-rtclock.h>
44 #include <pulsecore/core-util.h>
45 #include <pulsecore/sample-util.h>
46 #include <pulsecore/log.h>
47 #include <pulsecore/macro.h>
48 #include <pulsecore/thread.h>
49 #include <pulsecore/core-error.h>
50 #include <pulsecore/thread-mq.h>
51 #include <pulsecore/rtpoll.h>
52 #include <pulsecore/time-smoother.h>
54 #include <modules/reserve-wrap.h>
56 #include "alsa-util.h"
57 #include "alsa-source.h"
59 /* #define DEBUG_TIMING */
61 #define DEFAULT_DEVICE "default"
62 #define DEFAULT_TSCHED_BUFFER_USEC (2*PA_USEC_PER_SEC) /* 2s */
63 #define DEFAULT_TSCHED_WATERMARK_USEC (20*PA_USEC_PER_MSEC) /* 20ms */
64 #define TSCHED_WATERMARK_STEP_USEC (10*PA_USEC_PER_MSEC) /* 10ms */
65 #define TSCHED_MIN_SLEEP_USEC (10*PA_USEC_PER_MSEC) /* 10ms */
66 #define TSCHED_MIN_WAKEUP_USEC (4*PA_USEC_PER_MSEC) /* 4ms */
74 pa_thread_mq thread_mq;
77 snd_pcm_t *pcm_handle;
79 pa_alsa_fdlist *mixer_fdl;
80 snd_mixer_t *mixer_handle;
81 pa_alsa_path_set *mixer_path_set;
82 pa_alsa_path *mixer_path;
84 pa_cvolume hardware_volume;
101 pa_bool_t use_mmap:1, use_tsched:1;
103 pa_rtpoll_item *alsa_rtpoll_item;
105 snd_mixer_selem_channel_id_t mixer_map[SND_MIXER_SCHN_LAST];
107 pa_smoother *smoother;
110 pa_reserve_wrapper *reserve;
111 pa_hook_slot *reserve_slot;
112 pa_reserve_monitor_wrapper *monitor;
113 pa_hook_slot *monitor_slot;
116 static void userdata_free(struct userdata *u);
118 static pa_hook_result_t reserve_cb(pa_reserve_wrapper *r, void *forced, struct userdata *u) {
122 if (pa_source_suspend(u->source, TRUE, PA_SUSPEND_APPLICATION) < 0)
123 return PA_HOOK_CANCEL;
128 static void reserve_done(struct userdata *u) {
131 if (u->reserve_slot) {
132 pa_hook_slot_free(u->reserve_slot);
133 u->reserve_slot = NULL;
137 pa_reserve_wrapper_unref(u->reserve);
142 static void reserve_update(struct userdata *u) {
143 const char *description;
146 if (!u->source || !u->reserve)
149 if ((description = pa_proplist_gets(u->source->proplist, PA_PROP_DEVICE_DESCRIPTION)))
150 pa_reserve_wrapper_set_application_device_name(u->reserve, description);
153 static int reserve_init(struct userdata *u, const char *dname) {
162 if (pa_in_system_mode())
165 /* We are resuming, try to lock the device */
166 if (!(rname = pa_alsa_get_reserve_name(dname)))
169 u->reserve = pa_reserve_wrapper_get(u->core, rname);
177 pa_assert(!u->reserve_slot);
178 u->reserve_slot = pa_hook_connect(pa_reserve_wrapper_hook(u->reserve), PA_HOOK_NORMAL, (pa_hook_cb_t) reserve_cb, u);
183 static pa_hook_result_t monitor_cb(pa_reserve_monitor_wrapper *w, void* busy, struct userdata *u) {
189 b = PA_PTR_TO_UINT(busy) && !u->reserve;
191 pa_source_suspend(u->source, b, PA_SUSPEND_APPLICATION);
195 static void monitor_done(struct userdata *u) {
198 if (u->monitor_slot) {
199 pa_hook_slot_free(u->monitor_slot);
200 u->monitor_slot = NULL;
204 pa_reserve_monitor_wrapper_unref(u->monitor);
209 static int reserve_monitor_init(struct userdata *u, const char *dname) {
215 if (pa_in_system_mode())
218 /* We are resuming, try to lock the device */
219 if (!(rname = pa_alsa_get_reserve_name(dname)))
222 u->monitor = pa_reserve_monitor_wrapper_get(u->core, rname);
228 pa_assert(!u->monitor_slot);
229 u->monitor_slot = pa_hook_connect(pa_reserve_monitor_wrapper_hook(u->monitor), PA_HOOK_NORMAL, (pa_hook_cb_t) monitor_cb, u);
234 static void fix_min_sleep_wakeup(struct userdata *u) {
235 size_t max_use, max_use_2;
238 max_use = u->hwbuf_size - u->hwbuf_unused;
239 max_use_2 = pa_frame_align(max_use/2, &u->source->sample_spec);
241 u->min_sleep = pa_usec_to_bytes(TSCHED_MIN_SLEEP_USEC, &u->source->sample_spec);
242 u->min_sleep = PA_CLAMP(u->min_sleep, u->frame_size, max_use_2);
244 u->min_wakeup = pa_usec_to_bytes(TSCHED_MIN_WAKEUP_USEC, &u->source->sample_spec);
245 u->min_wakeup = PA_CLAMP(u->min_wakeup, u->frame_size, max_use_2);
248 static void fix_tsched_watermark(struct userdata *u) {
252 max_use = u->hwbuf_size - u->hwbuf_unused;
254 if (u->tsched_watermark > max_use - u->min_sleep)
255 u->tsched_watermark = max_use - u->min_sleep;
257 if (u->tsched_watermark < u->min_wakeup)
258 u->tsched_watermark = u->min_wakeup;
261 static void adjust_after_overrun(struct userdata *u) {
262 size_t old_watermark;
263 pa_usec_t old_min_latency, new_min_latency;
266 pa_assert(u->use_tsched);
268 /* First, just try to increase the watermark */
269 old_watermark = u->tsched_watermark;
270 u->tsched_watermark = PA_MIN(u->tsched_watermark * 2, u->tsched_watermark + u->watermark_step);
272 fix_tsched_watermark(u);
274 if (old_watermark != u->tsched_watermark) {
275 pa_log_notice("Increasing wakeup watermark to %0.2f ms",
276 (double) pa_bytes_to_usec(u->tsched_watermark, &u->source->sample_spec) / PA_USEC_PER_MSEC);
280 /* Hmm, we cannot increase the watermark any further, hence let's raise the latency */
281 old_min_latency = u->source->thread_info.min_latency;
282 new_min_latency = PA_MIN(old_min_latency * 2, old_min_latency + TSCHED_WATERMARK_STEP_USEC);
283 new_min_latency = PA_MIN(new_min_latency, u->source->thread_info.max_latency);
285 if (old_min_latency != new_min_latency) {
286 pa_log_notice("Increasing minimal latency to %0.2f ms",
287 (double) new_min_latency / PA_USEC_PER_MSEC);
289 pa_source_set_latency_range_within_thread(u->source, new_min_latency, u->source->thread_info.max_latency);
293 /* When we reach this we're officialy fucked! */
296 static pa_usec_t hw_sleep_time(struct userdata *u, pa_usec_t *sleep_usec, pa_usec_t*process_usec) {
301 usec = pa_source_get_requested_latency_within_thread(u->source);
303 if (usec == (pa_usec_t) -1)
304 usec = pa_bytes_to_usec(u->hwbuf_size, &u->source->sample_spec);
306 wm = pa_bytes_to_usec(u->tsched_watermark, &u->source->sample_spec);
311 *sleep_usec = usec - wm;
315 pa_log_debug("Buffer time: %lu ms; Sleep time: %lu ms; Process time: %lu ms",
316 (unsigned long) (usec / PA_USEC_PER_MSEC),
317 (unsigned long) (*sleep_usec / PA_USEC_PER_MSEC),
318 (unsigned long) (*process_usec / PA_USEC_PER_MSEC));
324 static int try_recover(struct userdata *u, const char *call, int err) {
329 pa_log_debug("%s: %s", call, pa_alsa_strerror(err));
331 pa_assert(err != -EAGAIN);
334 pa_log_debug("%s: Buffer overrun!", call);
336 if (err == -ESTRPIPE)
337 pa_log_debug("%s: System suspended!", call);
339 if ((err = snd_pcm_recover(u->pcm_handle, err, 1)) < 0) {
340 pa_log("%s: %s", call, pa_alsa_strerror(err));
344 snd_pcm_start(u->pcm_handle);
348 static size_t check_left_to_record(struct userdata *u, size_t n_bytes) {
349 size_t left_to_record;
350 size_t rec_space = u->hwbuf_size - u->hwbuf_unused;
352 /* We use <= instead of < for this check here because an overrun
353 * only happens after the last sample was processed, not already when
354 * it is removed from the buffer. This is particularly important
355 * when block transfer is used. */
357 if (n_bytes <= rec_space) {
358 left_to_record = rec_space - n_bytes;
361 pa_log_debug("%0.2f ms left to record", (double) pa_bytes_to_usec(left_to_record, &u->source->sample_spec) / PA_USEC_PER_MSEC);
371 if (pa_log_ratelimit())
372 pa_log_info("Overrun!");
375 adjust_after_overrun(u);
378 return left_to_record;
381 static int mmap_read(struct userdata *u, pa_usec_t *sleep_usec, pa_bool_t polled) {
382 pa_bool_t work_done = FALSE;
383 pa_usec_t max_sleep_usec = 0, process_usec = 0;
384 size_t left_to_record;
388 pa_source_assert_ref(u->source);
391 hw_sleep_time(u, &max_sleep_usec, &process_usec);
397 pa_bool_t after_avail = TRUE;
399 if (PA_UNLIKELY((n = pa_alsa_safe_avail(u->pcm_handle, u->hwbuf_size, &u->source->sample_spec)) < 0)) {
401 if ((r = try_recover(u, "snd_pcm_avail", (int) n)) == 0)
407 n_bytes = (size_t) n * u->frame_size;
410 pa_log_debug("avail: %lu", (unsigned long) n_bytes);
413 left_to_record = check_left_to_record(u, n_bytes);
417 pa_bytes_to_usec(left_to_record, &u->source->sample_spec) > process_usec+max_sleep_usec/2) {
419 pa_log_debug("Not reading, because too early.");
424 if (PA_UNLIKELY(n_bytes <= 0)) {
428 char *dn = pa_alsa_get_driver_name_by_pcm(u->pcm_handle);
429 pa_log(_("ALSA woke us up to read new data from the device, but there was actually nothing to read!\n"
430 "Most likely this is a bug in the ALSA driver '%s'. Please report this issue to the ALSA developers.\n"
431 "We were woken up with POLLIN set -- however a subsequent snd_pcm_avail() returned 0 or another value < min_avail."),
437 pa_log_debug("Not reading, because not necessary.");
444 pa_log_debug("Not filling up, because already too many iterations.");
453 pa_log_debug("Reading");
458 const snd_pcm_channel_area_t *areas;
459 snd_pcm_uframes_t offset, frames;
462 snd_pcm_sframes_t sframes;
464 frames = (snd_pcm_uframes_t) (n_bytes / u->frame_size);
466 /* pa_log_debug("%lu frames to read", (unsigned long) frames); */
468 if (PA_UNLIKELY((err = pa_alsa_safe_mmap_begin(u->pcm_handle, &areas, &offset, &frames, u->hwbuf_size, &u->source->sample_spec)) < 0)) {
470 if (!after_avail && err == -EAGAIN)
473 if ((r = try_recover(u, "snd_pcm_mmap_begin", err)) == 0)
479 /* Make sure that if these memblocks need to be copied they will fit into one slot */
480 if (frames > pa_mempool_block_size_max(u->source->core->mempool)/u->frame_size)
481 frames = pa_mempool_block_size_max(u->source->core->mempool)/u->frame_size;
483 if (!after_avail && frames == 0)
486 pa_assert(frames > 0);
489 /* Check these are multiples of 8 bit */
490 pa_assert((areas[0].first & 7) == 0);
491 pa_assert((areas[0].step & 7)== 0);
493 /* We assume a single interleaved memory buffer */
494 pa_assert((areas[0].first >> 3) == 0);
495 pa_assert((areas[0].step >> 3) == u->frame_size);
497 p = (uint8_t*) areas[0].addr + (offset * u->frame_size);
499 chunk.memblock = pa_memblock_new_fixed(u->core->mempool, p, frames * u->frame_size, TRUE);
500 chunk.length = pa_memblock_get_length(chunk.memblock);
503 pa_source_post(u->source, &chunk);
504 pa_memblock_unref_fixed(chunk.memblock);
506 if (PA_UNLIKELY((sframes = snd_pcm_mmap_commit(u->pcm_handle, offset, frames)) < 0)) {
508 if ((r = try_recover(u, "snd_pcm_mmap_commit", (int) sframes)) == 0)
516 u->read_count += frames * u->frame_size;
519 pa_log_debug("Read %lu bytes (of possible %lu bytes)", (unsigned long) (frames * u->frame_size), (unsigned long) n_bytes);
522 if ((size_t) frames * u->frame_size >= n_bytes)
525 n_bytes -= (size_t) frames * u->frame_size;
529 *sleep_usec = pa_bytes_to_usec(left_to_record, &u->source->sample_spec);
531 if (*sleep_usec > process_usec)
532 *sleep_usec -= process_usec;
536 return work_done ? 1 : 0;
539 static int unix_read(struct userdata *u, pa_usec_t *sleep_usec, pa_bool_t polled) {
540 int work_done = FALSE;
541 pa_usec_t max_sleep_usec = 0, process_usec = 0;
542 size_t left_to_record;
546 pa_source_assert_ref(u->source);
549 hw_sleep_time(u, &max_sleep_usec, &process_usec);
555 pa_bool_t after_avail = TRUE;
557 if (PA_UNLIKELY((n = pa_alsa_safe_avail(u->pcm_handle, u->hwbuf_size, &u->source->sample_spec)) < 0)) {
559 if ((r = try_recover(u, "snd_pcm_avail", (int) n)) == 0)
565 n_bytes = (size_t) n * u->frame_size;
566 left_to_record = check_left_to_record(u, n_bytes);
570 pa_bytes_to_usec(left_to_record, &u->source->sample_spec) > process_usec+max_sleep_usec/2)
573 if (PA_UNLIKELY(n_bytes <= 0)) {
577 char *dn = pa_alsa_get_driver_name_by_pcm(u->pcm_handle);
578 pa_log(_("ALSA woke us up to read new data from the device, but there was actually nothing to read!\n"
579 "Most likely this is a bug in the ALSA driver '%s'. Please report this issue to the ALSA developers.\n"
580 "We were woken up with POLLIN set -- however a subsequent snd_pcm_avail() returned 0 or another value < min_avail."),
590 pa_log_debug("Not filling up, because already too many iterations.");
600 snd_pcm_sframes_t frames;
603 chunk.memblock = pa_memblock_new(u->core->mempool, (size_t) -1);
605 frames = (snd_pcm_sframes_t) (pa_memblock_get_length(chunk.memblock) / u->frame_size);
607 if (frames > (snd_pcm_sframes_t) (n_bytes/u->frame_size))
608 frames = (snd_pcm_sframes_t) (n_bytes/u->frame_size);
610 /* pa_log_debug("%lu frames to read", (unsigned long) n); */
612 p = pa_memblock_acquire(chunk.memblock);
613 frames = snd_pcm_readi(u->pcm_handle, (uint8_t*) p, (snd_pcm_uframes_t) frames);
614 pa_memblock_release(chunk.memblock);
616 if (PA_UNLIKELY(frames < 0)) {
617 pa_memblock_unref(chunk.memblock);
619 if (!after_avail && (int) frames == -EAGAIN)
622 if ((r = try_recover(u, "snd_pcm_readi", (int) frames)) == 0)
628 if (!after_avail && frames == 0) {
629 pa_memblock_unref(chunk.memblock);
633 pa_assert(frames > 0);
637 chunk.length = (size_t) frames * u->frame_size;
639 pa_source_post(u->source, &chunk);
640 pa_memblock_unref(chunk.memblock);
644 u->read_count += frames * u->frame_size;
646 /* pa_log_debug("read %lu frames", (unsigned long) frames); */
648 if ((size_t) frames * u->frame_size >= n_bytes)
651 n_bytes -= (size_t) frames * u->frame_size;
655 *sleep_usec = pa_bytes_to_usec(left_to_record, &u->source->sample_spec);
657 if (*sleep_usec > process_usec)
658 *sleep_usec -= process_usec;
662 return work_done ? 1 : 0;
665 static void update_smoother(struct userdata *u) {
666 snd_pcm_sframes_t delay = 0;
669 pa_usec_t now1 = 0, now2;
670 snd_pcm_status_t *status;
672 snd_pcm_status_alloca(&status);
675 pa_assert(u->pcm_handle);
677 /* Let's update the time smoother */
679 if (PA_UNLIKELY((err = pa_alsa_safe_delay(u->pcm_handle, &delay, u->hwbuf_size, &u->source->sample_spec)) < 0)) {
680 pa_log_warn("Failed to get delay: %s", pa_alsa_strerror(err));
684 if (PA_UNLIKELY((err = snd_pcm_status(u->pcm_handle, status)) < 0))
685 pa_log_warn("Failed to get timestamp: %s", pa_alsa_strerror(err));
687 snd_htimestamp_t htstamp = { 0, 0 };
688 snd_pcm_status_get_htstamp(status, &htstamp);
689 now1 = pa_timespec_load(&htstamp);
692 position = u->read_count + ((uint64_t) delay * (uint64_t) u->frame_size);
694 /* Hmm, if the timestamp is 0, then it wasn't set and we take the current time */
696 now1 = pa_rtclock_now();
698 now2 = pa_bytes_to_usec(position, &u->source->sample_spec);
700 pa_smoother_put(u->smoother, now1, now2);
703 static pa_usec_t source_get_latency(struct userdata *u) {
705 pa_usec_t now1, now2;
709 now1 = pa_rtclock_now();
710 now2 = pa_smoother_get(u->smoother, now1);
712 delay = (int64_t) now2 - (int64_t) pa_bytes_to_usec(u->read_count, &u->source->sample_spec);
714 return delay >= 0 ? (pa_usec_t) delay : 0;
717 static int build_pollfd(struct userdata *u) {
719 pa_assert(u->pcm_handle);
721 if (u->alsa_rtpoll_item)
722 pa_rtpoll_item_free(u->alsa_rtpoll_item);
724 if (!(u->alsa_rtpoll_item = pa_alsa_build_pollfd(u->pcm_handle, u->rtpoll)))
730 static int suspend(struct userdata *u) {
732 pa_assert(u->pcm_handle);
734 pa_smoother_pause(u->smoother, pa_rtclock_now());
737 snd_pcm_close(u->pcm_handle);
738 u->pcm_handle = NULL;
740 if (u->alsa_rtpoll_item) {
741 pa_rtpoll_item_free(u->alsa_rtpoll_item);
742 u->alsa_rtpoll_item = NULL;
745 pa_log_info("Device suspended...");
750 static int update_sw_params(struct userdata *u) {
751 snd_pcm_uframes_t avail_min;
756 /* Use the full buffer if noone asked us for anything specific */
762 if ((latency = pa_source_get_requested_latency_within_thread(u->source)) != (pa_usec_t) -1) {
765 pa_log_debug("latency set to %0.2fms", (double) latency / PA_USEC_PER_MSEC);
767 b = pa_usec_to_bytes(latency, &u->source->sample_spec);
769 /* We need at least one sample in our buffer */
771 if (PA_UNLIKELY(b < u->frame_size))
774 u->hwbuf_unused = PA_LIKELY(b < u->hwbuf_size) ? (u->hwbuf_size - b) : 0;
777 fix_min_sleep_wakeup(u);
778 fix_tsched_watermark(u);
781 pa_log_debug("hwbuf_unused=%lu", (unsigned long) u->hwbuf_unused);
786 pa_usec_t sleep_usec, process_usec;
788 hw_sleep_time(u, &sleep_usec, &process_usec);
789 avail_min += pa_usec_to_bytes(sleep_usec, &u->source->sample_spec) / u->frame_size;
792 pa_log_debug("setting avail_min=%lu", (unsigned long) avail_min);
794 if ((err = pa_alsa_set_sw_params(u->pcm_handle, avail_min)) < 0) {
795 pa_log("Failed to set software parameters: %s", pa_alsa_strerror(err));
802 static int unsuspend(struct userdata *u) {
807 snd_pcm_uframes_t period_size;
810 pa_assert(!u->pcm_handle);
812 pa_log_info("Trying resume...");
814 if ((err = snd_pcm_open(&u->pcm_handle, u->device_name, SND_PCM_STREAM_CAPTURE,
815 /*SND_PCM_NONBLOCK|*/
816 SND_PCM_NO_AUTO_RESAMPLE|
817 SND_PCM_NO_AUTO_CHANNELS|
818 SND_PCM_NO_AUTO_FORMAT)) < 0) {
819 pa_log("Error opening PCM device %s: %s", u->device_name, pa_alsa_strerror(err));
823 ss = u->source->sample_spec;
824 nfrags = u->nfragments;
825 period_size = u->fragment_size / u->frame_size;
829 if ((err = pa_alsa_set_hw_params(u->pcm_handle, &ss, &nfrags, &period_size, u->hwbuf_size / u->frame_size, &b, &d, TRUE)) < 0) {
830 pa_log("Failed to set hardware parameters: %s", pa_alsa_strerror(err));
834 if (b != u->use_mmap || d != u->use_tsched) {
835 pa_log_warn("Resume failed, couldn't get original access mode.");
839 if (!pa_sample_spec_equal(&ss, &u->source->sample_spec)) {
840 pa_log_warn("Resume failed, couldn't restore original sample settings.");
844 if (nfrags != u->nfragments || period_size*u->frame_size != u->fragment_size) {
845 pa_log_warn("Resume failed, couldn't restore original fragment settings. (Old: %lu*%lu, New %lu*%lu)",
846 (unsigned long) u->nfragments, (unsigned long) u->fragment_size,
847 (unsigned long) nfrags, period_size * u->frame_size);
851 if (update_sw_params(u) < 0)
854 if (build_pollfd(u) < 0)
857 /* FIXME: We need to reload the volume somehow */
859 snd_pcm_start(u->pcm_handle);
862 pa_smoother_reset(u->smoother, pa_rtclock_now(), TRUE);
864 pa_log_info("Resumed successfully...");
870 snd_pcm_close(u->pcm_handle);
871 u->pcm_handle = NULL;
877 static int source_process_msg(pa_msgobject *o, int code, void *data, int64_t offset, pa_memchunk *chunk) {
878 struct userdata *u = PA_SOURCE(o)->userdata;
882 case PA_SOURCE_MESSAGE_GET_LATENCY: {
886 r = source_get_latency(u);
888 *((pa_usec_t*) data) = r;
893 case PA_SOURCE_MESSAGE_SET_STATE:
895 switch ((pa_source_state_t) PA_PTR_TO_UINT(data)) {
897 case PA_SOURCE_SUSPENDED:
898 pa_assert(PA_SOURCE_IS_OPENED(u->source->thread_info.state));
906 case PA_SOURCE_RUNNING:
908 if (u->source->thread_info.state == PA_SOURCE_INIT) {
909 if (build_pollfd(u) < 0)
912 snd_pcm_start(u->pcm_handle);
915 if (u->source->thread_info.state == PA_SOURCE_SUSPENDED) {
916 if (unsuspend(u) < 0)
922 case PA_SOURCE_UNLINKED:
924 case PA_SOURCE_INVALID_STATE:
931 return pa_source_process_msg(o, code, data, offset, chunk);
934 /* Called from main context */
935 static int source_set_state_cb(pa_source *s, pa_source_state_t new_state) {
936 pa_source_state_t old_state;
939 pa_source_assert_ref(s);
940 pa_assert_se(u = s->userdata);
942 old_state = pa_source_get_state(u->source);
944 if (PA_SINK_IS_OPENED(old_state) && new_state == PA_SINK_SUSPENDED)
946 else if (old_state == PA_SINK_SUSPENDED && PA_SINK_IS_OPENED(new_state))
947 if (reserve_init(u, u->device_name) < 0)
953 static int mixer_callback(snd_mixer_elem_t *elem, unsigned int mask) {
954 struct userdata *u = snd_mixer_elem_get_callback_private(elem);
957 pa_assert(u->mixer_handle);
959 if (mask == SND_CTL_EVENT_MASK_REMOVE)
962 if (mask & SND_CTL_EVENT_MASK_VALUE) {
963 pa_source_get_volume(u->source, TRUE);
964 pa_source_get_mute(u->source, TRUE);
970 static void source_get_volume_cb(pa_source *s) {
971 struct userdata *u = s->userdata;
973 char t[PA_CVOLUME_SNPRINT_MAX];
976 pa_assert(u->mixer_path);
977 pa_assert(u->mixer_handle);
979 if (pa_alsa_path_get_volume(u->mixer_path, u->mixer_handle, &s->channel_map, &r) < 0)
982 /* Shift down by the base volume, so that 0dB becomes maximum volume */
983 pa_sw_cvolume_multiply_scalar(&r, &r, s->base_volume);
985 pa_log_debug("Read hardware volume: %s", pa_cvolume_snprint(t, sizeof(t), &r));
987 if (pa_cvolume_equal(&u->hardware_volume, &r))
990 s->virtual_volume = u->hardware_volume = r;
992 if (u->mixer_path->has_dB) {
995 /* Hmm, so the hardware volume changed, let's reset our software volume */
996 pa_cvolume_reset(&reset, s->sample_spec.channels);
997 pa_source_set_soft_volume(s, &reset);
1001 static void source_set_volume_cb(pa_source *s) {
1002 struct userdata *u = s->userdata;
1004 char t[PA_CVOLUME_SNPRINT_MAX];
1007 pa_assert(u->mixer_path);
1008 pa_assert(u->mixer_handle);
1010 /* Shift up by the base volume */
1011 pa_sw_cvolume_divide_scalar(&r, &s->virtual_volume, s->base_volume);
1013 if (pa_alsa_path_set_volume(u->mixer_path, u->mixer_handle, &s->channel_map, &r) < 0)
1016 /* Shift down by the base volume, so that 0dB becomes maximum volume */
1017 pa_sw_cvolume_multiply_scalar(&r, &r, s->base_volume);
1019 u->hardware_volume = r;
1021 if (u->mixer_path->has_dB) {
1023 /* Match exactly what the user requested by software */
1024 pa_sw_cvolume_divide(&s->soft_volume, &s->virtual_volume, &u->hardware_volume);
1026 pa_log_debug("Requested volume: %s", pa_cvolume_snprint(t, sizeof(t), &s->virtual_volume));
1027 pa_log_debug("Got hardware volume: %s", pa_cvolume_snprint(t, sizeof(t), &u->hardware_volume));
1028 pa_log_debug("Calculated software volume: %s", pa_cvolume_snprint(t, sizeof(t), &s->soft_volume));
1031 pa_log_debug("Wrote hardware volume: %s", pa_cvolume_snprint(t, sizeof(t), &r));
1033 /* We can't match exactly what the user requested, hence let's
1034 * at least tell the user about it */
1036 s->virtual_volume = r;
1040 static void source_get_mute_cb(pa_source *s) {
1041 struct userdata *u = s->userdata;
1045 pa_assert(u->mixer_path);
1046 pa_assert(u->mixer_handle);
1048 if (pa_alsa_path_get_mute(u->mixer_path, u->mixer_handle, &b) < 0)
1054 static void source_set_mute_cb(pa_source *s) {
1055 struct userdata *u = s->userdata;
1058 pa_assert(u->mixer_path);
1059 pa_assert(u->mixer_handle);
1061 pa_alsa_path_set_mute(u->mixer_path, u->mixer_handle, s->muted);
1064 static int source_set_port_cb(pa_source *s, pa_device_port *p) {
1065 struct userdata *u = s->userdata;
1066 pa_alsa_port_data *data;
1070 pa_assert(u->mixer_handle);
1072 data = PA_DEVICE_PORT_DATA(p);
1074 pa_assert_se(u->mixer_path = data->path);
1075 pa_alsa_path_select(u->mixer_path, u->mixer_handle);
1077 if (u->mixer_path->has_volume && u->mixer_path->has_dB) {
1078 s->base_volume = pa_sw_volume_from_dB(-u->mixer_path->max_dB);
1079 s->n_volume_steps = PA_VOLUME_NORM+1;
1081 if (u->mixer_path->max_dB > 0.0)
1082 pa_log_info("Fixing base volume to %0.2f dB", pa_sw_volume_to_dB(s->base_volume));
1084 pa_log_info("No particular base volume set, fixing to 0 dB");
1086 s->base_volume = PA_VOLUME_NORM;
1087 s->n_volume_steps = u->mixer_path->max_volume - u->mixer_path->min_volume + 1;
1091 pa_alsa_setting_select(data->setting, u->mixer_handle);
1101 static void source_update_requested_latency_cb(pa_source *s) {
1102 struct userdata *u = s->userdata;
1108 update_sw_params(u);
1111 static void thread_func(void *userdata) {
1112 struct userdata *u = userdata;
1113 unsigned short revents = 0;
1117 pa_log_debug("Thread starting up");
1119 if (u->core->realtime_scheduling)
1120 pa_make_realtime(u->core->realtime_priority);
1122 pa_thread_mq_install(&u->thread_mq);
1128 pa_log_debug("Loop");
1131 /* Read some data and pass it to the sources */
1132 if (PA_SOURCE_IS_OPENED(u->source->thread_info.state)) {
1134 pa_usec_t sleep_usec = 0;
1137 work_done = mmap_read(u, &sleep_usec, revents & POLLIN);
1139 work_done = unix_read(u, &sleep_usec, revents & POLLIN);
1144 /* pa_log_debug("work_done = %i", work_done); */
1149 if (u->use_tsched) {
1152 /* OK, the capture buffer is now empty, let's
1153 * calculate when to wake up next */
1155 /* pa_log_debug("Waking up in %0.2fms (sound card clock).", (double) sleep_usec / PA_USEC_PER_MSEC); */
1157 /* Convert from the sound card time domain to the
1158 * system time domain */
1159 cusec = pa_smoother_translate(u->smoother, pa_rtclock_now(), sleep_usec);
1161 /* pa_log_debug("Waking up in %0.2fms (system clock).", (double) cusec / PA_USEC_PER_MSEC); */
1163 /* We don't trust the conversion, so we wake up whatever comes first */
1164 pa_rtpoll_set_timer_relative(u->rtpoll, PA_MIN(sleep_usec, cusec));
1166 } else if (u->use_tsched)
1168 /* OK, we're in an invalid state, let's disable our timers */
1169 pa_rtpoll_set_timer_disabled(u->rtpoll);
1171 /* Hmm, nothing to do. Let's sleep */
1172 if ((ret = pa_rtpoll_run(u->rtpoll, TRUE)) < 0)
1178 /* Tell ALSA about this and process its response */
1179 if (PA_SOURCE_IS_OPENED(u->source->thread_info.state)) {
1180 struct pollfd *pollfd;
1184 pollfd = pa_rtpoll_item_get_pollfd(u->alsa_rtpoll_item, &n);
1186 if ((err = snd_pcm_poll_descriptors_revents(u->pcm_handle, pollfd, n, &revents)) < 0) {
1187 pa_log("snd_pcm_poll_descriptors_revents() failed: %s", pa_alsa_strerror(err));
1191 if (revents & ~POLLIN) {
1192 if (pa_alsa_recover_from_poll(u->pcm_handle, revents) < 0)
1195 snd_pcm_start(u->pcm_handle);
1196 } else if (revents && u->use_tsched && pa_log_ratelimit())
1197 pa_log_debug("Wakeup from ALSA!");
1204 /* If this was no regular exit from the loop we have to continue
1205 * processing messages until we received PA_MESSAGE_SHUTDOWN */
1206 pa_asyncmsgq_post(u->thread_mq.outq, PA_MSGOBJECT(u->core), PA_CORE_MESSAGE_UNLOAD_MODULE, u->module, 0, NULL, NULL);
1207 pa_asyncmsgq_wait_for(u->thread_mq.inq, PA_MESSAGE_SHUTDOWN);
1210 pa_log_debug("Thread shutting down");
1213 static void set_source_name(pa_source_new_data *data, pa_modargs *ma, const char *device_id, const char *device_name, pa_alsa_mapping *mapping) {
1219 pa_assert(device_name);
1221 if ((n = pa_modargs_get_value(ma, "source_name", NULL))) {
1222 pa_source_new_data_set_name(data, n);
1223 data->namereg_fail = TRUE;
1227 if ((n = pa_modargs_get_value(ma, "name", NULL)))
1228 data->namereg_fail = TRUE;
1230 n = device_id ? device_id : device_name;
1231 data->namereg_fail = FALSE;
1235 t = pa_sprintf_malloc("alsa_input.%s.%s", n, mapping->name);
1237 t = pa_sprintf_malloc("alsa_input.%s", n);
1239 pa_source_new_data_set_name(data, t);
1243 static void find_mixer(struct userdata *u, pa_alsa_mapping *mapping, const char *element, pa_bool_t ignore_dB) {
1245 if (!mapping && !element)
1248 if (!(u->mixer_handle = pa_alsa_open_mixer_for_pcm(u->pcm_handle, &u->control_device))) {
1249 pa_log_info("Failed to find a working mixer device.");
1255 if (!(u->mixer_path = pa_alsa_path_synthesize(element, PA_ALSA_DIRECTION_INPUT)))
1258 if (pa_alsa_path_probe(u->mixer_path, u->mixer_handle, ignore_dB) < 0)
1261 pa_log_debug("Probed mixer path %s:", u->mixer_path->name);
1262 pa_alsa_path_dump(u->mixer_path);
1265 if (!(u->mixer_path_set = pa_alsa_path_set_new(mapping, PA_ALSA_DIRECTION_INPUT)))
1268 pa_alsa_path_set_probe(u->mixer_path_set, u->mixer_handle, ignore_dB);
1270 pa_log_debug("Probed mixer paths:");
1271 pa_alsa_path_set_dump(u->mixer_path_set);
1278 if (u->mixer_path_set) {
1279 pa_alsa_path_set_free(u->mixer_path_set);
1280 u->mixer_path_set = NULL;
1281 } else if (u->mixer_path) {
1282 pa_alsa_path_free(u->mixer_path);
1283 u->mixer_path = NULL;
1286 if (u->mixer_handle) {
1287 snd_mixer_close(u->mixer_handle);
1288 u->mixer_handle = NULL;
1292 static int setup_mixer(struct userdata *u, pa_bool_t ignore_dB) {
1295 if (!u->mixer_handle)
1298 if (u->source->active_port) {
1299 pa_alsa_port_data *data;
1301 /* We have a list of supported paths, so let's activate the
1302 * one that has been chosen as active */
1304 data = PA_DEVICE_PORT_DATA(u->source->active_port);
1305 u->mixer_path = data->path;
1307 pa_alsa_path_select(data->path, u->mixer_handle);
1310 pa_alsa_setting_select(data->setting, u->mixer_handle);
1314 if (!u->mixer_path && u->mixer_path_set)
1315 u->mixer_path = u->mixer_path_set->paths;
1317 if (u->mixer_path) {
1318 /* Hmm, we have only a single path, then let's activate it */
1320 pa_alsa_path_select(u->mixer_path, u->mixer_handle);
1322 if (u->mixer_path->settings)
1323 pa_alsa_setting_select(u->mixer_path->settings, u->mixer_handle);
1328 if (!u->mixer_path->has_volume)
1329 pa_log_info("Driver does not support hardware volume control, falling back to software volume control.");
1332 if (u->mixer_path->has_dB) {
1333 pa_log_info("Hardware volume ranges from %0.2f dB to %0.2f dB.", u->mixer_path->min_dB, u->mixer_path->max_dB);
1335 u->source->base_volume = pa_sw_volume_from_dB(-u->mixer_path->max_dB);
1336 u->source->n_volume_steps = PA_VOLUME_NORM+1;
1338 if (u->mixer_path->max_dB > 0.0)
1339 pa_log_info("Fixing base volume to %0.2f dB", pa_sw_volume_to_dB(u->source->base_volume));
1341 pa_log_info("No particular base volume set, fixing to 0 dB");
1344 pa_log_info("Hardware volume ranges from %li to %li.", u->mixer_path->min_volume, u->mixer_path->max_volume);
1345 u->source->base_volume = PA_VOLUME_NORM;
1346 u->source->n_volume_steps = u->mixer_path->max_volume - u->mixer_path->min_volume + 1;
1349 u->source->get_volume = source_get_volume_cb;
1350 u->source->set_volume = source_set_volume_cb;
1352 u->source->flags |= PA_SOURCE_HW_VOLUME_CTRL | (u->mixer_path->has_dB ? PA_SOURCE_DECIBEL_VOLUME : 0);
1353 pa_log_info("Using hardware volume control. Hardware dB scale %s.", u->mixer_path->has_dB ? "supported" : "not supported");
1356 if (!u->mixer_path->has_mute) {
1357 pa_log_info("Driver does not support hardware mute control, falling back to software mute control.");
1359 u->source->get_mute = source_get_mute_cb;
1360 u->source->set_mute = source_set_mute_cb;
1361 u->source->flags |= PA_SOURCE_HW_MUTE_CTRL;
1362 pa_log_info("Using hardware mute control.");
1365 u->mixer_fdl = pa_alsa_fdlist_new();
1367 if (pa_alsa_fdlist_set_mixer(u->mixer_fdl, u->mixer_handle, u->core->mainloop) < 0) {
1368 pa_log("Failed to initialize file descriptor monitoring");
1372 if (u->mixer_path_set)
1373 pa_alsa_path_set_set_callback(u->mixer_path_set, u->mixer_handle, mixer_callback, u);
1375 pa_alsa_path_set_callback(u->mixer_path, u->mixer_handle, mixer_callback, u);
1380 pa_source *pa_alsa_source_new(pa_module *m, pa_modargs *ma, const char*driver, pa_card *card, pa_alsa_mapping *mapping) {
1382 struct userdata *u = NULL;
1383 const char *dev_id = NULL;
1384 pa_sample_spec ss, requested_ss;
1386 uint32_t nfrags, hwbuf_size, frag_size, tsched_size, tsched_watermark;
1387 snd_pcm_uframes_t period_frames, tsched_frames;
1389 pa_bool_t use_mmap = TRUE, b, use_tsched = TRUE, d, ignore_dB = FALSE;
1390 pa_source_new_data data;
1391 pa_alsa_profile_set *profile_set = NULL;
1396 ss = m->core->default_sample_spec;
1397 map = m->core->default_channel_map;
1398 if (pa_modargs_get_sample_spec_and_channel_map(ma, &ss, &map, PA_CHANNEL_MAP_ALSA) < 0) {
1399 pa_log("Failed to parse sample specification");
1404 frame_size = pa_frame_size(&ss);
1406 nfrags = m->core->default_n_fragments;
1407 frag_size = (uint32_t) pa_usec_to_bytes(m->core->default_fragment_size_msec*PA_USEC_PER_MSEC, &ss);
1409 frag_size = (uint32_t) frame_size;
1410 tsched_size = (uint32_t) pa_usec_to_bytes(DEFAULT_TSCHED_BUFFER_USEC, &ss);
1411 tsched_watermark = (uint32_t) pa_usec_to_bytes(DEFAULT_TSCHED_WATERMARK_USEC, &ss);
1413 if (pa_modargs_get_value_u32(ma, "fragments", &nfrags) < 0 ||
1414 pa_modargs_get_value_u32(ma, "fragment_size", &frag_size) < 0 ||
1415 pa_modargs_get_value_u32(ma, "tsched_buffer_size", &tsched_size) < 0 ||
1416 pa_modargs_get_value_u32(ma, "tsched_buffer_watermark", &tsched_watermark) < 0) {
1417 pa_log("Failed to parse buffer metrics");
1421 hwbuf_size = frag_size * nfrags;
1422 period_frames = frag_size/frame_size;
1423 tsched_frames = tsched_size/frame_size;
1425 if (pa_modargs_get_value_boolean(ma, "mmap", &use_mmap) < 0) {
1426 pa_log("Failed to parse mmap argument.");
1430 if (pa_modargs_get_value_boolean(ma, "tsched", &use_tsched) < 0) {
1431 pa_log("Failed to parse timer_scheduling argument.");
1435 if (pa_modargs_get_value_boolean(ma, "ignore_dB", &ignore_dB) < 0) {
1436 pa_log("Failed to parse ignore_dB argument.");
1440 if (use_tsched && !pa_rtclock_hrtimer()) {
1441 pa_log_notice("Disabling timer-based scheduling because high-resolution timers are not available from the kernel.");
1445 u = pa_xnew0(struct userdata, 1);
1448 u->use_mmap = use_mmap;
1449 u->use_tsched = use_tsched;
1450 u->rtpoll = pa_rtpoll_new();
1451 pa_thread_mq_init(&u->thread_mq, m->core->mainloop, u->rtpoll);
1453 u->smoother = pa_smoother_new(
1454 DEFAULT_TSCHED_WATERMARK_USEC*2,
1455 DEFAULT_TSCHED_WATERMARK_USEC*2,
1462 dev_id = pa_modargs_get_value(
1464 pa_modargs_get_value(ma, "device", DEFAULT_DEVICE));
1466 if (reserve_init(u, dev_id) < 0)
1469 if (reserve_monitor_init(u, dev_id) < 0)
1477 if (!(dev_id = pa_modargs_get_value(ma, "device_id", NULL))) {
1478 pa_log("device_id= not set");
1482 if (!(u->pcm_handle = pa_alsa_open_by_device_id_mapping(
1486 SND_PCM_STREAM_CAPTURE,
1487 &nfrags, &period_frames, tsched_frames,
1491 } else if ((dev_id = pa_modargs_get_value(ma, "device_id", NULL))) {
1493 if (!(profile_set = pa_alsa_profile_set_new(NULL, &map)))
1496 if (!(u->pcm_handle = pa_alsa_open_by_device_id_auto(
1500 SND_PCM_STREAM_CAPTURE,
1501 &nfrags, &period_frames, tsched_frames,
1502 &b, &d, profile_set, &mapping)))
1507 if (!(u->pcm_handle = pa_alsa_open_by_device_string(
1508 pa_modargs_get_value(ma, "device", DEFAULT_DEVICE),
1511 SND_PCM_STREAM_CAPTURE,
1512 &nfrags, &period_frames, tsched_frames,
1517 pa_assert(u->device_name);
1518 pa_log_info("Successfully opened device %s.", u->device_name);
1520 if (pa_alsa_pcm_is_modem(u->pcm_handle)) {
1521 pa_log_notice("Device %s is modem, refusing further initialization.", u->device_name);
1526 pa_log_info("Selected mapping '%s' (%s).", mapping->description, mapping->name);
1528 if (use_mmap && !b) {
1529 pa_log_info("Device doesn't support mmap(), falling back to UNIX read/write mode.");
1530 u->use_mmap = use_mmap = FALSE;
1533 if (use_tsched && (!b || !d)) {
1534 pa_log_info("Cannot enable timer-based scheduling, falling back to sound IRQ scheduling.");
1535 u->use_tsched = use_tsched = FALSE;
1538 if (use_tsched && !pa_alsa_pcm_is_hw(u->pcm_handle)) {
1539 pa_log_info("Device is not a hardware device, disabling timer-based scheduling.");
1540 u->use_tsched = use_tsched = FALSE;
1544 pa_log_info("Successfully enabled mmap() mode.");
1547 pa_log_info("Successfully enabled timer-based scheduling mode.");
1549 /* ALSA might tweak the sample spec, so recalculate the frame size */
1550 frame_size = pa_frame_size(&ss);
1552 find_mixer(u, mapping, pa_modargs_get_value(ma, "control", NULL), ignore_dB);
1554 pa_source_new_data_init(&data);
1555 data.driver = driver;
1558 set_source_name(&data, ma, dev_id, u->device_name, mapping);
1559 pa_source_new_data_set_sample_spec(&data, &ss);
1560 pa_source_new_data_set_channel_map(&data, &map);
1562 pa_alsa_init_proplist_pcm(m->core, data.proplist, u->pcm_handle);
1563 pa_proplist_sets(data.proplist, PA_PROP_DEVICE_STRING, u->device_name);
1564 pa_proplist_setf(data.proplist, PA_PROP_DEVICE_BUFFERING_BUFFER_SIZE, "%lu", (unsigned long) (period_frames * frame_size * nfrags));
1565 pa_proplist_setf(data.proplist, PA_PROP_DEVICE_BUFFERING_FRAGMENT_SIZE, "%lu", (unsigned long) (period_frames * frame_size));
1566 pa_proplist_sets(data.proplist, PA_PROP_DEVICE_ACCESS_MODE, u->use_tsched ? "mmap+timer" : (u->use_mmap ? "mmap" : "serial"));
1569 pa_proplist_sets(data.proplist, PA_PROP_DEVICE_PROFILE_NAME, mapping->name);
1570 pa_proplist_sets(data.proplist, PA_PROP_DEVICE_PROFILE_DESCRIPTION, mapping->description);
1573 pa_alsa_init_description(data.proplist);
1575 if (u->control_device)
1576 pa_alsa_init_proplist_ctl(data.proplist, u->control_device);
1578 if (pa_modargs_get_proplist(ma, "source_properties", data.proplist, PA_UPDATE_REPLACE) < 0) {
1579 pa_log("Invalid properties");
1580 pa_source_new_data_done(&data);
1584 if (u->mixer_path_set)
1585 pa_alsa_add_ports(&data.ports, u->mixer_path_set);
1587 u->source = pa_source_new(m->core, &data, PA_SOURCE_HARDWARE|PA_SOURCE_LATENCY|(u->use_tsched ? PA_SOURCE_DYNAMIC_LATENCY : 0));
1588 pa_source_new_data_done(&data);
1591 pa_log("Failed to create source object");
1595 u->source->parent.process_msg = source_process_msg;
1596 u->source->update_requested_latency = source_update_requested_latency_cb;
1597 u->source->set_state = source_set_state_cb;
1598 u->source->set_port = source_set_port_cb;
1599 u->source->userdata = u;
1601 pa_source_set_asyncmsgq(u->source, u->thread_mq.inq);
1602 pa_source_set_rtpoll(u->source, u->rtpoll);
1604 u->frame_size = frame_size;
1605 u->fragment_size = frag_size = (uint32_t) (period_frames * frame_size);
1606 u->nfragments = nfrags;
1607 u->hwbuf_size = u->fragment_size * nfrags;
1608 u->tsched_watermark = pa_usec_to_bytes_round_up(pa_bytes_to_usec_round_up(tsched_watermark, &requested_ss), &u->source->sample_spec);
1609 pa_cvolume_mute(&u->hardware_volume, u->source->sample_spec.channels);
1611 pa_log_info("Using %u fragments of size %lu bytes, buffer time is %0.2fms",
1612 nfrags, (long unsigned) u->fragment_size,
1613 (double) pa_bytes_to_usec(u->hwbuf_size, &ss) / PA_USEC_PER_MSEC);
1615 if (u->use_tsched) {
1616 u->watermark_step = pa_usec_to_bytes(TSCHED_WATERMARK_STEP_USEC, &u->source->sample_spec);
1618 fix_min_sleep_wakeup(u);
1619 fix_tsched_watermark(u);
1621 pa_source_set_latency_range(u->source,
1623 pa_bytes_to_usec(u->hwbuf_size, &ss));
1625 pa_log_info("Time scheduling watermark is %0.2fms",
1626 (double) pa_bytes_to_usec(u->tsched_watermark, &ss) / PA_USEC_PER_MSEC);
1628 pa_source_set_fixed_latency(u->source, pa_bytes_to_usec(u->hwbuf_size, &ss));
1632 if (update_sw_params(u) < 0)
1635 if (setup_mixer(u, ignore_dB) < 0)
1638 pa_alsa_dump(PA_LOG_DEBUG, u->pcm_handle);
1640 if (!(u->thread = pa_thread_new(thread_func, u))) {
1641 pa_log("Failed to create thread.");
1644 /* Get initial mixer settings */
1645 if (data.volume_is_set) {
1646 if (u->source->set_volume)
1647 u->source->set_volume(u->source);
1649 if (u->source->get_volume)
1650 u->source->get_volume(u->source);
1653 if (data.muted_is_set) {
1654 if (u->source->set_mute)
1655 u->source->set_mute(u->source);
1657 if (u->source->get_mute)
1658 u->source->get_mute(u->source);
1661 pa_source_put(u->source);
1664 pa_alsa_profile_set_free(profile_set);
1674 pa_alsa_profile_set_free(profile_set);
1679 static void userdata_free(struct userdata *u) {
1683 pa_source_unlink(u->source);
1686 pa_asyncmsgq_send(u->thread_mq.inq, NULL, PA_MESSAGE_SHUTDOWN, NULL, 0, NULL);
1687 pa_thread_free(u->thread);
1690 pa_thread_mq_done(&u->thread_mq);
1693 pa_source_unref(u->source);
1695 if (u->alsa_rtpoll_item)
1696 pa_rtpoll_item_free(u->alsa_rtpoll_item);
1699 pa_rtpoll_free(u->rtpoll);
1701 if (u->pcm_handle) {
1702 snd_pcm_drop(u->pcm_handle);
1703 snd_pcm_close(u->pcm_handle);
1707 pa_alsa_fdlist_free(u->mixer_fdl);
1709 if (u->mixer_path_set)
1710 pa_alsa_path_set_free(u->mixer_path_set);
1711 else if (u->mixer_path)
1712 pa_alsa_path_free(u->mixer_path);
1714 if (u->mixer_handle)
1715 snd_mixer_close(u->mixer_handle);
1718 pa_smoother_free(u->smoother);
1723 pa_xfree(u->device_name);
1724 pa_xfree(u->control_device);
1728 void pa_alsa_source_free(pa_source *s) {
1731 pa_source_assert_ref(s);
1732 pa_assert_se(u = s->userdata);