FFmpeg
soxr_resample.c
Go to the documentation of this file.
1 /*
2  * audio resampling with soxr
3  * Copyright (c) 2012 Rob Sykes <robs@users.sourceforge.net>
4  *
5  * This file is part of FFmpeg.
6  *
7  * FFmpeg is free software; you can redistribute it and/or
8  * modify it under the terms of the GNU Lesser General Public
9  * License as published by the Free Software Foundation; either
10  * version 2.1 of the License, or (at your option) any later version.
11  *
12  * FFmpeg is distributed in the hope that it will be useful,
13  * but WITHOUT ANY WARRANTY; without even the implied warranty of
14  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
15  * Lesser General Public License for more details.
16  *
17  * You should have received a copy of the GNU Lesser General Public
18  * License along with FFmpeg; if not, write to the Free Software
19  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
20  */
21 
22 /**
23  * @file
24  * audio resampling with soxr
25  */
26 
27 #include "libavutil/log.h"
28 #include "swresample_internal.h"
29 
30 #include <soxr.h>
31 
32 static struct ResampleContext *create(struct ResampleContext *c, int out_rate, int in_rate, int filter_size, int phase_shift, int linear,
33  double cutoff, enum AVSampleFormat format, enum SwrFilterType filter_type, double kaiser_beta, double precision, int cheby, int exact_rational){
34  soxr_error_t error;
35 
36  soxr_datatype_t type =
37  format == AV_SAMPLE_FMT_S16P? SOXR_INT16_S :
38  format == AV_SAMPLE_FMT_S16 ? SOXR_INT16_I :
39  format == AV_SAMPLE_FMT_S32P? SOXR_INT32_S :
40  format == AV_SAMPLE_FMT_S32 ? SOXR_INT32_I :
41  format == AV_SAMPLE_FMT_FLTP? SOXR_FLOAT32_S :
42  format == AV_SAMPLE_FMT_FLT ? SOXR_FLOAT32_I :
43  format == AV_SAMPLE_FMT_DBLP? SOXR_FLOAT64_S :
44  format == AV_SAMPLE_FMT_DBL ? SOXR_FLOAT64_I : (soxr_datatype_t)-1;
45 
46  soxr_io_spec_t io_spec = soxr_io_spec(type, type);
47 
48  soxr_quality_spec_t q_spec = soxr_quality_spec((int)((precision-2)/4), (SOXR_HI_PREC_CLOCK|SOXR_ROLLOFF_NONE)*!!cheby);
49  q_spec.precision = precision;
50 #if !defined SOXR_VERSION /* Deprecated @ March 2013: */
51  q_spec.bw_pc = cutoff? FFMAX(FFMIN(cutoff,.995),.8)*100 : q_spec.bw_pc;
52 #else
53  q_spec.passband_end = cutoff? FFMAX(FFMIN(cutoff,.995),.8) : q_spec.passband_end;
54 #endif
55 
56  soxr_delete((soxr_t)c);
57  c = (struct ResampleContext *)
58  soxr_create(in_rate, out_rate, 0, &error, &io_spec, &q_spec, 0);
59  if (!c)
60  av_log(NULL, AV_LOG_ERROR, "soxr_create: %s\n", error);
61  return c;
62 }
63 
64 static void destroy(struct ResampleContext * *c){
65  soxr_delete((soxr_t)*c);
66  *c = NULL;
67 }
68 
69 static int flush(struct SwrContext *s){
70  s->delayed_samples_fixup = soxr_delay((soxr_t)s->resample);
71 
72  soxr_process((soxr_t)s->resample, NULL, 0, NULL, NULL, 0, NULL);
73 
74  {
75  float f;
76  size_t idone, odone;
77  soxr_process((soxr_t)s->resample, &f, 0, &idone, &f, 0, &odone);
78  s->delayed_samples_fixup -= soxr_delay((soxr_t)s->resample);
79  }
80 
81  return 0;
82 }
83 
84 static int process(
85  struct ResampleContext * c, AudioData *dst, int dst_size,
86  AudioData *src, int src_size, int *consumed){
87  size_t idone, odone;
88  soxr_error_t error = soxr_set_error((soxr_t)c, soxr_set_num_channels((soxr_t)c, src->ch_count));
89  if (!error)
90  error = soxr_process((soxr_t)c, src->ch, (size_t)src_size,
91  &idone, dst->ch, (size_t)dst_size, &odone);
92  else
93  idone = 0;
94 
95  *consumed = (int)idone;
96  return error? -1 : odone;
97 }
98 
100  double delayed_samples = soxr_delay((soxr_t)s->resample);
101  double delay_s;
102 
103  if (s->flushed)
104  delayed_samples += s->delayed_samples_fixup;
105 
106  delay_s = delayed_samples / s->out_sample_rate;
107 
108  return (int64_t)(delay_s * base + .5);
109 }
110 
112  int in_count, int *out_idx, int *out_sz){
113  return 0;
114 }
115 
116 static int64_t get_out_samples(struct SwrContext *s, int in_samples){
117  double out_samples = (double)s->out_sample_rate / s->in_sample_rate * in_samples;
118  double delayed_samples = soxr_delay((soxr_t)s->resample);
119 
120  if (s->flushed)
121  delayed_samples += s->delayed_samples_fixup;
122 
123  return (int64_t)(out_samples + delayed_samples + 1 + .5);
124 }
125 
127  create, destroy, process, flush, NULL /* set_compensation */, get_delay,
129 };
130 
error
static void error(const char *err)
Definition: target_bsf_fuzzer.c:32
get_delay
static int64_t get_delay(struct SwrContext *s, int64_t base)
Definition: soxr_resample.c:99
AV_SAMPLE_FMT_FLTP
@ AV_SAMPLE_FMT_FLTP
float, planar
Definition: samplefmt.h:66
destroy
static void destroy(struct ResampleContext **c)
Definition: soxr_resample.c:64
int64_t
long long int64_t
Definition: coverity.c:34
kaiser_beta
static float kaiser_beta(float att, float tr_bw)
Definition: asrc_sinc.c:125
AV_SAMPLE_FMT_S32P
@ AV_SAMPLE_FMT_S32P
signed 32 bits, planar
Definition: samplefmt.h:65
linear
static int linear(InterplayACMContext *s, unsigned ind, unsigned col)
Definition: interplayacm.c:135
base
uint8_t base
Definition: vp3data.h:128
FFMAX
#define FFMAX(a, b)
Definition: macros.h:47
AudioData
Definition: swresample_internal.h:45
flush
static int flush(struct SwrContext *s)
Definition: soxr_resample.c:69
type
it s the only field you need to keep assuming you have a context There is some magic you don t need to care about around this just let it vf type
Definition: writing_filters.txt:86
get_out_samples
static int64_t get_out_samples(struct SwrContext *s, int in_samples)
Definition: soxr_resample.c:116
AV_LOG_ERROR
#define AV_LOG_ERROR
Something went wrong and cannot losslessly be recovered.
Definition: log.h:209
s
#define s(width, name)
Definition: cbs_vp9.c:198
ResampleContext
Definition: resample.h:30
format
Filter the word “frame” indicates either a video frame or a group of audio as stored in an AVFrame structure Format for each input and each output the list of supported formats For video that means pixel format For audio that means channel sample format(the sample packing is implied by the sample format) and sample rate. The lists are not just lists
ResampleContext::filter_type
enum SwrFilterType filter_type
Definition: resample.h:45
SwrContext
The libswresample context.
Definition: swresample_internal.h:95
NULL
#define NULL
Definition: coverity.c:32
SwrFilterType
SwrFilterType
Resampling Filter Types.
Definition: swresample.h:173
create
static struct ResampleContext * create(struct ResampleContext *c, int out_rate, int in_rate, int filter_size, int phase_shift, int linear, double cutoff, enum AVSampleFormat format, enum SwrFilterType filter_type, double kaiser_beta, double precision, int cheby, int exact_rational)
Definition: soxr_resample.c:32
double
double
Definition: af_crystalizer.c:132
swri_soxr_resampler
struct Resampler const swri_soxr_resampler
Definition: soxr_resample.c:126
c
Undefined Behavior In the C some operations are like signed integer dereferencing freed accessing outside allocated Undefined Behavior must not occur in a C it is not safe even if the output of undefined operations is unused The unsafety may seem nit picking but Optimizing compilers have in fact optimized code on the assumption that no undefined Behavior occurs Optimizing code based on wrong assumptions can and has in some cases lead to effects beyond the output of computations The signed integer overflow problem in speed critical code Code which is highly optimized and works with signed integers sometimes has the problem that often the output of the computation does not c
Definition: undefined.txt:32
process
static int process(struct ResampleContext *c, AudioData *dst, int dst_size, AudioData *src, int src_size, int *consumed)
Definition: soxr_resample.c:84
invert_initial_buffer
static int invert_initial_buffer(struct ResampleContext *c, AudioData *dst, const AudioData *src, int in_count, int *out_idx, int *out_sz)
Definition: soxr_resample.c:111
f
f
Definition: af_crystalizer.c:122
dst
uint8_t ptrdiff_t const uint8_t ptrdiff_t int intptr_t intptr_t int int16_t * dst
Definition: dsp.h:83
swresample_internal.h
Resampler
Definition: swresample_internal.h:81
AV_SAMPLE_FMT_S16P
@ AV_SAMPLE_FMT_S16P
signed 16 bits, planar
Definition: samplefmt.h:64
log.h
AVSampleFormat
AVSampleFormat
Audio sample formats.
Definition: samplefmt.h:55
FFMIN
#define FFMIN(a, b)
Definition: macros.h:49
AV_SAMPLE_FMT_S16
@ AV_SAMPLE_FMT_S16
signed 16 bits
Definition: samplefmt.h:58
AV_SAMPLE_FMT_DBLP
@ AV_SAMPLE_FMT_DBLP
double, planar
Definition: samplefmt.h:67
av_log
#define av_log(a,...)
Definition: tableprint_vlc.h:27
AV_SAMPLE_FMT_DBL
@ AV_SAMPLE_FMT_DBL
double
Definition: samplefmt.h:61
AV_SAMPLE_FMT_S32
@ AV_SAMPLE_FMT_S32
signed 32 bits
Definition: samplefmt.h:59
AV_SAMPLE_FMT_FLT
@ AV_SAMPLE_FMT_FLT
float
Definition: samplefmt.h:60
src
#define src
Definition: vp8dsp.c:248