2 This file is part of PulseAudio.
4 Copyright 2004-2006 Lennart Poettering
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.1 of the License,
9 or (at your option) any later version.
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.
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
28 #ifdef HAVE_LIBSAMPLERATE
29 #include <samplerate.h>
33 #include <speex/speex_resampler.h>
36 #include <pulse/xmalloc.h>
37 #include <pulsecore/sconv.h>
38 #include <pulsecore/log.h>
39 #include <pulsecore/macro.h>
40 #include <pulsecore/strbuf.h>
41 #include <pulsecore/remap.h>
43 #include "ffmpeg/avcodec.h"
45 #include "resampler.h"
47 /* Number of samples of extra space we allow the resamplers to return */
48 #define EXTRA_FRAMES 128
51 pa_resample_method_t method
;
52 pa_resample_flags_t flags
;
54 pa_sample_spec i_ss
, o_ss
;
55 pa_channel_map i_cm
, o_cm
;
56 size_t i_fz
, o_fz
, w_sz
;
59 pa_memchunk buf1
, buf2
, buf3
, buf4
;
60 unsigned buf1_samples
, buf2_samples
, buf3_samples
, buf4_samples
;
62 pa_sample_format_t work_format
;
64 pa_convert_func_t to_work_format_func
;
65 pa_convert_func_t from_work_format_func
;
68 pa_bool_t map_required
;
70 void (*impl_free
)(pa_resampler
*r
);
71 void (*impl_update_rates
)(pa_resampler
*r
);
72 void (*impl_resample
)(pa_resampler
*r
, const pa_memchunk
*in
, unsigned in_samples
, pa_memchunk
*out
, unsigned *out_samples
);
73 void (*impl_reset
)(pa_resampler
*r
);
75 struct { /* data specific to the trivial resampler */
80 struct { /* data specific to the peak finder pseudo resampler */
84 float max_f
[PA_CHANNELS_MAX
];
85 int16_t max_i
[PA_CHANNELS_MAX
];
89 #ifdef HAVE_LIBSAMPLERATE
90 struct { /* data specific to libsamplerate */
96 struct { /* data specific to speex */
97 SpeexResamplerState
* state
;
101 struct { /* data specific to ffmpeg */
102 struct AVResampleContext
*state
;
103 pa_memchunk buf
[PA_CHANNELS_MAX
];
107 static int copy_init(pa_resampler
*r
);
108 static int trivial_init(pa_resampler
*r
);
110 static int speex_init(pa_resampler
*r
);
112 static int ffmpeg_init(pa_resampler
*r
);
113 static int peaks_init(pa_resampler
*r
);
114 #ifdef HAVE_LIBSAMPLERATE
115 static int libsamplerate_init(pa_resampler
*r
);
118 static void calc_map_table(pa_resampler
*r
);
120 static int (* const init_table
[])(pa_resampler
*r
) = {
121 #ifdef HAVE_LIBSAMPLERATE
122 [PA_RESAMPLER_SRC_SINC_BEST_QUALITY
] = libsamplerate_init
,
123 [PA_RESAMPLER_SRC_SINC_MEDIUM_QUALITY
] = libsamplerate_init
,
124 [PA_RESAMPLER_SRC_SINC_FASTEST
] = libsamplerate_init
,
125 [PA_RESAMPLER_SRC_ZERO_ORDER_HOLD
] = libsamplerate_init
,
126 [PA_RESAMPLER_SRC_LINEAR
] = libsamplerate_init
,
128 [PA_RESAMPLER_SRC_SINC_BEST_QUALITY
] = NULL
,
129 [PA_RESAMPLER_SRC_SINC_MEDIUM_QUALITY
] = NULL
,
130 [PA_RESAMPLER_SRC_SINC_FASTEST
] = NULL
,
131 [PA_RESAMPLER_SRC_ZERO_ORDER_HOLD
] = NULL
,
132 [PA_RESAMPLER_SRC_LINEAR
] = NULL
,
134 [PA_RESAMPLER_TRIVIAL
] = trivial_init
,
136 [PA_RESAMPLER_SPEEX_FLOAT_BASE
+0] = speex_init
,
137 [PA_RESAMPLER_SPEEX_FLOAT_BASE
+1] = speex_init
,
138 [PA_RESAMPLER_SPEEX_FLOAT_BASE
+2] = speex_init
,
139 [PA_RESAMPLER_SPEEX_FLOAT_BASE
+3] = speex_init
,
140 [PA_RESAMPLER_SPEEX_FLOAT_BASE
+4] = speex_init
,
141 [PA_RESAMPLER_SPEEX_FLOAT_BASE
+5] = speex_init
,
142 [PA_RESAMPLER_SPEEX_FLOAT_BASE
+6] = speex_init
,
143 [PA_RESAMPLER_SPEEX_FLOAT_BASE
+7] = speex_init
,
144 [PA_RESAMPLER_SPEEX_FLOAT_BASE
+8] = speex_init
,
145 [PA_RESAMPLER_SPEEX_FLOAT_BASE
+9] = speex_init
,
146 [PA_RESAMPLER_SPEEX_FLOAT_BASE
+10] = speex_init
,
147 [PA_RESAMPLER_SPEEX_FIXED_BASE
+0] = speex_init
,
148 [PA_RESAMPLER_SPEEX_FIXED_BASE
+1] = speex_init
,
149 [PA_RESAMPLER_SPEEX_FIXED_BASE
+2] = speex_init
,
150 [PA_RESAMPLER_SPEEX_FIXED_BASE
+3] = speex_init
,
151 [PA_RESAMPLER_SPEEX_FIXED_BASE
+4] = speex_init
,
152 [PA_RESAMPLER_SPEEX_FIXED_BASE
+5] = speex_init
,
153 [PA_RESAMPLER_SPEEX_FIXED_BASE
+6] = speex_init
,
154 [PA_RESAMPLER_SPEEX_FIXED_BASE
+7] = speex_init
,
155 [PA_RESAMPLER_SPEEX_FIXED_BASE
+8] = speex_init
,
156 [PA_RESAMPLER_SPEEX_FIXED_BASE
+9] = speex_init
,
157 [PA_RESAMPLER_SPEEX_FIXED_BASE
+10] = speex_init
,
159 [PA_RESAMPLER_SPEEX_FLOAT_BASE
+0] = NULL
,
160 [PA_RESAMPLER_SPEEX_FLOAT_BASE
+1] = NULL
,
161 [PA_RESAMPLER_SPEEX_FLOAT_BASE
+2] = NULL
,
162 [PA_RESAMPLER_SPEEX_FLOAT_BASE
+3] = NULL
,
163 [PA_RESAMPLER_SPEEX_FLOAT_BASE
+4] = NULL
,
164 [PA_RESAMPLER_SPEEX_FLOAT_BASE
+5] = NULL
,
165 [PA_RESAMPLER_SPEEX_FLOAT_BASE
+6] = NULL
,
166 [PA_RESAMPLER_SPEEX_FLOAT_BASE
+7] = NULL
,
167 [PA_RESAMPLER_SPEEX_FLOAT_BASE
+8] = NULL
,
168 [PA_RESAMPLER_SPEEX_FLOAT_BASE
+9] = NULL
,
169 [PA_RESAMPLER_SPEEX_FLOAT_BASE
+10] = NULL
,
170 [PA_RESAMPLER_SPEEX_FIXED_BASE
+0] = NULL
,
171 [PA_RESAMPLER_SPEEX_FIXED_BASE
+1] = NULL
,
172 [PA_RESAMPLER_SPEEX_FIXED_BASE
+2] = NULL
,
173 [PA_RESAMPLER_SPEEX_FIXED_BASE
+3] = NULL
,
174 [PA_RESAMPLER_SPEEX_FIXED_BASE
+4] = NULL
,
175 [PA_RESAMPLER_SPEEX_FIXED_BASE
+5] = NULL
,
176 [PA_RESAMPLER_SPEEX_FIXED_BASE
+6] = NULL
,
177 [PA_RESAMPLER_SPEEX_FIXED_BASE
+7] = NULL
,
178 [PA_RESAMPLER_SPEEX_FIXED_BASE
+8] = NULL
,
179 [PA_RESAMPLER_SPEEX_FIXED_BASE
+9] = NULL
,
180 [PA_RESAMPLER_SPEEX_FIXED_BASE
+10] = NULL
,
182 [PA_RESAMPLER_FFMPEG
] = ffmpeg_init
,
183 [PA_RESAMPLER_AUTO
] = NULL
,
184 [PA_RESAMPLER_COPY
] = copy_init
,
185 [PA_RESAMPLER_PEAKS
] = peaks_init
,
188 pa_resampler
* pa_resampler_new(
190 const pa_sample_spec
*a
,
191 const pa_channel_map
*am
,
192 const pa_sample_spec
*b
,
193 const pa_channel_map
*bm
,
194 pa_resample_method_t method
,
195 pa_resample_flags_t flags
) {
197 pa_resampler
*r
= NULL
;
202 pa_assert(pa_sample_spec_valid(a
));
203 pa_assert(pa_sample_spec_valid(b
));
204 pa_assert(method
>= 0);
205 pa_assert(method
< PA_RESAMPLER_MAX
);
209 if (!(flags
& PA_RESAMPLER_VARIABLE_RATE
) && a
->rate
== b
->rate
) {
210 pa_log_info("Forcing resampler 'copy', because of fixed, identical sample rates.");
211 method
= PA_RESAMPLER_COPY
;
214 if (!pa_resample_method_supported(method
)) {
215 pa_log_warn("Support for resampler '%s' not compiled in, reverting to 'auto'.", pa_resample_method_to_string(method
));
216 method
= PA_RESAMPLER_AUTO
;
219 if (method
== PA_RESAMPLER_FFMPEG
&& (flags
& PA_RESAMPLER_VARIABLE_RATE
)) {
220 pa_log_info("Resampler 'ffmpeg' cannot do variable rate, reverting to resampler 'auto'.");
221 method
= PA_RESAMPLER_AUTO
;
224 if (method
== PA_RESAMPLER_COPY
&& ((flags
& PA_RESAMPLER_VARIABLE_RATE
) || a
->rate
!= b
->rate
)) {
225 pa_log_info("Resampler 'copy' cannot change sampling rate, reverting to resampler 'auto'.");
226 method
= PA_RESAMPLER_AUTO
;
229 if (method
== PA_RESAMPLER_AUTO
) {
231 method
= PA_RESAMPLER_SPEEX_FLOAT_BASE
+ 3;
233 method
= PA_RESAMPLER_FFMPEG
;
237 r
= pa_xnew(pa_resampler
, 1);
243 r
->impl_update_rates
= NULL
;
244 r
->impl_resample
= NULL
;
245 r
->impl_reset
= NULL
;
247 /* Fill sample specs */
251 /* set up the remap structure */
252 r
->remap
.i_ss
= &r
->i_ss
;
253 r
->remap
.o_ss
= &r
->o_ss
;
254 r
->remap
.format
= &r
->work_format
;
258 else if (!pa_channel_map_init_auto(&r
->i_cm
, r
->i_ss
.channels
, PA_CHANNEL_MAP_DEFAULT
))
263 else if (!pa_channel_map_init_auto(&r
->o_cm
, r
->o_ss
.channels
, PA_CHANNEL_MAP_DEFAULT
))
266 r
->i_fz
= pa_frame_size(a
);
267 r
->o_fz
= pa_frame_size(b
);
269 pa_memchunk_reset(&r
->buf1
);
270 pa_memchunk_reset(&r
->buf2
);
271 pa_memchunk_reset(&r
->buf3
);
272 pa_memchunk_reset(&r
->buf4
);
274 r
->buf1_samples
= r
->buf2_samples
= r
->buf3_samples
= r
->buf4_samples
= 0;
278 pa_log_info("Using resampler '%s'", pa_resample_method_to_string(method
));
280 if ((method
>= PA_RESAMPLER_SPEEX_FIXED_BASE
&& method
<= PA_RESAMPLER_SPEEX_FIXED_MAX
) ||
281 (method
== PA_RESAMPLER_FFMPEG
))
282 r
->work_format
= PA_SAMPLE_S16NE
;
283 else if (method
== PA_RESAMPLER_TRIVIAL
|| method
== PA_RESAMPLER_COPY
|| method
== PA_RESAMPLER_PEAKS
) {
285 if (r
->map_required
|| a
->format
!= b
->format
|| method
== PA_RESAMPLER_PEAKS
) {
287 if (a
->format
== PA_SAMPLE_S32NE
|| a
->format
== PA_SAMPLE_S32RE
||
288 a
->format
== PA_SAMPLE_FLOAT32NE
|| a
->format
== PA_SAMPLE_FLOAT32RE
||
289 a
->format
== PA_SAMPLE_S24NE
|| a
->format
== PA_SAMPLE_S24RE
||
290 a
->format
== PA_SAMPLE_S24_32NE
|| a
->format
== PA_SAMPLE_S24_32RE
||
291 b
->format
== PA_SAMPLE_S32NE
|| b
->format
== PA_SAMPLE_S32RE
||
292 b
->format
== PA_SAMPLE_FLOAT32NE
|| b
->format
== PA_SAMPLE_FLOAT32RE
||
293 b
->format
== PA_SAMPLE_S24NE
|| b
->format
== PA_SAMPLE_S24RE
||
294 b
->format
== PA_SAMPLE_S24_32NE
|| b
->format
== PA_SAMPLE_S24_32RE
)
295 r
->work_format
= PA_SAMPLE_FLOAT32NE
;
297 r
->work_format
= PA_SAMPLE_S16NE
;
300 r
->work_format
= a
->format
;
303 r
->work_format
= PA_SAMPLE_FLOAT32NE
;
305 pa_log_info("Using %s as working format.", pa_sample_format_to_string(r
->work_format
));
307 r
->w_sz
= pa_sample_size_of_format(r
->work_format
);
309 if (r
->i_ss
.format
== r
->work_format
)
310 r
->to_work_format_func
= NULL
;
311 else if (r
->work_format
== PA_SAMPLE_FLOAT32NE
) {
312 if (!(r
->to_work_format_func
= pa_get_convert_to_float32ne_function(r
->i_ss
.format
)))
315 pa_assert(r
->work_format
== PA_SAMPLE_S16NE
);
316 if (!(r
->to_work_format_func
= pa_get_convert_to_s16ne_function(r
->i_ss
.format
)))
320 if (r
->o_ss
.format
== r
->work_format
)
321 r
->from_work_format_func
= NULL
;
322 else if (r
->work_format
== PA_SAMPLE_FLOAT32NE
) {
323 if (!(r
->from_work_format_func
= pa_get_convert_from_float32ne_function(r
->o_ss
.format
)))
326 pa_assert(r
->work_format
== PA_SAMPLE_S16NE
);
327 if (!(r
->from_work_format_func
= pa_get_convert_from_s16ne_function(r
->o_ss
.format
)))
331 /* initialize implementation */
332 if (init_table
[method
](r
) < 0)
343 void pa_resampler_free(pa_resampler
*r
) {
349 if (r
->buf1
.memblock
)
350 pa_memblock_unref(r
->buf1
.memblock
);
351 if (r
->buf2
.memblock
)
352 pa_memblock_unref(r
->buf2
.memblock
);
353 if (r
->buf3
.memblock
)
354 pa_memblock_unref(r
->buf3
.memblock
);
355 if (r
->buf4
.memblock
)
356 pa_memblock_unref(r
->buf4
.memblock
);
361 void pa_resampler_set_input_rate(pa_resampler
*r
, uint32_t rate
) {
365 if (r
->i_ss
.rate
== rate
)
370 r
->impl_update_rates(r
);
373 void pa_resampler_set_output_rate(pa_resampler
*r
, uint32_t rate
) {
377 if (r
->o_ss
.rate
== rate
)
382 r
->impl_update_rates(r
);
385 size_t pa_resampler_request(pa_resampler
*r
, size_t out_length
) {
388 /* Let's round up here */
390 return (((((out_length
+ r
->o_fz
-1) / r
->o_fz
) * r
->i_ss
.rate
) + r
->o_ss
.rate
-1) / r
->o_ss
.rate
) * r
->i_fz
;
393 size_t pa_resampler_result(pa_resampler
*r
, size_t in_length
) {
396 /* Let's round up here */
398 return (((((in_length
+ r
->i_fz
-1) / r
->i_fz
) * r
->o_ss
.rate
) + r
->i_ss
.rate
-1) / r
->i_ss
.rate
) * r
->o_fz
;
401 size_t pa_resampler_max_block_size(pa_resampler
*r
) {
402 size_t block_size_max
;
408 block_size_max
= pa_mempool_block_size_max(r
->mempool
);
410 /* We deduce the "largest" sample spec we're using during the
412 ss
.channels
= (uint8_t) (PA_MAX(r
->i_ss
.channels
, r
->o_ss
.channels
));
414 /* We silently assume that the format enum is ordered by size */
415 ss
.format
= PA_MAX(r
->i_ss
.format
, r
->o_ss
.format
);
416 ss
.format
= PA_MAX(ss
.format
, r
->work_format
);
418 ss
.rate
= PA_MAX(r
->i_ss
.rate
, r
->o_ss
.rate
);
420 fs
= pa_frame_size(&ss
);
422 return (((block_size_max
/fs
- EXTRA_FRAMES
)*r
->i_ss
.rate
)/ss
.rate
)*r
->i_fz
;
425 void pa_resampler_reset(pa_resampler
*r
) {
432 pa_resample_method_t
pa_resampler_get_method(pa_resampler
*r
) {
438 const pa_channel_map
* pa_resampler_input_channel_map(pa_resampler
*r
) {
444 const pa_sample_spec
* pa_resampler_input_sample_spec(pa_resampler
*r
) {
450 const pa_channel_map
* pa_resampler_output_channel_map(pa_resampler
*r
) {
456 const pa_sample_spec
* pa_resampler_output_sample_spec(pa_resampler
*r
) {
462 static const char * const resample_methods
[] = {
463 "src-sinc-best-quality",
464 "src-sinc-medium-quality",
466 "src-zero-order-hold",
497 const char *pa_resample_method_to_string(pa_resample_method_t m
) {
499 if (m
< 0 || m
>= PA_RESAMPLER_MAX
)
502 return resample_methods
[m
];
505 int pa_resample_method_supported(pa_resample_method_t m
) {
507 if (m
< 0 || m
>= PA_RESAMPLER_MAX
)
510 #ifndef HAVE_LIBSAMPLERATE
511 if (m
<= PA_RESAMPLER_SRC_LINEAR
)
516 if (m
>= PA_RESAMPLER_SPEEX_FLOAT_BASE
&& m
<= PA_RESAMPLER_SPEEX_FLOAT_MAX
)
518 if (m
>= PA_RESAMPLER_SPEEX_FIXED_BASE
&& m
<= PA_RESAMPLER_SPEEX_FIXED_MAX
)
525 pa_resample_method_t
pa_parse_resample_method(const char *string
) {
526 pa_resample_method_t m
;
530 for (m
= 0; m
< PA_RESAMPLER_MAX
; m
++)
531 if (!strcmp(string
, resample_methods
[m
]))
534 if (!strcmp(string
, "speex-fixed"))
535 return PA_RESAMPLER_SPEEX_FIXED_BASE
+ 3;
537 if (!strcmp(string
, "speex-float"))
538 return PA_RESAMPLER_SPEEX_FLOAT_BASE
+ 3;
540 return PA_RESAMPLER_INVALID
;
543 static pa_bool_t
on_left(pa_channel_position_t p
) {
546 p
== PA_CHANNEL_POSITION_FRONT_LEFT
||
547 p
== PA_CHANNEL_POSITION_REAR_LEFT
||
548 p
== PA_CHANNEL_POSITION_FRONT_LEFT_OF_CENTER
||
549 p
== PA_CHANNEL_POSITION_SIDE_LEFT
||
550 p
== PA_CHANNEL_POSITION_TOP_FRONT_LEFT
||
551 p
== PA_CHANNEL_POSITION_TOP_REAR_LEFT
;
554 static pa_bool_t
on_right(pa_channel_position_t p
) {
557 p
== PA_CHANNEL_POSITION_FRONT_RIGHT
||
558 p
== PA_CHANNEL_POSITION_REAR_RIGHT
||
559 p
== PA_CHANNEL_POSITION_FRONT_RIGHT_OF_CENTER
||
560 p
== PA_CHANNEL_POSITION_SIDE_RIGHT
||
561 p
== PA_CHANNEL_POSITION_TOP_FRONT_RIGHT
||
562 p
== PA_CHANNEL_POSITION_TOP_REAR_RIGHT
;
565 static pa_bool_t
on_center(pa_channel_position_t p
) {
568 p
== PA_CHANNEL_POSITION_FRONT_CENTER
||
569 p
== PA_CHANNEL_POSITION_REAR_CENTER
||
570 p
== PA_CHANNEL_POSITION_TOP_CENTER
||
571 p
== PA_CHANNEL_POSITION_TOP_FRONT_CENTER
||
572 p
== PA_CHANNEL_POSITION_TOP_REAR_CENTER
;
575 static pa_bool_t
on_lfe(pa_channel_position_t p
) {
577 p
== PA_CHANNEL_POSITION_LFE
;
580 static pa_bool_t
on_front(pa_channel_position_t p
) {
582 p
== PA_CHANNEL_POSITION_FRONT_LEFT
||
583 p
== PA_CHANNEL_POSITION_FRONT_RIGHT
||
584 p
== PA_CHANNEL_POSITION_FRONT_CENTER
||
585 p
== PA_CHANNEL_POSITION_TOP_FRONT_LEFT
||
586 p
== PA_CHANNEL_POSITION_TOP_FRONT_RIGHT
||
587 p
== PA_CHANNEL_POSITION_TOP_FRONT_CENTER
||
588 p
== PA_CHANNEL_POSITION_FRONT_LEFT_OF_CENTER
||
589 p
== PA_CHANNEL_POSITION_FRONT_RIGHT_OF_CENTER
;
592 static pa_bool_t
on_rear(pa_channel_position_t p
) {
594 p
== PA_CHANNEL_POSITION_REAR_LEFT
||
595 p
== PA_CHANNEL_POSITION_REAR_RIGHT
||
596 p
== PA_CHANNEL_POSITION_REAR_CENTER
||
597 p
== PA_CHANNEL_POSITION_TOP_REAR_LEFT
||
598 p
== PA_CHANNEL_POSITION_TOP_REAR_RIGHT
||
599 p
== PA_CHANNEL_POSITION_TOP_REAR_CENTER
;
602 static pa_bool_t
on_side(pa_channel_position_t p
) {
604 p
== PA_CHANNEL_POSITION_SIDE_LEFT
||
605 p
== PA_CHANNEL_POSITION_SIDE_RIGHT
||
606 p
== PA_CHANNEL_POSITION_TOP_CENTER
;
616 static int front_rear_side(pa_channel_position_t p
) {
626 static void calc_map_table(pa_resampler
*r
) {
629 pa_bool_t ic_connected
[PA_CHANNELS_MAX
];
637 if (!(r
->map_required
= (r
->i_ss
.channels
!= r
->o_ss
.channels
|| (!(r
->flags
& PA_RESAMPLER_NO_REMAP
) && !pa_channel_map_equal(&r
->i_cm
, &r
->o_cm
)))))
642 n_oc
= r
->o_ss
.channels
;
643 n_ic
= r
->i_ss
.channels
;
645 memset(m
->map_table_f
, 0, sizeof(m
->map_table_f
));
646 memset(m
->map_table_i
, 0, sizeof(m
->map_table_i
));
648 memset(ic_connected
, 0, sizeof(ic_connected
));
649 remix
= (r
->flags
& (PA_RESAMPLER_NO_REMAP
|PA_RESAMPLER_NO_REMIX
)) == 0;
651 for (oc
= 0; oc
< n_oc
; oc
++) {
652 pa_bool_t oc_connected
= FALSE
;
653 pa_channel_position_t b
= r
->o_cm
.map
[oc
];
655 for (ic
= 0; ic
< n_ic
; ic
++) {
656 pa_channel_position_t a
= r
->i_cm
.map
[ic
];
658 if (r
->flags
& PA_RESAMPLER_NO_REMAP
) {
659 /* We shall not do any remapping. Hence, just check by index */
662 m
->map_table_f
[oc
][ic
] = 1.0;
667 if (r
->flags
& PA_RESAMPLER_NO_REMIX
) {
668 /* We shall not do any remixing. Hence, just check by name */
671 m
->map_table_f
[oc
][ic
] = 1.0;
678 /* OK, we shall do the full monty: upmixing and
679 * downmixing. Our algorithm is relatively simple, does
680 * not do spacialization, delay elements or apply lowpass
681 * filters for LFE. Patches are always welcome,
682 * though. Oh, and it doesn't do any matrix
683 * decoding. (Which probably wouldn't make any sense
686 * This code is not idempotent: downmixing an upmixed
687 * stereo stream is not identical to the original. The
688 * volume will not match, and the two channels will be a
689 * linear combination of both.
691 * This is loosely based on random suggestions found on the
692 * Internet, such as this:
693 * http://www.halfgaar.net/surround-sound-in-linux and the
696 * The algorithm works basically like this:
698 * 1) Connect all channels with matching names.
701 * S:Mono: Copy into all D:channels
702 * D:Mono: Copy in all S:channels
704 * 3) Mix D:Left, D:Right:
705 * D:Left: If not connected, avg all S:Left
706 * D:Right: If not connected, avg all S:Right
709 * If not connected, avg all S:Center
710 * If still not connected, avg all S:Left, S:Right
713 * If not connected, avg all S:*
715 * 6) Make sure S:Left/S:Right is used: S:Left/S:Right: If
716 * not connected, mix into all D:left and all D:right
717 * channels. Gain is 0.1, the current left and right
718 * should be multiplied by 0.9.
720 * 7) Make sure S:Center, S:LFE is used:
722 * S:Center, S:LFE: If not connected, mix into all
723 * D:left, all D:right, all D:center channels, gain is
724 * 0.375. The current (as result of 1..6) factors
725 * should be multiplied by 0.75. (Alt. suggestion: 0.25
726 * vs. 0.5) If C-front is only mixed into
727 * L-front/R-front if available, otherwise into all L/R
728 * channels. Similarly for C-rear.
730 * S: and D: shall relate to the source resp. destination channels.
732 * Rationale: 1, 2 are probably obvious. For 3: this
733 * copies front to rear if needed. For 4: we try to find
734 * some suitable C source for C, if we don't find any, we
735 * avg L and R. For 5: LFE is mixed from all channels. For
736 * 6: the rear channels should not be dropped entirely,
737 * however have only minimal impact. For 7: movies usually
738 * encode speech on the center channel. Thus we have to
739 * make sure this channel is distributed to L and R if not
740 * available in the output. Also, LFE is used to achieve a
741 * greater dynamic range, and thus we should try to do our
742 * best to pass it to L+R.
745 if (a
== b
|| a
== PA_CHANNEL_POSITION_MONO
|| b
== PA_CHANNEL_POSITION_MONO
) {
746 m
->map_table_f
[oc
][ic
] = 1.0;
749 ic_connected
[ic
] = TRUE
;
753 if (!oc_connected
&& remix
) {
754 /* OK, we shall remix */
756 /* Try to find matching input ports for this output port */
761 /* We are not connected and on the left side, let's
762 * average all left side input channels. */
764 for (ic
= 0; ic
< n_ic
; ic
++)
765 if (on_left(r
->i_cm
.map
[ic
]))
769 for (ic
= 0; ic
< n_ic
; ic
++)
770 if (on_left(r
->i_cm
.map
[ic
])) {
771 m
->map_table_f
[oc
][ic
] = 1.0f
/ (float) n
;
772 ic_connected
[ic
] = TRUE
;
775 /* We ignore the case where there is no left input
776 * channel. Something is really wrong in this case
779 } else if (on_right(b
)) {
782 /* We are not connected and on the right side, let's
783 * average all right side input channels. */
785 for (ic
= 0; ic
< n_ic
; ic
++)
786 if (on_right(r
->i_cm
.map
[ic
]))
790 for (ic
= 0; ic
< n_ic
; ic
++)
791 if (on_right(r
->i_cm
.map
[ic
])) {
792 m
->map_table_f
[oc
][ic
] = 1.0f
/ (float) n
;
793 ic_connected
[ic
] = TRUE
;
796 /* We ignore the case where there is no right input
797 * channel. Something is really wrong in this case
800 } else if (on_center(b
)) {
803 /* We are not connected and at the center. Let's
804 * average all center input channels. */
806 for (ic
= 0; ic
< n_ic
; ic
++)
807 if (on_center(r
->i_cm
.map
[ic
]))
811 for (ic
= 0; ic
< n_ic
; ic
++)
812 if (on_center(r
->i_cm
.map
[ic
])) {
813 m
->map_table_f
[oc
][ic
] = 1.0f
/ (float) n
;
814 ic_connected
[ic
] = TRUE
;
818 /* Hmm, no center channel around, let's synthesize
819 * it by mixing L and R.*/
823 for (ic
= 0; ic
< n_ic
; ic
++)
824 if (on_left(r
->i_cm
.map
[ic
]) || on_right(r
->i_cm
.map
[ic
]))
828 for (ic
= 0; ic
< n_ic
; ic
++)
829 if (on_left(r
->i_cm
.map
[ic
]) || on_right(r
->i_cm
.map
[ic
])) {
830 m
->map_table_f
[oc
][ic
] = 1.0f
/ (float) n
;
831 ic_connected
[ic
] = TRUE
;
834 /* We ignore the case where there is not even a
835 * left or right input channel. Something is
836 * really wrong in this case anyway. */
839 } else if (on_lfe(b
)) {
841 /* We are not connected and an LFE. Let's average all
842 * channels for LFE. */
844 for (ic
= 0; ic
< n_ic
; ic
++) {
846 if (!(r
->flags
& PA_RESAMPLER_NO_LFE
))
847 m
->map_table_f
[oc
][ic
] = 1.0f
/ (float) n_ic
;
849 m
->map_table_f
[oc
][ic
] = 0;
851 /* Please note that a channel connected to LFE
852 * doesn't really count as connected. */
860 ic_unconnected_left
= 0,
861 ic_unconnected_right
= 0,
862 ic_unconnected_center
= 0,
863 ic_unconnected_lfe
= 0;
865 for (ic
= 0; ic
< n_ic
; ic
++) {
866 pa_channel_position_t a
= r
->i_cm
.map
[ic
];
868 if (ic_connected
[ic
])
872 ic_unconnected_left
++;
873 else if (on_right(a
))
874 ic_unconnected_right
++;
875 else if (on_center(a
))
876 ic_unconnected_center
++;
878 ic_unconnected_lfe
++;
881 if (ic_unconnected_left
> 0) {
883 /* OK, so there are unconnected input channels on the
884 * left. Let's multiply all already connected channels on
885 * the left side by .9 and add in our averaged unconnected
886 * channels multiplied by .1 */
888 for (oc
= 0; oc
< n_oc
; oc
++) {
890 if (!on_left(r
->o_cm
.map
[oc
]))
893 for (ic
= 0; ic
< n_ic
; ic
++) {
895 if (ic_connected
[ic
]) {
896 m
->map_table_f
[oc
][ic
] *= .9f
;
900 if (on_left(r
->i_cm
.map
[ic
]))
901 m
->map_table_f
[oc
][ic
] = .1f
/ (float) ic_unconnected_left
;
906 if (ic_unconnected_right
> 0) {
908 /* OK, so there are unconnected input channels on the
909 * right. Let's multiply all already connected channels on
910 * the right side by .9 and add in our averaged unconnected
911 * channels multiplied by .1 */
913 for (oc
= 0; oc
< n_oc
; oc
++) {
915 if (!on_right(r
->o_cm
.map
[oc
]))
918 for (ic
= 0; ic
< n_ic
; ic
++) {
920 if (ic_connected
[ic
]) {
921 m
->map_table_f
[oc
][ic
] *= .9f
;
925 if (on_right(r
->i_cm
.map
[ic
]))
926 m
->map_table_f
[oc
][ic
] = .1f
/ (float) ic_unconnected_right
;
931 if (ic_unconnected_center
> 0) {
932 pa_bool_t mixed_in
= FALSE
;
934 /* OK, so there are unconnected input channels on the
935 * center. Let's multiply all already connected channels on
936 * the center side by .9 and add in our averaged unconnected
937 * channels multiplied by .1 */
939 for (oc
= 0; oc
< n_oc
; oc
++) {
941 if (!on_center(r
->o_cm
.map
[oc
]))
944 for (ic
= 0; ic
< n_ic
; ic
++) {
946 if (ic_connected
[ic
]) {
947 m
->map_table_f
[oc
][ic
] *= .9f
;
951 if (on_center(r
->i_cm
.map
[ic
])) {
952 m
->map_table_f
[oc
][ic
] = .1f
/ (float) ic_unconnected_center
;
959 unsigned ncenter
[PA_CHANNELS_MAX
];
960 pa_bool_t found_frs
[PA_CHANNELS_MAX
];
962 memset(ncenter
, 0, sizeof(ncenter
));
963 memset(found_frs
, 0, sizeof(found_frs
));
965 /* Hmm, as it appears there was no center channel we
966 could mix our center channel in. In this case, mix
967 it into left and right. Using .375 and 0.75 as
970 for (ic
= 0; ic
< n_ic
; ic
++) {
972 if (ic_connected
[ic
])
975 if (!on_center(r
->i_cm
.map
[ic
]))
978 for (oc
= 0; oc
< n_oc
; oc
++) {
980 if (!on_left(r
->o_cm
.map
[oc
]) && !on_right(r
->o_cm
.map
[oc
]))
983 if (front_rear_side(r
->i_cm
.map
[ic
]) == front_rear_side(r
->o_cm
.map
[oc
])) {
984 found_frs
[ic
] = TRUE
;
989 for (oc
= 0; oc
< n_oc
; oc
++) {
991 if (!on_left(r
->o_cm
.map
[oc
]) && !on_right(r
->o_cm
.map
[oc
]))
994 if (!found_frs
[ic
] || front_rear_side(r
->i_cm
.map
[ic
]) == front_rear_side(r
->o_cm
.map
[oc
]))
999 for (oc
= 0; oc
< n_oc
; oc
++) {
1001 if (!on_left(r
->o_cm
.map
[oc
]) && !on_right(r
->o_cm
.map
[oc
]))
1004 if (ncenter
[oc
] <= 0)
1007 for (ic
= 0; ic
< n_ic
; ic
++) {
1009 if (ic_connected
[ic
]) {
1010 m
->map_table_f
[oc
][ic
] *= .75f
;
1014 if (!on_center(r
->i_cm
.map
[ic
]))
1017 if (!found_frs
[ic
] || front_rear_side(r
->i_cm
.map
[ic
]) == front_rear_side(r
->o_cm
.map
[oc
]))
1018 m
->map_table_f
[oc
][ic
] = .375f
/ (float) ncenter
[oc
];
1024 if (ic_unconnected_lfe
> 0 && !(r
->flags
& PA_RESAMPLER_NO_LFE
)) {
1026 /* OK, so there is an unconnected LFE channel. Let's mix
1027 * it into all channels, with factor 0.375 */
1029 for (ic
= 0; ic
< n_ic
; ic
++) {
1031 if (!on_lfe(r
->i_cm
.map
[ic
]))
1034 for (oc
= 0; oc
< n_oc
; oc
++)
1035 m
->map_table_f
[oc
][ic
] = 0.375f
/ (float) ic_unconnected_lfe
;
1039 /* make an 16:16 int version of the matrix */
1040 for (oc
= 0; oc
< n_oc
; oc
++)
1041 for (ic
= 0; ic
< n_ic
; ic
++)
1042 m
->map_table_i
[oc
][ic
] = (int32_t) (m
->map_table_f
[oc
][ic
] * 0x10000);
1044 s
= pa_strbuf_new();
1046 pa_strbuf_printf(s
, " ");
1047 for (ic
= 0; ic
< n_ic
; ic
++)
1048 pa_strbuf_printf(s
, " I%02u ", ic
);
1049 pa_strbuf_puts(s
, "\n +");
1051 for (ic
= 0; ic
< n_ic
; ic
++)
1052 pa_strbuf_printf(s
, "------");
1053 pa_strbuf_puts(s
, "\n");
1055 for (oc
= 0; oc
< n_oc
; oc
++) {
1056 pa_strbuf_printf(s
, "O%02u |", oc
);
1058 for (ic
= 0; ic
< n_ic
; ic
++)
1059 pa_strbuf_printf(s
, " %1.3f", m
->map_table_f
[oc
][ic
]);
1061 pa_strbuf_puts(s
, "\n");
1064 pa_log_debug("Channel matrix:\n%s", t
= pa_strbuf_tostring_free(s
));
1067 /* initialize the remapping function */
1071 static pa_memchunk
* convert_to_work_format(pa_resampler
*r
, pa_memchunk
*input
) {
1077 pa_assert(input
->memblock
);
1079 /* Convert the incoming sample into the work sample format and place them in buf1 */
1081 if (!r
->to_work_format_func
|| !input
->length
)
1084 n_samples
= (unsigned) ((input
->length
/ r
->i_fz
) * r
->i_ss
.channels
);
1087 r
->buf1
.length
= r
->w_sz
* n_samples
;
1089 if (!r
->buf1
.memblock
|| r
->buf1_samples
< n_samples
) {
1090 if (r
->buf1
.memblock
)
1091 pa_memblock_unref(r
->buf1
.memblock
);
1093 r
->buf1_samples
= n_samples
;
1094 r
->buf1
.memblock
= pa_memblock_new(r
->mempool
, r
->buf1
.length
);
1097 src
= (uint8_t*) pa_memblock_acquire(input
->memblock
) + input
->index
;
1098 dst
= (uint8_t*) pa_memblock_acquire(r
->buf1
.memblock
);
1100 r
->to_work_format_func(n_samples
, src
, dst
);
1102 pa_memblock_release(input
->memblock
);
1103 pa_memblock_release(r
->buf1
.memblock
);
1108 static pa_memchunk
*remap_channels(pa_resampler
*r
, pa_memchunk
*input
) {
1109 unsigned in_n_samples
, out_n_samples
, n_frames
;
1115 pa_assert(input
->memblock
);
1117 /* Remap channels and place the result int buf2 */
1119 if (!r
->map_required
|| !input
->length
)
1122 in_n_samples
= (unsigned) (input
->length
/ r
->w_sz
);
1123 n_frames
= in_n_samples
/ r
->i_ss
.channels
;
1124 out_n_samples
= n_frames
* r
->o_ss
.channels
;
1127 r
->buf2
.length
= r
->w_sz
* out_n_samples
;
1129 if (!r
->buf2
.memblock
|| r
->buf2_samples
< out_n_samples
) {
1130 if (r
->buf2
.memblock
)
1131 pa_memblock_unref(r
->buf2
.memblock
);
1133 r
->buf2_samples
= out_n_samples
;
1134 r
->buf2
.memblock
= pa_memblock_new(r
->mempool
, r
->buf2
.length
);
1137 src
= ((uint8_t*) pa_memblock_acquire(input
->memblock
) + input
->index
);
1138 dst
= pa_memblock_acquire(r
->buf2
.memblock
);
1142 pa_assert(remap
->do_remap
);
1143 remap
->do_remap(remap
, dst
, src
, n_frames
);
1145 pa_memblock_release(input
->memblock
);
1146 pa_memblock_release(r
->buf2
.memblock
);
1151 static pa_memchunk
*resample(pa_resampler
*r
, pa_memchunk
*input
) {
1152 unsigned in_n_frames
, in_n_samples
;
1153 unsigned out_n_frames
, out_n_samples
;
1158 /* Resample the data and place the result in buf3 */
1160 if (!r
->impl_resample
|| !input
->length
)
1163 in_n_samples
= (unsigned) (input
->length
/ r
->w_sz
);
1164 in_n_frames
= (unsigned) (in_n_samples
/ r
->o_ss
.channels
);
1166 out_n_frames
= ((in_n_frames
*r
->o_ss
.rate
)/r
->i_ss
.rate
)+EXTRA_FRAMES
;
1167 out_n_samples
= out_n_frames
* r
->o_ss
.channels
;
1170 r
->buf3
.length
= r
->w_sz
* out_n_samples
;
1172 if (!r
->buf3
.memblock
|| r
->buf3_samples
< out_n_samples
) {
1173 if (r
->buf3
.memblock
)
1174 pa_memblock_unref(r
->buf3
.memblock
);
1176 r
->buf3_samples
= out_n_samples
;
1177 r
->buf3
.memblock
= pa_memblock_new(r
->mempool
, r
->buf3
.length
);
1180 r
->impl_resample(r
, input
, in_n_frames
, &r
->buf3
, &out_n_frames
);
1181 r
->buf3
.length
= out_n_frames
* r
->w_sz
* r
->o_ss
.channels
;
1186 static pa_memchunk
*convert_from_work_format(pa_resampler
*r
, pa_memchunk
*input
) {
1187 unsigned n_samples
, n_frames
;
1193 /* Convert the data into the correct sample type and place the result in buf4 */
1195 if (!r
->from_work_format_func
|| !input
->length
)
1198 n_samples
= (unsigned) (input
->length
/ r
->w_sz
);
1199 n_frames
= n_samples
/ r
->o_ss
.channels
;
1202 r
->buf4
.length
= r
->o_fz
* n_frames
;
1204 if (!r
->buf4
.memblock
|| r
->buf4_samples
< n_samples
) {
1205 if (r
->buf4
.memblock
)
1206 pa_memblock_unref(r
->buf4
.memblock
);
1208 r
->buf4_samples
= n_samples
;
1209 r
->buf4
.memblock
= pa_memblock_new(r
->mempool
, r
->buf4
.length
);
1212 src
= (uint8_t*) pa_memblock_acquire(input
->memblock
) + input
->index
;
1213 dst
= pa_memblock_acquire(r
->buf4
.memblock
);
1214 r
->from_work_format_func(n_samples
, src
, dst
);
1215 pa_memblock_release(input
->memblock
);
1216 pa_memblock_release(r
->buf4
.memblock
);
1218 r
->buf4
.length
= r
->o_fz
* n_frames
;
1223 void pa_resampler_run(pa_resampler
*r
, const pa_memchunk
*in
, pa_memchunk
*out
) {
1229 pa_assert(in
->length
);
1230 pa_assert(in
->memblock
);
1231 pa_assert(in
->length
% r
->i_fz
== 0);
1233 buf
= (pa_memchunk
*) in
;
1234 buf
= convert_to_work_format(r
, buf
);
1235 buf
= remap_channels(r
, buf
);
1236 buf
= resample(r
, buf
);
1239 buf
= convert_from_work_format(r
, buf
);
1243 pa_memblock_ref(buf
->memblock
);
1245 pa_memchunk_reset(buf
);
1247 pa_memchunk_reset(out
);
1250 /*** libsamplerate based implementation ***/
1252 #ifdef HAVE_LIBSAMPLERATE
1253 static void libsamplerate_resample(pa_resampler
*r
, const pa_memchunk
*input
, unsigned in_n_frames
, pa_memchunk
*output
, unsigned *out_n_frames
) {
1259 pa_assert(out_n_frames
);
1261 memset(&data
, 0, sizeof(data
));
1263 data
.data_in
= (float*) ((uint8_t*) pa_memblock_acquire(input
->memblock
) + input
->index
);
1264 data
.input_frames
= (long int) in_n_frames
;
1266 data
.data_out
= (float*) ((uint8_t*) pa_memblock_acquire(output
->memblock
) + output
->index
);
1267 data
.output_frames
= (long int) *out_n_frames
;
1269 data
.src_ratio
= (double) r
->o_ss
.rate
/ r
->i_ss
.rate
;
1270 data
.end_of_input
= 0;
1272 pa_assert_se(src_process(r
->src
.state
, &data
) == 0);
1273 pa_assert((unsigned) data
.input_frames_used
== in_n_frames
);
1275 pa_memblock_release(input
->memblock
);
1276 pa_memblock_release(output
->memblock
);
1278 *out_n_frames
= (unsigned) data
.output_frames_gen
;
1281 static void libsamplerate_update_rates(pa_resampler
*r
) {
1284 pa_assert_se(src_set_ratio(r
->src
.state
, (double) r
->o_ss
.rate
/ r
->i_ss
.rate
) == 0);
1287 static void libsamplerate_reset(pa_resampler
*r
) {
1290 pa_assert_se(src_reset(r
->src
.state
) == 0);
1293 static void libsamplerate_free(pa_resampler
*r
) {
1297 src_delete(r
->src
.state
);
1300 static int libsamplerate_init(pa_resampler
*r
) {
1305 if (!(r
->src
.state
= src_new(r
->method
, r
->o_ss
.channels
, &err
)))
1308 r
->impl_free
= libsamplerate_free
;
1309 r
->impl_update_rates
= libsamplerate_update_rates
;
1310 r
->impl_resample
= libsamplerate_resample
;
1311 r
->impl_reset
= libsamplerate_reset
;
1318 /*** speex based implementation ***/
1320 static void speex_resample_float(pa_resampler
*r
, const pa_memchunk
*input
, unsigned in_n_frames
, pa_memchunk
*output
, unsigned *out_n_frames
) {
1322 uint32_t inf
= in_n_frames
, outf
= *out_n_frames
;
1327 pa_assert(out_n_frames
);
1329 in
= (float*) ((uint8_t*) pa_memblock_acquire(input
->memblock
) + input
->index
);
1330 out
= (float*) ((uint8_t*) pa_memblock_acquire(output
->memblock
) + output
->index
);
1332 pa_assert_se(speex_resampler_process_interleaved_float(r
->speex
.state
, in
, &inf
, out
, &outf
) == 0);
1334 pa_memblock_release(input
->memblock
);
1335 pa_memblock_release(output
->memblock
);
1337 pa_assert(inf
== in_n_frames
);
1338 *out_n_frames
= outf
;
1341 static void speex_resample_int(pa_resampler
*r
, const pa_memchunk
*input
, unsigned in_n_frames
, pa_memchunk
*output
, unsigned *out_n_frames
) {
1343 uint32_t inf
= in_n_frames
, outf
= *out_n_frames
;
1348 pa_assert(out_n_frames
);
1350 in
= (int16_t*) ((uint8_t*) pa_memblock_acquire(input
->memblock
) + input
->index
);
1351 out
= (int16_t*) ((uint8_t*) pa_memblock_acquire(output
->memblock
) + output
->index
);
1353 pa_assert_se(speex_resampler_process_interleaved_int(r
->speex
.state
, in
, &inf
, out
, &outf
) == 0);
1355 pa_memblock_release(input
->memblock
);
1356 pa_memblock_release(output
->memblock
);
1358 pa_assert(inf
== in_n_frames
);
1359 *out_n_frames
= outf
;
1362 static void speex_update_rates(pa_resampler
*r
) {
1365 pa_assert_se(speex_resampler_set_rate(r
->speex
.state
, r
->i_ss
.rate
, r
->o_ss
.rate
) == 0);
1368 static void speex_reset(pa_resampler
*r
) {
1371 pa_assert_se(speex_resampler_reset_mem(r
->speex
.state
) == 0);
1374 static void speex_free(pa_resampler
*r
) {
1377 if (!r
->speex
.state
)
1380 speex_resampler_destroy(r
->speex
.state
);
1383 static int speex_init(pa_resampler
*r
) {
1388 r
->impl_free
= speex_free
;
1389 r
->impl_update_rates
= speex_update_rates
;
1390 r
->impl_reset
= speex_reset
;
1392 if (r
->method
>= PA_RESAMPLER_SPEEX_FIXED_BASE
&& r
->method
<= PA_RESAMPLER_SPEEX_FIXED_MAX
) {
1394 q
= r
->method
- PA_RESAMPLER_SPEEX_FIXED_BASE
;
1395 r
->impl_resample
= speex_resample_int
;
1398 pa_assert(r
->method
>= PA_RESAMPLER_SPEEX_FLOAT_BASE
&& r
->method
<= PA_RESAMPLER_SPEEX_FLOAT_MAX
);
1400 q
= r
->method
- PA_RESAMPLER_SPEEX_FLOAT_BASE
;
1401 r
->impl_resample
= speex_resample_float
;
1404 pa_log_info("Choosing speex quality setting %i.", q
);
1406 if (!(r
->speex
.state
= speex_resampler_init(r
->o_ss
.channels
, r
->i_ss
.rate
, r
->o_ss
.rate
, q
, &err
)))
1413 /* Trivial implementation */
1415 static void trivial_resample(pa_resampler
*r
, const pa_memchunk
*input
, unsigned in_n_frames
, pa_memchunk
*output
, unsigned *out_n_frames
) {
1417 unsigned i_index
, o_index
;
1423 pa_assert(out_n_frames
);
1425 fz
= r
->w_sz
* r
->o_ss
.channels
;
1427 src
= (uint8_t*) pa_memblock_acquire(input
->memblock
) + input
->index
;
1428 dst
= (uint8_t*) pa_memblock_acquire(output
->memblock
) + output
->index
;
1430 for (o_index
= 0;; o_index
++, r
->trivial
.o_counter
++) {
1431 i_index
= (r
->trivial
.o_counter
* r
->i_ss
.rate
) / r
->o_ss
.rate
;
1432 i_index
= i_index
> r
->trivial
.i_counter
? i_index
- r
->trivial
.i_counter
: 0;
1434 if (i_index
>= in_n_frames
)
1437 pa_assert_fp(o_index
* fz
< pa_memblock_get_length(output
->memblock
));
1439 /* Directly assign some common sample sizes, use memcpy as fallback */
1441 for (unsigned c
= 0; c
< r
->o_ss
.channels
; c
++)
1442 ((uint16_t *) dst
)[o_index
+c
] = ((uint16_t *) src
)[i_index
+c
];
1443 } else if (r
->w_sz
== 4) {
1444 for (unsigned c
= 0; c
< r
->o_ss
.channels
; c
++)
1445 ((uint32_t *) dst
)[o_index
+c
] = ((uint32_t *) src
)[i_index
+c
];
1447 memcpy((uint8_t *) dst
+ fz
* o_index
, (uint8_t *) src
+ fz
* i_index
, (int) fz
);
1451 pa_memblock_release(input
->memblock
);
1452 pa_memblock_release(output
->memblock
);
1454 *out_n_frames
= o_index
;
1456 r
->trivial
.i_counter
+= in_n_frames
;
1458 /* Normalize counters */
1459 while (r
->trivial
.i_counter
>= r
->i_ss
.rate
) {
1460 pa_assert(r
->trivial
.o_counter
>= r
->o_ss
.rate
);
1462 r
->trivial
.i_counter
-= r
->i_ss
.rate
;
1463 r
->trivial
.o_counter
-= r
->o_ss
.rate
;
1467 static void trivial_update_rates_or_reset(pa_resampler
*r
) {
1470 r
->trivial
.i_counter
= 0;
1471 r
->trivial
.o_counter
= 0;
1474 static int trivial_init(pa_resampler
*r
) {
1477 r
->trivial
.o_counter
= r
->trivial
.i_counter
= 0;
1479 r
->impl_resample
= trivial_resample
;
1480 r
->impl_update_rates
= trivial_update_rates_or_reset
;
1481 r
->impl_reset
= trivial_update_rates_or_reset
;
1486 /* Peak finder implementation */
1488 static void peaks_resample(pa_resampler
*r
, const pa_memchunk
*input
, unsigned in_n_frames
, pa_memchunk
*output
, unsigned *out_n_frames
) {
1489 unsigned c
, o_index
= 0;
1490 unsigned i
, i_end
= 0;
1496 pa_assert(out_n_frames
);
1497 pa_assert(r
->i_ss
.rate
>= r
->o_ss
.rate
);
1498 pa_assert(r
->work_format
== PA_SAMPLE_S16NE
|| r
->work_format
== PA_SAMPLE_FLOAT32NE
);
1500 src
= (uint8_t*) pa_memblock_acquire(input
->memblock
) + input
->index
;
1501 dst
= (uint8_t*) pa_memblock_acquire(output
->memblock
) + output
->index
;
1503 i
= (r
->peaks
.o_counter
* r
->i_ss
.rate
) / r
->o_ss
.rate
;
1504 i
= i
> r
->peaks
.i_counter
? i
- r
->peaks
.i_counter
: 0;
1506 while (i_end
< in_n_frames
) {
1507 i_end
= ((r
->peaks
.o_counter
+1) * r
->i_ss
.rate
) / r
->o_ss
.rate
;
1508 i_end
= i_end
> r
->peaks
.i_counter
? i_end
- r
->peaks
.i_counter
: 0;
1510 pa_assert_fp(o_index
* r
->w_sz
* r
->o_ss
.channels
< pa_memblock_get_length(output
->memblock
));
1512 /* 1ch float is treated separately, because that is the common case */
1513 if (r
->o_ss
.channels
== 1 && r
->work_format
== PA_SAMPLE_FLOAT32NE
) {
1514 float *s
= (float*) src
+ i
;
1515 float *d
= (float*) dst
+ o_index
;
1517 for (; i
< i_end
&& i
< in_n_frames
; i
++) {
1518 float n
= fabsf(*s
++);
1520 if (n
> r
->peaks
.max_f
[0])
1521 r
->peaks
.max_f
[0] = n
;
1525 *d
= r
->peaks
.max_f
[0];
1526 r
->peaks
.max_f
[0] = 0;
1527 o_index
++, r
->peaks
.o_counter
++;
1529 } else if (r
->work_format
== PA_SAMPLE_S16NE
) {
1530 int16_t *s
= (int16_t*) src
+ r
->i_ss
.channels
* i
;
1531 int16_t *d
= (int16_t*) dst
+ r
->o_ss
.channels
* o_index
;
1533 for (; i
< i_end
&& i
< in_n_frames
; i
++)
1534 for (c
= 0; c
< r
->o_ss
.channels
; c
++) {
1535 int16_t n
= abs(*s
++);
1537 if (n
> r
->peaks
.max_i
[c
])
1538 r
->peaks
.max_i
[c
] = n
;
1542 for (c
= 0; c
< r
->o_ss
.channels
; c
++, d
++) {
1543 *d
= r
->peaks
.max_i
[c
];
1544 r
->peaks
.max_i
[c
] = 0;
1546 o_index
++, r
->peaks
.o_counter
++;
1549 float *s
= (float*) src
+ r
->i_ss
.channels
* i
;
1550 float *d
= (float*) dst
+ r
->o_ss
.channels
* o_index
;
1552 for (; i
< i_end
&& i
< in_n_frames
; i
++)
1553 for (c
= 0; c
< r
->o_ss
.channels
; c
++) {
1554 float n
= fabsf(*s
++);
1556 if (n
> r
->peaks
.max_f
[c
])
1557 r
->peaks
.max_f
[c
] = n
;
1561 for (c
= 0; c
< r
->o_ss
.channels
; c
++, d
++) {
1562 *d
= r
->peaks
.max_f
[c
];
1563 r
->peaks
.max_f
[c
] = 0;
1565 o_index
++, r
->peaks
.o_counter
++;
1570 pa_memblock_release(input
->memblock
);
1571 pa_memblock_release(output
->memblock
);
1573 *out_n_frames
= o_index
;
1575 r
->peaks
.i_counter
+= in_n_frames
;
1577 /* Normalize counters */
1578 while (r
->peaks
.i_counter
>= r
->i_ss
.rate
) {
1579 pa_assert(r
->peaks
.o_counter
>= r
->o_ss
.rate
);
1581 r
->peaks
.i_counter
-= r
->i_ss
.rate
;
1582 r
->peaks
.o_counter
-= r
->o_ss
.rate
;
1586 static void peaks_update_rates_or_reset(pa_resampler
*r
) {
1589 r
->peaks
.i_counter
= 0;
1590 r
->peaks
.o_counter
= 0;
1593 static int peaks_init(pa_resampler
*r
) {
1596 r
->peaks
.o_counter
= r
->peaks
.i_counter
= 0;
1597 memset(r
->peaks
.max_i
, 0, sizeof(r
->peaks
.max_i
));
1598 memset(r
->peaks
.max_f
, 0, sizeof(r
->peaks
.max_f
));
1600 r
->impl_resample
= peaks_resample
;
1601 r
->impl_update_rates
= peaks_update_rates_or_reset
;
1602 r
->impl_reset
= peaks_update_rates_or_reset
;
1607 /*** ffmpeg based implementation ***/
1609 static void ffmpeg_resample(pa_resampler
*r
, const pa_memchunk
*input
, unsigned in_n_frames
, pa_memchunk
*output
, unsigned *out_n_frames
) {
1610 unsigned used_frames
= 0, c
;
1615 pa_assert(out_n_frames
);
1617 for (c
= 0; c
< r
->o_ss
.channels
; c
++) {
1620 int16_t *p
, *t
, *k
, *q
, *s
;
1621 int consumed_frames
;
1624 /* Allocate a new block */
1625 b
= pa_memblock_new(r
->mempool
, r
->ffmpeg
.buf
[c
].length
+ in_n_frames
* sizeof(int16_t));
1626 p
= pa_memblock_acquire(b
);
1628 /* Copy the remaining data into it */
1629 l
= (unsigned) r
->ffmpeg
.buf
[c
].length
;
1630 if (r
->ffmpeg
.buf
[c
].memblock
) {
1631 t
= (int16_t*) ((uint8_t*) pa_memblock_acquire(r
->ffmpeg
.buf
[c
].memblock
) + r
->ffmpeg
.buf
[c
].index
);
1633 pa_memblock_release(r
->ffmpeg
.buf
[c
].memblock
);
1634 pa_memblock_unref(r
->ffmpeg
.buf
[c
].memblock
);
1635 pa_memchunk_reset(&r
->ffmpeg
.buf
[c
]);
1638 /* Now append the new data, splitting up channels */
1639 t
= ((int16_t*) ((uint8_t*) pa_memblock_acquire(input
->memblock
) + input
->index
)) + c
;
1640 k
= (int16_t*) ((uint8_t*) p
+ l
);
1641 for (u
= 0; u
< in_n_frames
; u
++) {
1643 t
+= r
->o_ss
.channels
;
1646 pa_memblock_release(input
->memblock
);
1648 /* Calculate the resulting number of frames */
1649 in
= (unsigned) in_n_frames
+ l
/ (unsigned) sizeof(int16_t);
1651 /* Allocate buffer for the result */
1652 w
= pa_memblock_new(r
->mempool
, *out_n_frames
* sizeof(int16_t));
1653 q
= pa_memblock_acquire(w
);
1656 used_frames
= (unsigned) av_resample(r
->ffmpeg
.state
,
1659 (int) in
, (int) *out_n_frames
,
1660 c
>= (unsigned) (r
->o_ss
.channels
-1));
1662 pa_memblock_release(b
);
1664 /* Now store the remaining samples away */
1665 pa_assert(consumed_frames
<= (int) in
);
1666 if (consumed_frames
< (int) in
) {
1667 r
->ffmpeg
.buf
[c
].memblock
= b
;
1668 r
->ffmpeg
.buf
[c
].index
= (size_t) consumed_frames
* sizeof(int16_t);
1669 r
->ffmpeg
.buf
[c
].length
= (size_t) (in
- (unsigned) consumed_frames
) * sizeof(int16_t);
1671 pa_memblock_unref(b
);
1673 /* And place the results in the output buffer */
1674 s
= (short*) ((uint8_t*) pa_memblock_acquire(output
->memblock
) + output
->index
) + c
;
1675 for (u
= 0; u
< used_frames
; u
++) {
1678 s
+= r
->o_ss
.channels
;
1680 pa_memblock_release(output
->memblock
);
1681 pa_memblock_release(w
);
1682 pa_memblock_unref(w
);
1685 *out_n_frames
= used_frames
;
1688 static void ffmpeg_free(pa_resampler
*r
) {
1693 if (r
->ffmpeg
.state
)
1694 av_resample_close(r
->ffmpeg
.state
);
1696 for (c
= 0; c
< PA_ELEMENTSOF(r
->ffmpeg
.buf
); c
++)
1697 if (r
->ffmpeg
.buf
[c
].memblock
)
1698 pa_memblock_unref(r
->ffmpeg
.buf
[c
].memblock
);
1701 static int ffmpeg_init(pa_resampler
*r
) {
1706 /* We could probably implement different quality levels by
1707 * adjusting the filter parameters here. However, ffmpeg
1708 * internally only uses these hardcoded values, so let's use them
1709 * here for now as well until ffmpeg makes this configurable. */
1711 if (!(r
->ffmpeg
.state
= av_resample_init((int) r
->o_ss
.rate
, (int) r
->i_ss
.rate
, 16, 10, 0, 0.8)))
1714 r
->impl_free
= ffmpeg_free
;
1715 r
->impl_resample
= ffmpeg_resample
;
1717 for (c
= 0; c
< PA_ELEMENTSOF(r
->ffmpeg
.buf
); c
++)
1718 pa_memchunk_reset(&r
->ffmpeg
.buf
[c
]);
1723 /*** copy (noop) implementation ***/
1725 static int copy_init(pa_resampler
*r
) {
1728 pa_assert(r
->o_ss
.rate
== r
->i_ss
.rate
);