From 6031546f6660e06e05d0b40a4dbc0c8769eb10a6 Mon Sep 17 00:00:00 2001 From: Uoti Urpala Date: Sat, 28 Jul 2012 18:24:30 +0300 Subject: [PATCH] sink-input: Fix underrun_for calculation when resampling. pa_sink_input_seek() calculates output lenth (slength) and corresponding input length (ilength). During an underrun, the function generates slength bytes of silence and adds ilength to the underrun_for value. However, the ilength value may be shortened to match resampler limits, and there's no corresponding adjustment to slength. Thus, the length of the generated silence is longer than resampler output would have been, and underrun_for should be increased by more than the limited ilength. This error makes the user-visible since_underrun field in struct pa_timing_info too small. Fix by using the original value calculated before limiting in this case. --- src/pulsecore/sink-input.c | 7 ++++++- 1 file changed, 6 insertions(+), 1 deletion(-) diff --git a/src/pulsecore/sink-input.c b/src/pulsecore/sink-input.c index 4db20175c..93887881f 100644 --- a/src/pulsecore/sink-input.c +++ b/src/pulsecore/sink-input.c @@ -783,6 +783,7 @@ void pa_sink_input_peek(pa_sink_input *i, size_t slength /* in sink frames */, p pa_bool_t volume_is_norm; size_t block_size_max_sink, block_size_max_sink_input; size_t ilength; + size_t ilength_full; pa_sink_input_assert_ref(i); pa_sink_input_assert_io_context(i); @@ -816,6 +817,10 @@ void pa_sink_input_peek(pa_sink_input *i, size_t slength /* in sink frames */, p } else ilength = slength; + /* Length corresponding to slength (without limiting to + * block_size_max_sink_input). */ + ilength_full = ilength; + if (ilength > block_size_max_sink_input) ilength = block_size_max_sink_input; @@ -843,7 +848,7 @@ void pa_sink_input_peek(pa_sink_input *i, size_t slength /* in sink frames */, p pa_memblockq_seek(i->thread_info.render_memblockq, (int64_t) slength, PA_SEEK_RELATIVE, TRUE); i->thread_info.playing_for = 0; if (i->thread_info.underrun_for != (uint64_t) -1) - i->thread_info.underrun_for += ilength; + i->thread_info.underrun_for += ilength_full; break; }