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 #ifdef HAVE_VALGRIND_MEMCHECK_H
32 #include <valgrind/memcheck.h>
35 #include <pulse/xmalloc.h>
36 #include <pulse/util.h>
37 #include <pulse/timeval.h>
38 #include <pulse/i18n.h>
40 #include <pulsecore/core-error.h>
41 #include <pulsecore/core.h>
42 #include <pulsecore/module.h>
43 #include <pulsecore/memchunk.h>
44 #include <pulsecore/sink.h>
45 #include <pulsecore/modargs.h>
46 #include <pulsecore/core-util.h>
47 #include <pulsecore/sample-util.h>
48 #include <pulsecore/log.h>
49 #include <pulsecore/macro.h>
50 #include <pulsecore/thread.h>
51 #include <pulsecore/core-error.h>
52 #include <pulsecore/thread-mq.h>
53 #include <pulsecore/rtpoll.h>
54 #include <pulsecore/time-smoother.h>
55 #include <pulsecore/rtclock.h>
57 #include <modules/reserve-wrap.h>
59 #include "alsa-util.h"
60 #include "alsa-source.h"
62 /* #define DEBUG_TIMING */
64 #define DEFAULT_DEVICE "default"
65 #define DEFAULT_TSCHED_BUFFER_USEC (2*PA_USEC_PER_SEC) /* 2s */
66 #define DEFAULT_TSCHED_WATERMARK_USEC (20*PA_USEC_PER_MSEC) /* 20ms */
67 #define TSCHED_WATERMARK_STEP_USEC (10*PA_USEC_PER_MSEC) /* 10ms */
68 #define TSCHED_MIN_SLEEP_USEC (10*PA_USEC_PER_MSEC) /* 10ms */
69 #define TSCHED_MIN_WAKEUP_USEC (4*PA_USEC_PER_MSEC) /* 4ms */
77 pa_thread_mq thread_mq;
80 snd_pcm_t *pcm_handle;
82 pa_alsa_fdlist *mixer_fdl;
83 snd_mixer_t *mixer_handle;
84 snd_mixer_elem_t *mixer_elem;
85 long hw_volume_max, hw_volume_min;
86 long hw_dB_max, hw_dB_min;
87 pa_bool_t hw_dB_supported:1;
88 pa_bool_t mixer_seperate_channels:1;
90 pa_cvolume hardware_volume;
106 pa_bool_t use_mmap:1, use_tsched:1;
108 pa_rtpoll_item *alsa_rtpoll_item;
110 snd_mixer_selem_channel_id_t mixer_map[SND_MIXER_SCHN_LAST];
112 pa_smoother *smoother;
115 pa_reserve_wrapper *reserve;
116 pa_hook_slot *reserve_slot;
119 static void userdata_free(struct userdata *u);
121 static pa_hook_result_t reserve_cb(pa_reserve_wrapper *r, void *forced, struct userdata *u) {
125 if (pa_source_suspend(u->source, TRUE) < 0)
126 return PA_HOOK_CANCEL;
131 static void reserve_done(struct userdata *u) {
134 if (u->reserve_slot) {
135 pa_hook_slot_free(u->reserve_slot);
136 u->reserve_slot = NULL;
140 pa_reserve_wrapper_unref(u->reserve);
145 static void reserve_update(struct userdata *u) {
146 const char *description;
149 if (!u->source || !u->reserve)
152 if ((description = pa_proplist_gets(u->source->proplist, PA_PROP_DEVICE_DESCRIPTION)))
153 pa_reserve_wrapper_set_application_device_name(u->reserve, description);
156 static int reserve_init(struct userdata *u, const char *dname) {
165 if (pa_in_system_mode())
168 /* We are resuming, try to lock the device */
169 if (!(rname = pa_alsa_get_reserve_name(dname)))
172 u->reserve = pa_reserve_wrapper_get(u->core, rname);
180 pa_assert(!u->reserve_slot);
181 u->reserve_slot = pa_hook_connect(pa_reserve_wrapper_hook(u->reserve), PA_HOOK_NORMAL, (pa_hook_cb_t) reserve_cb, u);
186 static void fix_min_sleep_wakeup(struct userdata *u) {
187 size_t max_use, max_use_2;
190 max_use = u->hwbuf_size - u->hwbuf_unused;
191 max_use_2 = pa_frame_align(max_use/2, &u->source->sample_spec);
193 u->min_sleep = pa_usec_to_bytes(TSCHED_MIN_SLEEP_USEC, &u->source->sample_spec);
194 u->min_sleep = PA_CLAMP(u->min_sleep, u->frame_size, max_use_2);
196 u->min_wakeup = pa_usec_to_bytes(TSCHED_MIN_WAKEUP_USEC, &u->source->sample_spec);
197 u->min_wakeup = PA_CLAMP(u->min_wakeup, u->frame_size, max_use_2);
200 static void fix_tsched_watermark(struct userdata *u) {
204 max_use = u->hwbuf_size - u->hwbuf_unused;
206 if (u->tsched_watermark > max_use - u->min_sleep)
207 u->tsched_watermark = max_use - u->min_sleep;
209 if (u->tsched_watermark < u->min_wakeup)
210 u->tsched_watermark = u->min_wakeup;
213 static void adjust_after_overrun(struct userdata *u) {
214 size_t old_watermark;
215 pa_usec_t old_min_latency, new_min_latency;
218 pa_assert(u->use_tsched);
220 /* First, just try to increase the watermark */
221 old_watermark = u->tsched_watermark;
222 u->tsched_watermark = PA_MIN(u->tsched_watermark * 2, u->tsched_watermark + u->watermark_step);
224 fix_tsched_watermark(u);
226 if (old_watermark != u->tsched_watermark) {
227 pa_log_notice("Increasing wakeup watermark to %0.2f ms",
228 (double) pa_bytes_to_usec(u->tsched_watermark, &u->source->sample_spec) / PA_USEC_PER_MSEC);
232 /* Hmm, we cannot increase the watermark any further, hence let's raise the latency */
233 old_min_latency = u->source->thread_info.min_latency;
234 new_min_latency = PA_MIN(old_min_latency * 2, old_min_latency + TSCHED_WATERMARK_STEP_USEC);
235 new_min_latency = PA_MIN(new_min_latency, u->source->thread_info.max_latency);
237 if (old_min_latency != new_min_latency) {
238 pa_log_notice("Increasing minimal latency to %0.2f ms",
239 (double) new_min_latency / PA_USEC_PER_MSEC);
241 pa_source_update_latency_range(u->source, new_min_latency, u->source->thread_info.max_latency);
245 /* When we reach this we're officialy fucked! */
248 static pa_usec_t hw_sleep_time(struct userdata *u, pa_usec_t *sleep_usec, pa_usec_t*process_usec) {
253 usec = pa_source_get_requested_latency_within_thread(u->source);
255 if (usec == (pa_usec_t) -1)
256 usec = pa_bytes_to_usec(u->hwbuf_size, &u->source->sample_spec);
258 wm = pa_bytes_to_usec(u->tsched_watermark, &u->source->sample_spec);
263 *sleep_usec = usec - wm;
267 pa_log_debug("Buffer time: %lu ms; Sleep time: %lu ms; Process time: %lu ms",
268 (unsigned long) (usec / PA_USEC_PER_MSEC),
269 (unsigned long) (*sleep_usec / PA_USEC_PER_MSEC),
270 (unsigned long) (*process_usec / PA_USEC_PER_MSEC));
276 static int try_recover(struct userdata *u, const char *call, int err) {
281 pa_log_debug("%s: %s", call, snd_strerror(err));
283 pa_assert(err != -EAGAIN);
286 pa_log_debug("%s: Buffer overrun!", call);
288 if ((err = snd_pcm_recover(u->pcm_handle, err, 1)) < 0) {
289 pa_log("%s: %s", call, snd_strerror(err));
293 snd_pcm_start(u->pcm_handle);
297 static size_t check_left_to_record(struct userdata *u, size_t n_bytes) {
298 size_t left_to_record;
299 size_t rec_space = u->hwbuf_size - u->hwbuf_unused;
301 /* We use <= instead of < for this check here because an overrun
302 * only happens after the last sample was processed, not already when
303 * it is removed from the buffer. This is particularly important
304 * when block transfer is used. */
306 if (n_bytes <= rec_space) {
307 left_to_record = rec_space - n_bytes;
310 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);
320 if (pa_log_ratelimit())
321 pa_log_info("Overrun!");
324 adjust_after_overrun(u);
327 return left_to_record;
330 static int mmap_read(struct userdata *u, pa_usec_t *sleep_usec, pa_bool_t polled) {
331 pa_bool_t work_done = FALSE;
332 pa_usec_t max_sleep_usec = 0, process_usec = 0;
333 size_t left_to_record;
337 pa_source_assert_ref(u->source);
340 hw_sleep_time(u, &max_sleep_usec, &process_usec);
347 if (PA_UNLIKELY((n = pa_alsa_safe_avail(u->pcm_handle, u->hwbuf_size, &u->source->sample_spec)) < 0)) {
349 if ((r = try_recover(u, "snd_pcm_avail", (int) n)) == 0)
355 n_bytes = (size_t) n * u->frame_size;
358 pa_log_debug("avail: %lu", (unsigned long) n_bytes);
361 left_to_record = check_left_to_record(u, n_bytes);
365 pa_bytes_to_usec(left_to_record, &u->source->sample_spec) > process_usec+max_sleep_usec/2) {
367 pa_log_debug("Not reading, because too early.");
372 if (PA_UNLIKELY(n_bytes <= 0)) {
376 char *dn = pa_alsa_get_driver_name_by_pcm(u->pcm_handle);
377 pa_log(_("ALSA woke us up to read new data from the device, but there was actually nothing to read!\n"
378 "Most likely this is a bug in the ALSA driver '%s'. Please report this issue to the ALSA developers.\n"
379 "We were woken up with POLLIN set -- however a subsequent snd_pcm_avail() returned 0 or another value < min_avail."),
385 pa_log_debug("Not reading, because not necessary.");
392 pa_log_debug("Not filling up, because already too many iterations.");
401 pa_log_debug("Reading");
406 const snd_pcm_channel_area_t *areas;
407 snd_pcm_uframes_t offset, frames;
410 snd_pcm_sframes_t sframes;
412 frames = (snd_pcm_uframes_t) (n_bytes / u->frame_size);
414 /* pa_log_debug("%lu frames to read", (unsigned long) frames); */
416 if (PA_UNLIKELY((err = pa_alsa_safe_mmap_begin(u->pcm_handle, &areas, &offset, &frames, u->hwbuf_size, &u->source->sample_spec)) < 0)) {
418 if ((r = try_recover(u, "snd_pcm_mmap_begin", err)) == 0)
424 /* Make sure that if these memblocks need to be copied they will fit into one slot */
425 if (frames > pa_mempool_block_size_max(u->source->core->mempool)/u->frame_size)
426 frames = pa_mempool_block_size_max(u->source->core->mempool)/u->frame_size;
428 /* Check these are multiples of 8 bit */
429 pa_assert((areas[0].first & 7) == 0);
430 pa_assert((areas[0].step & 7)== 0);
432 /* We assume a single interleaved memory buffer */
433 pa_assert((areas[0].first >> 3) == 0);
434 pa_assert((areas[0].step >> 3) == u->frame_size);
436 p = (uint8_t*) areas[0].addr + (offset * u->frame_size);
438 chunk.memblock = pa_memblock_new_fixed(u->core->mempool, p, frames * u->frame_size, TRUE);
439 chunk.length = pa_memblock_get_length(chunk.memblock);
442 pa_source_post(u->source, &chunk);
443 pa_memblock_unref_fixed(chunk.memblock);
445 if (PA_UNLIKELY((sframes = snd_pcm_mmap_commit(u->pcm_handle, offset, frames)) < 0)) {
447 if ((r = try_recover(u, "snd_pcm_mmap_commit", (int) sframes)) == 0)
455 u->read_count += frames * u->frame_size;
458 pa_log_debug("Read %lu bytes", (unsigned long) (frames * u->frame_size));
461 if ((size_t) frames * u->frame_size >= n_bytes)
464 n_bytes -= (size_t) frames * u->frame_size;
468 *sleep_usec = pa_bytes_to_usec(left_to_record, &u->source->sample_spec) - process_usec;
469 return work_done ? 1 : 0;
472 static int unix_read(struct userdata *u, pa_usec_t *sleep_usec, pa_bool_t polled) {
473 int work_done = FALSE;
474 pa_usec_t max_sleep_usec = 0, process_usec = 0;
475 size_t left_to_record;
479 pa_source_assert_ref(u->source);
482 hw_sleep_time(u, &max_sleep_usec, &process_usec);
489 if (PA_UNLIKELY((n = pa_alsa_safe_avail(u->pcm_handle, u->hwbuf_size, &u->source->sample_spec)) < 0)) {
491 if ((r = try_recover(u, "snd_pcm_avail", (int) n)) == 0)
497 n_bytes = (size_t) n * u->frame_size;
498 left_to_record = check_left_to_record(u, n_bytes);
502 pa_bytes_to_usec(left_to_record, &u->source->sample_spec) > process_usec+max_sleep_usec/2)
505 if (PA_UNLIKELY(n_bytes <= 0)) {
509 char *dn = pa_alsa_get_driver_name_by_pcm(u->pcm_handle);
510 pa_log(_("ALSA woke us up to read new data from the device, but there was actually nothing to read!\n"
511 "Most likely this is a bug in the ALSA driver '%s'. Please report this issue to the ALSA developers.\n"
512 "We were woken up with POLLIN set -- however a subsequent snd_pcm_avail() returned 0 or another value < min_avail."),
522 pa_log_debug("Not filling up, because already too many iterations.");
532 snd_pcm_sframes_t frames;
535 chunk.memblock = pa_memblock_new(u->core->mempool, (size_t) -1);
537 frames = (snd_pcm_sframes_t) (pa_memblock_get_length(chunk.memblock) / u->frame_size);
539 if (frames > (snd_pcm_sframes_t) (n_bytes/u->frame_size))
540 frames = (snd_pcm_sframes_t) (n_bytes/u->frame_size);
542 /* pa_log_debug("%lu frames to read", (unsigned long) n); */
544 p = pa_memblock_acquire(chunk.memblock);
545 frames = snd_pcm_readi(u->pcm_handle, (uint8_t*) p, (snd_pcm_uframes_t) frames);
546 pa_memblock_release(chunk.memblock);
548 pa_assert(frames != 0);
550 if (PA_UNLIKELY(frames < 0)) {
551 pa_memblock_unref(chunk.memblock);
553 if ((r = try_recover(u, "snd_pcm_readi", (int) (frames))) == 0)
560 chunk.length = (size_t) frames * u->frame_size;
562 pa_source_post(u->source, &chunk);
563 pa_memblock_unref(chunk.memblock);
567 u->read_count += frames * u->frame_size;
569 /* pa_log_debug("read %lu frames", (unsigned long) frames); */
571 if ((size_t) frames * u->frame_size >= n_bytes)
574 n_bytes -= (size_t) frames * u->frame_size;
578 *sleep_usec = pa_bytes_to_usec(left_to_record, &u->source->sample_spec) - process_usec;
579 return work_done ? 1 : 0;
582 static void update_smoother(struct userdata *u) {
583 snd_pcm_sframes_t delay = 0;
586 pa_usec_t now1 = 0, now2;
587 snd_pcm_status_t *status;
589 snd_pcm_status_alloca(&status);
592 pa_assert(u->pcm_handle);
594 /* Let's update the time smoother */
596 if (PA_UNLIKELY((err = pa_alsa_safe_delay(u->pcm_handle, &delay, u->hwbuf_size, &u->source->sample_spec)) < 0)) {
597 pa_log_warn("Failed to get delay: %s", snd_strerror(err));
601 if (PA_UNLIKELY((err = snd_pcm_status(u->pcm_handle, status)) < 0))
602 pa_log_warn("Failed to get timestamp: %s", snd_strerror(err));
604 snd_htimestamp_t htstamp = { 0, 0 };
605 snd_pcm_status_get_htstamp(status, &htstamp);
606 now1 = pa_timespec_load(&htstamp);
609 position = u->read_count + ((uint64_t) delay * (uint64_t) u->frame_size);
611 /* Hmm, if the timestamp is 0, then it wasn't set and we take the current time */
613 now1 = pa_rtclock_usec();
615 now2 = pa_bytes_to_usec(position, &u->source->sample_spec);
617 pa_smoother_put(u->smoother, now1, now2);
620 static pa_usec_t source_get_latency(struct userdata *u) {
622 pa_usec_t now1, now2;
626 now1 = pa_rtclock_usec();
627 now2 = pa_smoother_get(u->smoother, now1);
629 delay = (int64_t) now2 - (int64_t) pa_bytes_to_usec(u->read_count, &u->source->sample_spec);
631 return delay >= 0 ? (pa_usec_t) delay : 0;
634 static int build_pollfd(struct userdata *u) {
636 pa_assert(u->pcm_handle);
638 if (u->alsa_rtpoll_item)
639 pa_rtpoll_item_free(u->alsa_rtpoll_item);
641 if (!(u->alsa_rtpoll_item = pa_alsa_build_pollfd(u->pcm_handle, u->rtpoll)))
647 static int suspend(struct userdata *u) {
649 pa_assert(u->pcm_handle);
651 pa_smoother_pause(u->smoother, pa_rtclock_usec());
654 snd_pcm_close(u->pcm_handle);
655 u->pcm_handle = NULL;
657 if (u->alsa_rtpoll_item) {
658 pa_rtpoll_item_free(u->alsa_rtpoll_item);
659 u->alsa_rtpoll_item = NULL;
662 pa_log_info("Device suspended...");
667 static int update_sw_params(struct userdata *u) {
668 snd_pcm_uframes_t avail_min;
673 /* Use the full buffer if noone asked us for anything specific */
679 if ((latency = pa_source_get_requested_latency_within_thread(u->source)) != (pa_usec_t) -1) {
682 pa_log_debug("latency set to %0.2fms", (double) latency / PA_USEC_PER_MSEC);
684 b = pa_usec_to_bytes(latency, &u->source->sample_spec);
686 /* We need at least one sample in our buffer */
688 if (PA_UNLIKELY(b < u->frame_size))
691 u->hwbuf_unused = PA_LIKELY(b < u->hwbuf_size) ? (u->hwbuf_size - b) : 0;
694 fix_min_sleep_wakeup(u);
695 fix_tsched_watermark(u);
698 pa_log_debug("hwbuf_unused=%lu", (unsigned long) u->hwbuf_unused);
703 pa_usec_t sleep_usec, process_usec;
705 hw_sleep_time(u, &sleep_usec, &process_usec);
706 avail_min += pa_usec_to_bytes(sleep_usec, &u->source->sample_spec) / u->frame_size;
709 pa_log_debug("setting avail_min=%lu", (unsigned long) avail_min);
711 if ((err = pa_alsa_set_sw_params(u->pcm_handle, avail_min)) < 0) {
712 pa_log("Failed to set software parameters: %s", snd_strerror(err));
719 static int unsuspend(struct userdata *u) {
724 snd_pcm_uframes_t period_size;
727 pa_assert(!u->pcm_handle);
729 pa_log_info("Trying resume...");
731 snd_config_update_free_global();
733 if ((err = snd_pcm_open(&u->pcm_handle, u->device_name, SND_PCM_STREAM_CAPTURE,
734 /*SND_PCM_NONBLOCK|*/
735 SND_PCM_NO_AUTO_RESAMPLE|
736 SND_PCM_NO_AUTO_CHANNELS|
737 SND_PCM_NO_AUTO_FORMAT)) < 0) {
738 pa_log("Error opening PCM device %s: %s", u->device_name, snd_strerror(err));
742 ss = u->source->sample_spec;
743 nfrags = u->nfragments;
744 period_size = u->fragment_size / u->frame_size;
748 if ((err = pa_alsa_set_hw_params(u->pcm_handle, &ss, &nfrags, &period_size, u->hwbuf_size / u->frame_size, &b, &d, TRUE)) < 0) {
749 pa_log("Failed to set hardware parameters: %s", snd_strerror(err));
753 if (b != u->use_mmap || d != u->use_tsched) {
754 pa_log_warn("Resume failed, couldn't get original access mode.");
758 if (!pa_sample_spec_equal(&ss, &u->source->sample_spec)) {
759 pa_log_warn("Resume failed, couldn't restore original sample settings.");
763 if (nfrags != u->nfragments || period_size*u->frame_size != u->fragment_size) {
764 pa_log_warn("Resume failed, couldn't restore original fragment settings. (Old: %lu*%lu, New %lu*%lu)",
765 (unsigned long) u->nfragments, (unsigned long) u->fragment_size,
766 (unsigned long) nfrags, period_size * u->frame_size);
770 if (update_sw_params(u) < 0)
773 if (build_pollfd(u) < 0)
776 /* FIXME: We need to reload the volume somehow */
778 snd_pcm_start(u->pcm_handle);
779 pa_smoother_resume(u->smoother, pa_rtclock_usec());
781 pa_log_info("Resumed successfully...");
787 snd_pcm_close(u->pcm_handle);
788 u->pcm_handle = NULL;
794 static int source_process_msg(pa_msgobject *o, int code, void *data, int64_t offset, pa_memchunk *chunk) {
795 struct userdata *u = PA_SOURCE(o)->userdata;
799 case PA_SOURCE_MESSAGE_GET_LATENCY: {
803 r = source_get_latency(u);
805 *((pa_usec_t*) data) = r;
810 case PA_SOURCE_MESSAGE_SET_STATE:
812 switch ((pa_source_state_t) PA_PTR_TO_UINT(data)) {
814 case PA_SOURCE_SUSPENDED:
815 pa_assert(PA_SOURCE_IS_OPENED(u->source->thread_info.state));
823 case PA_SOURCE_RUNNING:
825 if (u->source->thread_info.state == PA_SOURCE_INIT) {
826 if (build_pollfd(u) < 0)
829 snd_pcm_start(u->pcm_handle);
832 if (u->source->thread_info.state == PA_SOURCE_SUSPENDED) {
833 if (unsuspend(u) < 0)
839 case PA_SOURCE_UNLINKED:
841 case PA_SOURCE_INVALID_STATE:
848 return pa_source_process_msg(o, code, data, offset, chunk);
851 /* Called from main context */
852 static int source_set_state_cb(pa_source *s, pa_source_state_t new_state) {
853 pa_source_state_t old_state;
856 pa_source_assert_ref(s);
857 pa_assert_se(u = s->userdata);
859 old_state = pa_source_get_state(u->source);
861 if (PA_SINK_IS_OPENED(old_state) && new_state == PA_SINK_SUSPENDED)
863 else if (old_state == PA_SINK_SUSPENDED && PA_SINK_IS_OPENED(new_state))
864 if (reserve_init(u, u->device_name) < 0)
870 static int mixer_callback(snd_mixer_elem_t *elem, unsigned int mask) {
871 struct userdata *u = snd_mixer_elem_get_callback_private(elem);
874 pa_assert(u->mixer_handle);
876 if (mask == SND_CTL_EVENT_MASK_REMOVE)
879 if (mask & SND_CTL_EVENT_MASK_VALUE) {
880 pa_source_get_volume(u->source, TRUE);
881 pa_source_get_mute(u->source, TRUE);
887 static pa_volume_t from_alsa_volume(struct userdata *u, long alsa_vol) {
889 return (pa_volume_t) round(((double) (alsa_vol - u->hw_volume_min) * PA_VOLUME_NORM) /
890 (double) (u->hw_volume_max - u->hw_volume_min));
893 static long to_alsa_volume(struct userdata *u, pa_volume_t vol) {
896 alsa_vol = (long) round(((double) vol * (double) (u->hw_volume_max - u->hw_volume_min))
897 / PA_VOLUME_NORM) + u->hw_volume_min;
899 return PA_CLAMP_UNLIKELY(alsa_vol, u->hw_volume_min, u->hw_volume_max);
902 static void source_get_volume_cb(pa_source *s) {
903 struct userdata *u = s->userdata;
907 char t[PA_CVOLUME_SNPRINT_MAX];
910 pa_assert(u->mixer_elem);
912 if (u->mixer_seperate_channels) {
914 r.channels = s->sample_spec.channels;
916 for (i = 0; i < s->sample_spec.channels; i++) {
919 if (u->hw_dB_supported) {
921 if ((err = snd_mixer_selem_get_capture_dB(u->mixer_elem, u->mixer_map[i], &alsa_vol)) < 0)
924 #ifdef HAVE_VALGRIND_MEMCHECK_H
925 VALGRIND_MAKE_MEM_DEFINED(&alsa_vol, sizeof(alsa_vol));
928 r.values[i] = pa_sw_volume_from_dB((double) (alsa_vol - u->hw_dB_max) / 100.0);
931 if ((err = snd_mixer_selem_get_capture_volume(u->mixer_elem, u->mixer_map[i], &alsa_vol)) < 0)
934 r.values[i] = from_alsa_volume(u, alsa_vol);
941 if (u->hw_dB_supported) {
943 if ((err = snd_mixer_selem_get_capture_dB(u->mixer_elem, SND_MIXER_SCHN_MONO, &alsa_vol)) < 0)
946 #ifdef HAVE_VALGRIND_MEMCHECK_H
947 VALGRIND_MAKE_MEM_DEFINED(&alsa_vol, sizeof(alsa_vol));
950 pa_cvolume_set(&r, s->sample_spec.channels, pa_sw_volume_from_dB((double) (alsa_vol - u->hw_dB_max) / 100.0));
954 if ((err = snd_mixer_selem_get_capture_volume(u->mixer_elem, SND_MIXER_SCHN_MONO, &alsa_vol)) < 0)
957 pa_cvolume_set(&r, s->sample_spec.channels, from_alsa_volume(u, alsa_vol));
961 pa_log_debug("Read hardware volume: %s", pa_cvolume_snprint(t, sizeof(t), &r));
963 if (!pa_cvolume_equal(&u->hardware_volume, &r)) {
965 s->virtual_volume = u->hardware_volume = r;
967 if (u->hw_dB_supported) {
970 /* Hmm, so the hardware volume changed, let's reset our software volume */
971 pa_cvolume_reset(&reset, s->sample_spec.channels);
972 pa_source_set_soft_volume(s, &reset);
979 pa_log_error("Unable to read volume: %s", snd_strerror(err));
982 static void source_set_volume_cb(pa_source *s) {
983 struct userdata *u = s->userdata;
989 pa_assert(u->mixer_elem);
991 if (u->mixer_seperate_channels) {
993 r.channels = s->sample_spec.channels;
995 for (i = 0; i < s->sample_spec.channels; i++) {
999 vol = s->virtual_volume.values[i];
1001 if (u->hw_dB_supported) {
1003 alsa_vol = (long) (pa_sw_volume_to_dB(vol) * 100);
1004 alsa_vol += u->hw_dB_max;
1005 alsa_vol = PA_CLAMP_UNLIKELY(alsa_vol, u->hw_dB_min, u->hw_dB_max);
1007 if ((err = snd_mixer_selem_set_capture_dB(u->mixer_elem, u->mixer_map[i], alsa_vol, 1)) < 0)
1010 if ((err = snd_mixer_selem_get_capture_dB(u->mixer_elem, u->mixer_map[i], &alsa_vol)) < 0)
1013 #ifdef HAVE_VALGRIND_MEMCHECK_H
1014 VALGRIND_MAKE_MEM_DEFINED(&alsa_vol, sizeof(alsa_vol));
1017 r.values[i] = pa_sw_volume_from_dB((double) (alsa_vol - u->hw_dB_max) / 100.0);
1020 alsa_vol = to_alsa_volume(u, vol);
1022 if ((err = snd_mixer_selem_set_capture_volume(u->mixer_elem, u->mixer_map[i], alsa_vol)) < 0)
1025 if ((err = snd_mixer_selem_get_capture_volume(u->mixer_elem, u->mixer_map[i], &alsa_vol)) < 0)
1028 r.values[i] = from_alsa_volume(u, alsa_vol);
1036 vol = pa_cvolume_max(&s->virtual_volume);
1038 if (u->hw_dB_supported) {
1039 alsa_vol = (long) (pa_sw_volume_to_dB(vol) * 100);
1040 alsa_vol += u->hw_dB_max;
1041 alsa_vol = PA_CLAMP_UNLIKELY(alsa_vol, u->hw_dB_min, u->hw_dB_max);
1043 if ((err = snd_mixer_selem_set_capture_dB_all(u->mixer_elem, alsa_vol, 1)) < 0)
1046 if ((err = snd_mixer_selem_get_capture_dB(u->mixer_elem, SND_MIXER_SCHN_MONO, &alsa_vol)) < 0)
1049 #ifdef HAVE_VALGRIND_MEMCHECK_H
1050 VALGRIND_MAKE_MEM_DEFINED(&alsa_vol, sizeof(alsa_vol));
1053 pa_cvolume_set(&r, s->sample_spec.channels, pa_sw_volume_from_dB((double) (alsa_vol - u->hw_dB_max) / 100.0));
1056 alsa_vol = to_alsa_volume(u, vol);
1058 if ((err = snd_mixer_selem_set_capture_volume_all(u->mixer_elem, alsa_vol)) < 0)
1061 if ((err = snd_mixer_selem_get_capture_volume(u->mixer_elem, SND_MIXER_SCHN_MONO, &alsa_vol)) < 0)
1064 pa_cvolume_set(&r, s->sample_spec.channels, from_alsa_volume(u, alsa_vol));
1068 u->hardware_volume = r;
1070 if (u->hw_dB_supported) {
1071 char t[PA_CVOLUME_SNPRINT_MAX];
1073 /* Match exactly what the user requested by software */
1075 pa_sw_cvolume_divide(&s->soft_volume, &s->virtual_volume, &u->hardware_volume);
1077 pa_log_debug("Requested volume: %s", pa_cvolume_snprint(t, sizeof(t), &s->virtual_volume));
1078 pa_log_debug("Got hardware volume: %s", pa_cvolume_snprint(t, sizeof(t), &u->hardware_volume));
1079 pa_log_debug("Calculated software volume: %s", pa_cvolume_snprint(t, sizeof(t), &s->soft_volume));
1083 /* We can't match exactly what the user requested, hence let's
1084 * at least tell the user about it */
1086 s->virtual_volume = r;
1091 pa_log_error("Unable to set volume: %s", snd_strerror(err));
1094 static void source_get_mute_cb(pa_source *s) {
1095 struct userdata *u = s->userdata;
1099 pa_assert(u->mixer_elem);
1101 if ((err = snd_mixer_selem_get_capture_switch(u->mixer_elem, 0, &sw)) < 0) {
1102 pa_log_error("Unable to get switch: %s", snd_strerror(err));
1109 static void source_set_mute_cb(pa_source *s) {
1110 struct userdata *u = s->userdata;
1114 pa_assert(u->mixer_elem);
1116 if ((err = snd_mixer_selem_set_capture_switch_all(u->mixer_elem, !s->muted)) < 0) {
1117 pa_log_error("Unable to set switch: %s", snd_strerror(err));
1122 static void source_update_requested_latency_cb(pa_source *s) {
1123 struct userdata *u = s->userdata;
1129 update_sw_params(u);
1132 static void thread_func(void *userdata) {
1133 struct userdata *u = userdata;
1134 unsigned short revents = 0;
1138 pa_log_debug("Thread starting up");
1140 if (u->core->realtime_scheduling)
1141 pa_make_realtime(u->core->realtime_priority);
1143 pa_thread_mq_install(&u->thread_mq);
1144 pa_rtpoll_install(u->rtpoll);
1150 pa_log_debug("Loop");
1153 /* Read some data and pass it to the sources */
1154 if (PA_SOURCE_IS_OPENED(u->source->thread_info.state)) {
1156 pa_usec_t sleep_usec = 0;
1159 work_done = mmap_read(u, &sleep_usec, revents & POLLIN);
1161 work_done = unix_read(u, &sleep_usec, revents & POLLIN);
1166 /* pa_log_debug("work_done = %i", work_done); */
1171 if (u->use_tsched) {
1174 /* OK, the capture buffer is now empty, let's
1175 * calculate when to wake up next */
1177 /* pa_log_debug("Waking up in %0.2fms (sound card clock).", (double) sleep_usec / PA_USEC_PER_MSEC); */
1179 /* Convert from the sound card time domain to the
1180 * system time domain */
1181 cusec = pa_smoother_translate(u->smoother, pa_rtclock_usec(), sleep_usec);
1183 /* pa_log_debug("Waking up in %0.2fms (system clock).", (double) cusec / PA_USEC_PER_MSEC); */
1185 /* We don't trust the conversion, so we wake up whatever comes first */
1186 pa_rtpoll_set_timer_relative(u->rtpoll, PA_MIN(sleep_usec, cusec));
1188 } else if (u->use_tsched)
1190 /* OK, we're in an invalid state, let's disable our timers */
1191 pa_rtpoll_set_timer_disabled(u->rtpoll);
1193 /* Hmm, nothing to do. Let's sleep */
1194 if ((ret = pa_rtpoll_run(u->rtpoll, TRUE)) < 0)
1200 /* Tell ALSA about this and process its response */
1201 if (PA_SOURCE_IS_OPENED(u->source->thread_info.state)) {
1202 struct pollfd *pollfd;
1206 pollfd = pa_rtpoll_item_get_pollfd(u->alsa_rtpoll_item, &n);
1208 if ((err = snd_pcm_poll_descriptors_revents(u->pcm_handle, pollfd, n, &revents)) < 0) {
1209 pa_log("snd_pcm_poll_descriptors_revents() failed: %s", snd_strerror(err));
1213 if (revents & ~POLLIN) {
1214 if (pa_alsa_recover_from_poll(u->pcm_handle, revents) < 0)
1217 snd_pcm_start(u->pcm_handle);
1218 } else if (revents && u->use_tsched && pa_log_ratelimit())
1219 pa_log_debug("Wakeup from ALSA!");
1226 /* If this was no regular exit from the loop we have to continue
1227 * processing messages until we received PA_MESSAGE_SHUTDOWN */
1228 pa_asyncmsgq_post(u->thread_mq.outq, PA_MSGOBJECT(u->core), PA_CORE_MESSAGE_UNLOAD_MODULE, u->module, 0, NULL, NULL);
1229 pa_asyncmsgq_wait_for(u->thread_mq.inq, PA_MESSAGE_SHUTDOWN);
1232 pa_log_debug("Thread shutting down");
1235 static void set_source_name(pa_source_new_data *data, pa_modargs *ma, const char *device_id, const char *device_name) {
1241 pa_assert(device_name);
1243 if ((n = pa_modargs_get_value(ma, "source_name", NULL))) {
1244 pa_source_new_data_set_name(data, n);
1245 data->namereg_fail = TRUE;
1249 if ((n = pa_modargs_get_value(ma, "name", NULL)))
1250 data->namereg_fail = TRUE;
1252 n = device_id ? device_id : device_name;
1253 data->namereg_fail = FALSE;
1256 t = pa_sprintf_malloc("alsa_input.%s", n);
1257 pa_source_new_data_set_name(data, t);
1261 static int setup_mixer(struct userdata *u, pa_bool_t ignore_dB) {
1264 if (!u->mixer_handle)
1267 pa_assert(u->mixer_elem);
1269 if (snd_mixer_selem_has_capture_volume(u->mixer_elem)) {
1270 pa_bool_t suitable = FALSE;
1272 if (snd_mixer_selem_get_capture_volume_range(u->mixer_elem, &u->hw_volume_min, &u->hw_volume_max) < 0)
1273 pa_log_info("Failed to get volume range. Falling back to software volume control.");
1274 else if (u->hw_volume_min >= u->hw_volume_max)
1275 pa_log_warn("Your kernel driver is broken: it reports a volume range from %li to %li which makes no sense.", u->hw_volume_min, u->hw_volume_max);
1277 pa_log_info("Volume ranges from %li to %li.", u->hw_volume_min, u->hw_volume_max);
1282 if (ignore_dB || snd_mixer_selem_get_capture_dB_range(u->mixer_elem, &u->hw_dB_min, &u->hw_dB_max) < 0)
1283 pa_log_info("Mixer doesn't support dB information or data is ignored.");
1285 #ifdef HAVE_VALGRIND_MEMCHECK_H
1286 VALGRIND_MAKE_MEM_DEFINED(&u->hw_dB_min, sizeof(u->hw_dB_min));
1287 VALGRIND_MAKE_MEM_DEFINED(&u->hw_dB_max, sizeof(u->hw_dB_max));
1290 if (u->hw_dB_min >= u->hw_dB_max)
1291 pa_log_warn("Your kernel driver is broken: it reports a volume range from %0.2f dB to %0.2f dB which makes no sense.", (double) u->hw_dB_min/100.0, (double) u->hw_dB_max/100.0);
1293 pa_log_info("Volume ranges from %0.2f dB to %0.2f dB.", (double) u->hw_dB_min/100.0, (double) u->hw_dB_max/100.0);
1294 u->hw_dB_supported = TRUE;
1296 if (u->hw_dB_max > 0) {
1297 u->source->base_volume = pa_sw_volume_from_dB(- (double) u->hw_dB_max/100.0);
1298 pa_log_info("Fixing base volume to %0.2f dB", pa_sw_volume_to_dB(u->source->base_volume));
1300 pa_log_info("No particular base volume set, fixing to 0 dB");
1304 if (!u->hw_dB_supported &&
1305 u->hw_volume_max - u->hw_volume_min < 3) {
1307 pa_log_info("Device has less than 4 volume levels. Falling back to software volume control.");
1313 u->mixer_seperate_channels = pa_alsa_calc_mixer_map(u->mixer_elem, &u->source->channel_map, u->mixer_map, FALSE) >= 0;
1315 u->source->get_volume = source_get_volume_cb;
1316 u->source->set_volume = source_set_volume_cb;
1317 u->source->flags |= PA_SOURCE_HW_VOLUME_CTRL | (u->hw_dB_supported ? PA_SOURCE_DECIBEL_VOLUME : 0);
1318 pa_log_info("Using hardware volume control. Hardware dB scale %s.", u->hw_dB_supported ? "supported" : "not supported");
1320 if (!u->hw_dB_supported)
1321 u->source->n_volume_steps = u->hw_volume_max - u->hw_volume_min + 1;
1323 pa_log_info("Using software volume control.");
1326 if (snd_mixer_selem_has_capture_switch(u->mixer_elem)) {
1327 u->source->get_mute = source_get_mute_cb;
1328 u->source->set_mute = source_set_mute_cb;
1329 u->source->flags |= PA_SOURCE_HW_MUTE_CTRL;
1331 pa_log_info("Using software mute control.");
1333 u->mixer_fdl = pa_alsa_fdlist_new();
1335 if (pa_alsa_fdlist_set_mixer(u->mixer_fdl, u->mixer_handle, u->core->mainloop) < 0) {
1336 pa_log("Failed to initialize file descriptor monitoring");
1340 snd_mixer_elem_set_callback(u->mixer_elem, mixer_callback);
1341 snd_mixer_elem_set_callback_private(u->mixer_elem, u);
1346 pa_source *pa_alsa_source_new(pa_module *m, pa_modargs *ma, const char*driver, pa_card *card, const pa_alsa_profile_info *profile) {
1348 struct userdata *u = NULL;
1349 const char *dev_id = NULL;
1350 pa_sample_spec ss, requested_ss;
1352 uint32_t nfrags, hwbuf_size, frag_size, tsched_size, tsched_watermark;
1353 snd_pcm_uframes_t period_frames, tsched_frames;
1355 pa_bool_t use_mmap = TRUE, b, use_tsched = TRUE, d, ignore_dB = FALSE;
1356 pa_source_new_data data;
1361 ss = m->core->default_sample_spec;
1362 map = m->core->default_channel_map;
1363 if (pa_modargs_get_sample_spec_and_channel_map(ma, &ss, &map, PA_CHANNEL_MAP_ALSA) < 0) {
1364 pa_log("Failed to parse sample specification");
1369 frame_size = pa_frame_size(&ss);
1371 nfrags = m->core->default_n_fragments;
1372 frag_size = (uint32_t) pa_usec_to_bytes(m->core->default_fragment_size_msec*PA_USEC_PER_MSEC, &ss);
1374 frag_size = (uint32_t) frame_size;
1375 tsched_size = (uint32_t) pa_usec_to_bytes(DEFAULT_TSCHED_BUFFER_USEC, &ss);
1376 tsched_watermark = (uint32_t) pa_usec_to_bytes(DEFAULT_TSCHED_WATERMARK_USEC, &ss);
1378 if (pa_modargs_get_value_u32(ma, "fragments", &nfrags) < 0 ||
1379 pa_modargs_get_value_u32(ma, "fragment_size", &frag_size) < 0 ||
1380 pa_modargs_get_value_u32(ma, "tsched_buffer_size", &tsched_size) < 0 ||
1381 pa_modargs_get_value_u32(ma, "tsched_buffer_watermark", &tsched_watermark) < 0) {
1382 pa_log("Failed to parse buffer metrics");
1386 hwbuf_size = frag_size * nfrags;
1387 period_frames = frag_size/frame_size;
1388 tsched_frames = tsched_size/frame_size;
1390 if (pa_modargs_get_value_boolean(ma, "mmap", &use_mmap) < 0) {
1391 pa_log("Failed to parse mmap argument.");
1395 if (pa_modargs_get_value_boolean(ma, "tsched", &use_tsched) < 0) {
1396 pa_log("Failed to parse timer_scheduling argument.");
1400 if (pa_modargs_get_value_boolean(ma, "ignore_dB", &ignore_dB) < 0) {
1401 pa_log("Failed to parse ignore_dB argument.");
1405 if (use_tsched && !pa_rtclock_hrtimer()) {
1406 pa_log_notice("Disabling timer-based scheduling because high-resolution timers are not available from the kernel.");
1410 u = pa_xnew0(struct userdata, 1);
1413 u->use_mmap = use_mmap;
1414 u->use_tsched = use_tsched;
1415 u->rtpoll = pa_rtpoll_new();
1416 pa_thread_mq_init(&u->thread_mq, m->core->mainloop, u->rtpoll);
1417 u->alsa_rtpoll_item = NULL;
1419 u->smoother = pa_smoother_new(DEFAULT_TSCHED_WATERMARK_USEC*2, DEFAULT_TSCHED_WATERMARK_USEC*2, TRUE, 5);
1420 pa_smoother_set_time_offset(u->smoother, pa_rtclock_usec());
1422 if (reserve_init(u, pa_modargs_get_value(
1424 pa_modargs_get_value(ma, "device", DEFAULT_DEVICE))) < 0)
1432 if (!(dev_id = pa_modargs_get_value(ma, "device_id", NULL))) {
1433 pa_log("device_id= not set");
1437 if (!(u->pcm_handle = pa_alsa_open_by_device_id_profile(
1441 SND_PCM_STREAM_CAPTURE,
1442 &nfrags, &period_frames, tsched_frames,
1446 } else if ((dev_id = pa_modargs_get_value(ma, "device_id", NULL))) {
1448 if (!(u->pcm_handle = pa_alsa_open_by_device_id_auto(
1452 SND_PCM_STREAM_CAPTURE,
1453 &nfrags, &period_frames, tsched_frames,
1459 if (!(u->pcm_handle = pa_alsa_open_by_device_string(
1460 pa_modargs_get_value(ma, "device", DEFAULT_DEVICE),
1463 SND_PCM_STREAM_CAPTURE,
1464 &nfrags, &period_frames, tsched_frames,
1469 pa_assert(u->device_name);
1470 pa_log_info("Successfully opened device %s.", u->device_name);
1473 pa_log_info("Selected configuration '%s' (%s).", profile->description, profile->name);
1475 if (use_mmap && !b) {
1476 pa_log_info("Device doesn't support mmap(), falling back to UNIX read/write mode.");
1477 u->use_mmap = use_mmap = FALSE;
1480 if (use_tsched && (!b || !d)) {
1481 pa_log_info("Cannot enable timer-based scheduling, falling back to sound IRQ scheduling.");
1482 u->use_tsched = use_tsched = FALSE;
1486 pa_log_info("Successfully enabled mmap() mode.");
1489 pa_log_info("Successfully enabled timer-based scheduling mode.");
1491 /* ALSA might tweak the sample spec, so recalculate the frame size */
1492 frame_size = pa_frame_size(&ss);
1494 pa_alsa_find_mixer_and_elem(u->pcm_handle, &u->mixer_handle, &u->mixer_elem);
1496 pa_source_new_data_init(&data);
1497 data.driver = driver;
1500 set_source_name(&data, ma, dev_id, u->device_name);
1501 pa_source_new_data_set_sample_spec(&data, &ss);
1502 pa_source_new_data_set_channel_map(&data, &map);
1504 pa_alsa_init_proplist_pcm(m->core, data.proplist, u->pcm_handle);
1505 pa_proplist_sets(data.proplist, PA_PROP_DEVICE_STRING, u->device_name);
1506 pa_proplist_setf(data.proplist, PA_PROP_DEVICE_BUFFERING_BUFFER_SIZE, "%lu", (unsigned long) (period_frames * frame_size * nfrags));
1507 pa_proplist_setf(data.proplist, PA_PROP_DEVICE_BUFFERING_FRAGMENT_SIZE, "%lu", (unsigned long) (period_frames * frame_size));
1508 pa_proplist_sets(data.proplist, PA_PROP_DEVICE_ACCESS_MODE, u->use_tsched ? "mmap+timer" : (u->use_mmap ? "mmap" : "serial"));
1511 pa_proplist_sets(data.proplist, PA_PROP_DEVICE_PROFILE_NAME, profile->name);
1512 pa_proplist_sets(data.proplist, PA_PROP_DEVICE_PROFILE_DESCRIPTION, profile->description);
1515 pa_alsa_init_description(data.proplist);
1517 u->source = pa_source_new(m->core, &data, PA_SOURCE_HARDWARE|PA_SOURCE_LATENCY);
1518 pa_source_new_data_done(&data);
1521 pa_log("Failed to create source object");
1525 u->source->parent.process_msg = source_process_msg;
1526 u->source->update_requested_latency = source_update_requested_latency_cb;
1527 u->source->set_state = source_set_state_cb;
1528 u->source->userdata = u;
1530 pa_source_set_asyncmsgq(u->source, u->thread_mq.inq);
1531 pa_source_set_rtpoll(u->source, u->rtpoll);
1533 u->frame_size = frame_size;
1534 u->fragment_size = frag_size = (uint32_t) (period_frames * frame_size);
1535 u->nfragments = nfrags;
1536 u->hwbuf_size = u->fragment_size * nfrags;
1537 u->tsched_watermark = pa_usec_to_bytes_round_up(pa_bytes_to_usec_round_up(tsched_watermark, &requested_ss), &u->source->sample_spec);
1538 pa_cvolume_mute(&u->hardware_volume, u->source->sample_spec.channels);
1541 fix_min_sleep_wakeup(u);
1542 fix_tsched_watermark(u);
1544 u->watermark_step = pa_usec_to_bytes(TSCHED_WATERMARK_STEP_USEC, &u->source->sample_spec);
1547 pa_source_set_latency_range(u->source,
1548 use_tsched ? (pa_usec_t) -1 : pa_bytes_to_usec(u->hwbuf_size, &ss),
1549 pa_bytes_to_usec(u->hwbuf_size, &ss));
1551 pa_log_info("Using %u fragments of size %lu bytes, buffer time is %0.2fms",
1552 nfrags, (long unsigned) u->fragment_size,
1553 (double) pa_bytes_to_usec(u->hwbuf_size, &ss) / PA_USEC_PER_MSEC);
1556 pa_log_info("Time scheduling watermark is %0.2fms",
1557 (double) pa_bytes_to_usec(u->tsched_watermark, &ss) / PA_USEC_PER_MSEC);
1561 if (update_sw_params(u) < 0)
1564 if (setup_mixer(u, ignore_dB) < 0)
1567 pa_alsa_dump(u->pcm_handle);
1569 if (!(u->thread = pa_thread_new(thread_func, u))) {
1570 pa_log("Failed to create thread.");
1573 /* Get initial mixer settings */
1574 if (data.volume_is_set) {
1575 if (u->source->set_volume)
1576 u->source->set_volume(u->source);
1578 if (u->source->get_volume)
1579 u->source->get_volume(u->source);
1582 if (data.muted_is_set) {
1583 if (u->source->set_mute)
1584 u->source->set_mute(u->source);
1586 if (u->source->get_mute)
1587 u->source->get_mute(u->source);
1590 pa_source_put(u->source);
1601 static void userdata_free(struct userdata *u) {
1605 pa_source_unlink(u->source);
1608 pa_asyncmsgq_send(u->thread_mq.inq, NULL, PA_MESSAGE_SHUTDOWN, NULL, 0, NULL);
1609 pa_thread_free(u->thread);
1612 pa_thread_mq_done(&u->thread_mq);
1615 pa_source_unref(u->source);
1617 if (u->alsa_rtpoll_item)
1618 pa_rtpoll_item_free(u->alsa_rtpoll_item);
1621 pa_rtpoll_free(u->rtpoll);
1624 pa_alsa_fdlist_free(u->mixer_fdl);
1626 if (u->mixer_handle)
1627 snd_mixer_close(u->mixer_handle);
1629 if (u->pcm_handle) {
1630 snd_pcm_drop(u->pcm_handle);
1631 snd_pcm_close(u->pcm_handle);
1635 pa_smoother_free(u->smoother);
1639 pa_xfree(u->device_name);
1643 void pa_alsa_source_free(pa_source *s) {
1646 pa_source_assert_ref(s);
1647 pa_assert_se(u = s->userdata);