FFmpeg
af_silenceremove.c
Go to the documentation of this file.
1 /*
2  * Copyright (c) 2001 Heikki Leinonen
3  * Copyright (c) 2001 Chris Bagwell
4  * Copyright (c) 2003 Donnie Smith
5  * Copyright (c) 2014 Paul B Mahol
6  *
7  * This file is part of FFmpeg.
8  *
9  * FFmpeg is free software; you can redistribute it and/or
10  * modify it under the terms of the GNU Lesser General Public
11  * License as published by the Free Software Foundation; either
12  * version 2.1 of the License, or (at your option) any later version.
13  *
14  * FFmpeg is distributed in the hope that it will be useful,
15  * but WITHOUT ANY WARRANTY; without even the implied warranty of
16  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
17  * Lesser General Public License for more details.
18  *
19  * You should have received a copy of the GNU Lesser General Public
20  * License along with FFmpeg; if not, write to the Free Software
21  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
22  */
23 
24 #include <float.h> /* DBL_MAX */
25 
26 #include "libavutil/audio_fifo.h"
27 #include "libavutil/avassert.h"
28 #include "libavutil/opt.h"
29 #include "libavutil/timestamp.h"
30 #include "audio.h"
31 #include "formats.h"
32 #include "avfilter.h"
33 #include "internal.h"
34 
38 };
39 
43 };
44 
51 };
52 
53 typedef struct SilenceRemoveContext {
54  const AVClass *class;
55 
57 
59  int64_t start_duration;
62  int64_t start_silence;
65 
67  int64_t stop_duration;
70  int64_t stop_silence;
72  int stop_mode;
73 
75 
83 
91 
94  int64_t window_duration;
95  double sum;
96 
98  int restart;
99  int64_t next_pts;
100 
102  void (*update)(struct SilenceRemoveContext *s, AVFrame *frame, int ch, int offset);
104  void (*copy)(struct SilenceRemoveContext *s, AVFrame *out, AVFrame *in,
105  int ch, int out_offset, int in_offset);
106 
109 
110 #define OFFSET(x) offsetof(SilenceRemoveContext, x)
111 #define AF AV_OPT_FLAG_FILTERING_PARAM|AV_OPT_FLAG_AUDIO_PARAM
112 
113 static const AVOption silenceremove_options[] = {
114  { "start_periods", "set periods of silence parts to skip from start", OFFSET(start_periods), AV_OPT_TYPE_INT, {.i64=0}, 0, 9000, AF },
115  { "start_duration", "set start duration of non-silence part", OFFSET(start_duration_opt), AV_OPT_TYPE_DURATION, {.i64=0}, 0, INT32_MAX, AF },
116  { "start_threshold", "set threshold for start silence detection", OFFSET(start_threshold), AV_OPT_TYPE_DOUBLE, {.dbl=0}, 0, DBL_MAX, AF },
117  { "start_silence", "set start duration of silence part to keep", OFFSET(start_silence_opt), AV_OPT_TYPE_DURATION, {.i64=0}, 0, INT32_MAX, AF },
118  { "start_mode", "set which channel will trigger trimming from start", OFFSET(start_mode), AV_OPT_TYPE_INT, {.i64=T_ANY}, T_ANY, T_ALL, AF, "mode" },
119  { "any", 0, 0, AV_OPT_TYPE_CONST, {.i64=T_ANY}, 0, 0, AF, "mode" },
120  { "all", 0, 0, AV_OPT_TYPE_CONST, {.i64=T_ALL}, 0, 0, AF, "mode" },
121  { "stop_periods", "set periods of silence parts to skip from end", OFFSET(stop_periods), AV_OPT_TYPE_INT, {.i64=0}, -9000, 9000, AF },
122  { "stop_duration", "set stop duration of non-silence part", OFFSET(stop_duration_opt), AV_OPT_TYPE_DURATION, {.i64=0}, 0, INT32_MAX, AF },
123  { "stop_threshold", "set threshold for stop silence detection", OFFSET(stop_threshold), AV_OPT_TYPE_DOUBLE, {.dbl=0}, 0, DBL_MAX, AF },
124  { "stop_silence", "set stop duration of silence part to keep", OFFSET(stop_silence_opt), AV_OPT_TYPE_DURATION, {.i64=0}, 0, INT32_MAX, AF },
125  { "stop_mode", "set which channel will trigger trimming from end", OFFSET(stop_mode), AV_OPT_TYPE_INT, {.i64=T_ANY}, T_ANY, T_ALL, AF, "mode" },
126  { "detection", "set how silence is detected", OFFSET(detection), AV_OPT_TYPE_INT, {.i64=D_RMS}, D_PEAK,D_RMS, AF, "detection" },
127  { "peak", "use absolute values of samples", 0, AV_OPT_TYPE_CONST, {.i64=D_PEAK},0, 0, AF, "detection" },
128  { "rms", "use squared values of samples", 0, AV_OPT_TYPE_CONST, {.i64=D_RMS}, 0, 0, AF, "detection" },
129  { "window", "set duration of window for silence detection", OFFSET(window_duration_opt), AV_OPT_TYPE_DURATION, {.i64=20000}, 0, 100000000, AF },
130  { NULL }
131 };
132 
133 AVFILTER_DEFINE_CLASS(silenceremove);
134 
136  int ch, int out_offset, int in_offset)
137 {
138  const double *srcp = (const double *)in->data[0];
139  const double src = srcp[in->ch_layout.nb_channels * in_offset + ch];
140  double *dstp = (double *)out->data[0];
141 
142  dstp[out->ch_layout.nb_channels * out_offset + ch] = src;
143 }
144 
146  int ch, int out_offset, int in_offset)
147 {
148  const double *srcp = (const double *)in->extended_data[ch];
149  const double src = srcp[in_offset];
150  double *dstp = (double *)out->extended_data[ch];
151 
152  dstp[out_offset] = src;
153 }
154 
156  int ch, int out_offset, int in_offset)
157 {
158  const float *srcp = (const float *)in->data[0];
159  const float src = srcp[in->ch_layout.nb_channels * in_offset + ch];
160  float *dstp = (float *)out->data[0];
161 
162  dstp[out->ch_layout.nb_channels * out_offset + ch] = src;
163 }
164 
166  int ch, int out_offset, int in_offset)
167 {
168  const float *srcp = (const float *)in->extended_data[ch];
169  const float src = srcp[in_offset];
170  float *dstp = (float *)out->extended_data[ch];
171 
172  dstp[out_offset] = src;
173 }
174 
176 {
177  const double *samples = (const double *)frame->data[0];
178  const double *wsamples = (const double *)s->window->data[0];
179  double sample = samples[frame->ch_layout.nb_channels * offset + ch];
180  double wsample = wsamples[frame->ch_layout.nb_channels * s->window_offset + ch];
181  double new_sum;
182 
183  new_sum = s->sum;
184  new_sum -= wsample;
185  new_sum = fmax(new_sum, 0.);
186  new_sum += fabs(sample);
187 
188  return new_sum / s->window_duration;
189 }
190 
192 {
193  const double *samples = (const double *)frame->data[0];
194  double *wsamples = (double *)s->window->data[0];
195  double sample = samples[frame->ch_layout.nb_channels * offset + ch];
196  double *wsample = &wsamples[frame->ch_layout.nb_channels * s->window_offset + ch];
197 
198  s->sum -= *wsample;
199  s->sum = fmax(s->sum, 0.);
200  *wsample = fabs(sample);
201  s->sum += *wsample;
202 }
203 
205 {
206  const float *samples = (const float *)frame->data[0];
207  const float *wsamples = (const float *)s->window->data[0];
208  float sample = samples[frame->ch_layout.nb_channels * offset + ch];
209  float wsample = wsamples[frame->ch_layout.nb_channels * s->window_offset + ch];
210  float new_sum;
211 
212  new_sum = s->sum;
213  new_sum -= wsample;
214  new_sum = fmaxf(new_sum, 0.f);
215  new_sum += fabsf(sample);
216 
217  return new_sum / s->window_duration;
218 }
219 
221 {
222  const float *samples = (const float *)frame->data[0];
223  float *wsamples = (float *)s->window->data[0];
224  float sample = samples[frame->ch_layout.nb_channels * offset + ch];
225  float *wsample = &wsamples[frame->ch_layout.nb_channels * s->window_offset + ch];
226 
227  s->sum -= *wsample;
228  s->sum = fmaxf(s->sum, 0.f);
229  *wsample = fabsf(sample);
230  s->sum += *wsample;
231 }
232 
234 {
235  const double *samples = (const double *)frame->data[0];
236  const double *wsamples = (const double *)s->window->data[0];
237  double sample = samples[frame->ch_layout.nb_channels * offset + ch];
238  double wsample = wsamples[frame->ch_layout.nb_channels * s->window_offset + ch];
239  double new_sum;
240 
241  new_sum = s->sum;
242  new_sum -= wsample;
243  new_sum = fmax(new_sum, 0.);
244  new_sum += sample * sample;
245 
246  av_assert2(new_sum >= 0.);
247  return sqrt(new_sum / s->window_duration);
248 }
249 
251 {
252  const double *samples = (const double *)frame->data[0];
253  double *wsamples = (double *)s->window->data[0];
254  double sample = samples[frame->ch_layout.nb_channels * offset + ch];
255  double *wsample = &wsamples[frame->ch_layout.nb_channels * s->window_offset + ch];
256 
257  s->sum -= *wsample;
258  s->sum = fmax(s->sum, 0.);
259  *wsample = sample * sample;
260  s->sum += *wsample;
261 }
262 
264 {
265  const float *samples = (const float *)frame->data[0];
266  const float *wsamples = (const float *)s->window->data[0];
267  float sample = samples[frame->ch_layout.nb_channels * offset + ch];
268  float wsample = wsamples[frame->ch_layout.nb_channels * s->window_offset + ch];
269  float new_sum;
270 
271  new_sum = s->sum;
272  new_sum -= wsample;
273  new_sum = fmaxf(new_sum, 0.f);
274  new_sum += sample * sample;
275 
276  av_assert2(new_sum >= 0.f);
277  return sqrtf(new_sum / s->window_duration);
278 }
279 
281 {
282  const float *samples = (const float *)frame->data[0];
283  float sample = samples[frame->ch_layout.nb_channels * offset + ch];
284  float *wsamples = (float *)s->window->data[0];
285  float *wsample = &wsamples[frame->ch_layout.nb_channels * s->window_offset + ch];
286 
287  s->sum -= *wsample;
288  s->sum = fmaxf(s->sum, 0.f);
289  *wsample = sample * sample;
290  s->sum += *wsample;
291 }
292 
294 {
295  const double *samples = (const double *)frame->extended_data[ch];
296  const double *wsamples = (const double *)s->window->extended_data[ch];
297  double sample = samples[offset];
298  double wsample = wsamples[s->window_offset];
299  double new_sum;
300 
301  new_sum = s->sum;
302  new_sum -= wsample;
303  new_sum = fmax(new_sum, 0.);
304  new_sum += fabs(sample);
305 
306  return new_sum / s->window_duration;
307 }
308 
310 {
311  const double *samples = (const double *)frame->extended_data[ch];
312  double *wsamples = (double *)s->window->extended_data[ch];
313  double sample = samples[offset];
314  double *wsample = &wsamples[s->window_offset];
315 
316  s->sum -= *wsample;
317  s->sum = fmax(s->sum, 0.);
318  *wsample = fabs(sample);
319  s->sum += *wsample;
320 }
321 
323 {
324  const float *samples = (const float *)frame->extended_data[ch];
325  const float *wsamples = (const float *)s->window->extended_data[ch];
326  float sample = samples[offset];
327  float wsample = wsamples[s->window_offset];
328  float new_sum;
329 
330  new_sum = s->sum;
331  new_sum -= wsample;
332  new_sum = fmaxf(new_sum, 0.f);
333  new_sum += fabsf(sample);
334 
335  return new_sum / s->window_duration;
336 }
337 
339 {
340  const float *samples = (const float *)frame->extended_data[ch];
341  float *wsamples = (float *)s->window->extended_data[ch];
342  float sample = samples[offset];
343  float *wsample = &wsamples[s->window_offset];
344 
345  s->sum -= *wsample;
346  s->sum = fmaxf(s->sum, 0.f);
347  *wsample = fabsf(sample);
348  s->sum += *wsample;
349 }
350 
352 {
353  const double *samples = (const double *)frame->extended_data[ch];
354  const double *wsamples = (const double *)s->window->extended_data[ch];
355  double sample = samples[offset];
356  double wsample = wsamples[s->window_offset];
357  double new_sum;
358 
359  new_sum = s->sum;
360  new_sum -= wsample;
361  new_sum = fmax(new_sum, 0.);
362  new_sum += sample * sample;
363 
364  av_assert2(new_sum >= 0.);
365  return sqrt(new_sum / s->window_duration);
366 }
367 
369 {
370  const double *samples = (const double *)frame->extended_data[ch];
371  double *wsamples = (double *)s->window->extended_data[ch];
372  double sample = samples[offset];
373  double *wsample = &wsamples[s->window_offset];
374 
375  s->sum -= *wsample;
376  s->sum = fmax(s->sum, 0.);
377  *wsample = sample * sample;
378  s->sum += *wsample;
379 }
380 
382 {
383  const float *samples = (const float *)frame->extended_data[ch];
384  const float *wsamples = (const float *)s->window->extended_data[ch];
385  float sample = samples[offset];
386  float wsample = wsamples[s->window_offset];
387  float new_sum;
388 
389  new_sum = s->sum;
390  new_sum -= wsample;
391  new_sum = fmaxf(new_sum, 0.f);
392  new_sum += sample * sample;
393 
394  av_assert2(new_sum >= 0.f);
395  return sqrtf(new_sum / s->window_duration);
396 }
397 
399 {
400  const float *samples = (const float *)frame->extended_data[ch];
401  float *wsamples = (float *)s->window->extended_data[ch];
402  float sample = samples[offset];
403  float *wsample = &wsamples[s->window_offset];
404 
405  s->sum -= *wsample;
406  s->sum = fmaxf(s->sum, 0.f);
407  *wsample = sample * sample;
408  s->sum += *wsample;
409 }
410 
412 {
413  SilenceRemoveContext *s = ctx->priv;
414 
415  if (s->stop_periods < 0) {
416  s->stop_periods = -s->stop_periods;
417  s->restart = 1;
418  }
419 
420  return 0;
421 }
422 
424 {
425  av_samples_set_silence(s->window->extended_data, 0, s->window_duration,
426  s->window->ch_layout.nb_channels, s->window->format);
427 
428  s->window_offset = 0;
429  s->sum = 0;
430 }
431 
433 {
434  AVFilterContext *ctx = inlink->dst;
435  SilenceRemoveContext *s = ctx->priv;
436 
437  s->next_pts = AV_NOPTS_VALUE;
438  s->window_duration = av_rescale(s->window_duration_opt, inlink->sample_rate,
439  AV_TIME_BASE);
440  s->window_duration = FFMAX(1, s->window_duration);
441  s->window = ff_get_audio_buffer(ctx->outputs[0], s->window_duration);
442  if (!s->window)
443  return AVERROR(ENOMEM);
444 
445  clear_window(s);
446 
447  s->start_duration = av_rescale(s->start_duration_opt, inlink->sample_rate,
448  AV_TIME_BASE);
449  s->start_silence = av_rescale(s->start_silence_opt, inlink->sample_rate,
450  AV_TIME_BASE);
451  s->stop_duration = av_rescale(s->stop_duration_opt, inlink->sample_rate,
452  AV_TIME_BASE);
453  s->stop_silence = av_rescale(s->stop_silence_opt, inlink->sample_rate,
454  AV_TIME_BASE);
455 
456  s->start_holdoff = ff_get_audio_buffer(ctx->outputs[0],
457  FFMAX(s->start_duration, 1));
458  if (!s->start_holdoff)
459  return AVERROR(ENOMEM);
460 
461  s->start_silence_hold = ff_get_audio_buffer(ctx->outputs[0],
462  FFMAX(s->start_silence, 1));
463  if (!s->start_silence_hold)
464  return AVERROR(ENOMEM);
465 
466  s->start_holdoff_offset = 0;
467  s->start_holdoff_end = 0;
468  s->start_found_periods = 0;
469 
470  s->stop_holdoff = ff_get_audio_buffer(ctx->outputs[0],
471  FFMAX(s->stop_duration, 1));
472  if (!s->stop_holdoff)
473  return AVERROR(ENOMEM);
474 
475  s->stop_silence_hold = ff_get_audio_buffer(ctx->outputs[0],
476  FFMAX(s->stop_silence, 1));
477  if (!s->stop_silence_hold)
478  return AVERROR(ENOMEM);
479 
480  s->stop_holdoff_offset = 0;
481  s->stop_holdoff_end = 0;
482  s->stop_found_periods = 0;
483 
484  if (s->start_periods) {
485  s->mode = SILENCE_TRIM;
486  s->one_period = 1;
487  } else {
488  s->mode = SILENCE_COPY;
489  }
490 
491  switch (inlink->format) {
492  case AV_SAMPLE_FMT_DBL:
493  s->copy = copy_double;
494  switch (s->detection) {
495  case D_PEAK:
496  s->update = update_peak_double;
497  s->compute = compute_peak_double;
498  break;
499  case D_RMS:
500  s->update = update_rms_double;
501  s->compute = compute_rms_double;
502  break;
503  }
504  break;
505  case AV_SAMPLE_FMT_FLT:
506  s->copy = copy_float;
507  switch (s->detection) {
508  case D_PEAK:
509  s->update = update_peak_float;
510  s->compute = compute_peak_float;
511  break;
512  case D_RMS:
513  s->update = update_rms_float;
514  s->compute = compute_rms_float;
515  break;
516  }
517  break;
518  case AV_SAMPLE_FMT_DBLP:
519  s->copy = copy_doublep;
520  switch (s->detection) {
521  case D_PEAK:
522  s->update = update_peak_doublep;
523  s->compute = compute_peak_doublep;
524  break;
525  case D_RMS:
526  s->update = update_rms_doublep;
527  s->compute = compute_rms_doublep;
528  break;
529  }
530  break;
531  case AV_SAMPLE_FMT_FLTP:
532  s->copy = copy_floatp;
533  switch (s->detection) {
534  case D_PEAK:
535  s->update = update_peak_floatp;
536  s->compute = compute_peak_floatp;
537  break;
538  case D_RMS:
539  s->update = update_rms_floatp;
540  s->compute = compute_rms_floatp;
541  break;
542  }
543  break;
544  default:
545  return AVERROR_BUG;
546  }
547 
548  s->fifo = av_audio_fifo_alloc(inlink->format, inlink->ch_layout.nb_channels, 1024);
549  if (!s->fifo)
550  return AVERROR(ENOMEM);
551 
552  return 0;
553 }
554 
556  AVFrame *out, AVFilterLink *outlink,
557  int *nb_samples_written, int flush_silence)
558 {
559  AVFrame *silence;
560 
561  if (*nb_samples_written) {
562  out->nb_samples = *nb_samples_written;
563 
564  av_audio_fifo_write(s->fifo, (void **)out->extended_data, out->nb_samples);
565  *nb_samples_written = 0;
566  }
567 
568  av_frame_free(&out);
569 
570  if (s->stop_silence_end <= 0 || !flush_silence)
571  return;
572 
573  silence = ff_get_audio_buffer(outlink, s->stop_silence_end);
574  if (!silence)
575  return;
576 
577  if (s->stop_silence_offset < s->stop_silence_end) {
578  av_samples_copy(silence->extended_data, s->stop_silence_hold->extended_data, 0,
579  s->stop_silence_offset,
580  s->stop_silence_end - s->stop_silence_offset,
581  outlink->ch_layout.nb_channels, outlink->format);
582  }
583 
584  if (s->stop_silence_offset > 0) {
585  av_samples_copy(silence->extended_data, s->stop_silence_hold->extended_data,
586  s->stop_silence_end - s->stop_silence_offset,
587  0, s->stop_silence_offset,
588  outlink->ch_layout.nb_channels, outlink->format);
589  }
590 
591  s->stop_silence_offset = 0;
592  s->stop_silence_end = 0;
593 
594  av_audio_fifo_write(s->fifo, (void **)silence->extended_data, silence->nb_samples);
595  av_frame_free(&silence);
596 }
597 
599 {
600  AVFilterContext *ctx = inlink->dst;
601  AVFilterLink *outlink = ctx->outputs[0];
602  SilenceRemoveContext *s = ctx->priv;
603  int nbs, nb_samples_read, nb_samples_written;
604  int i, j, threshold, ret = 0;
605  AVFrame *out;
606 
607  nb_samples_read = nb_samples_written = 0;
608 
609  if (s->next_pts == AV_NOPTS_VALUE)
610  s->next_pts = in->pts;
611 
612  switch (s->mode) {
613  case SILENCE_TRIM:
614 silence_trim:
615  nbs = in->nb_samples - nb_samples_read;
616  if (!nbs)
617  break;
618 
619  for (i = 0; i < nbs; i++) {
620  if (s->start_mode == T_ANY) {
621  threshold = 0;
622  for (j = 0; j < outlink->ch_layout.nb_channels; j++) {
623  threshold |= s->compute(s, in, j, nb_samples_read) > s->start_threshold;
624  }
625  } else {
626  threshold = 1;
627  for (j = 0; j < outlink->ch_layout.nb_channels; j++) {
628  threshold &= s->compute(s, in, j, nb_samples_read) > s->start_threshold;
629  }
630  }
631 
632  if (threshold) {
633  for (j = 0; j < outlink->ch_layout.nb_channels; j++) {
634  s->update(s, in, j, nb_samples_read);
635  s->copy(s, s->start_holdoff, in, j, s->start_holdoff_end, nb_samples_read);
636  }
637 
638  s->window_offset++;
639  if (s->window_offset >= s->window_duration)
640  s->window_offset = 0;
641  s->start_holdoff_end++;
642  nb_samples_read++;
643 
644  if (s->start_holdoff_end >= s->start_duration) {
645  s->start_found_periods += s->one_period >= 1;
646  s->one_period = 0;
647  if (s->start_found_periods >= s->start_periods) {
648  s->mode = SILENCE_TRIM_FLUSH;
649  goto silence_trim_flush;
650  }
651 
652  s->start_holdoff_offset = 0;
653  s->start_holdoff_end = 0;
654  s->start_silence_offset = 0;
655  s->start_silence_end = 0;
656  }
657  } else {
658  s->start_holdoff_end = 0;
659  s->one_period++;
660 
661  for (j = 0; j < outlink->ch_layout.nb_channels; j++) {
662  s->update(s, in, j, nb_samples_read);
663  if (s->start_silence)
664  s->copy(s, s->start_silence_hold, in, j, s->start_silence_offset, nb_samples_read);
665  }
666 
667  s->window_offset++;
668  if (s->window_offset >= s->window_duration)
669  s->window_offset = 0;
670  nb_samples_read++;
671  s->start_silence_offset++;
672 
673  if (s->start_silence) {
674  s->start_silence_end = FFMIN(s->start_silence_end + 1, s->start_silence);
675  if (s->start_silence_offset >= s->start_silence)
676  s->start_silence_offset = 0;
677  }
678  }
679  }
680  break;
681 
682  case SILENCE_TRIM_FLUSH:
683 silence_trim_flush:
684  nbs = s->start_holdoff_end - s->start_holdoff_offset;
685  if (!nbs)
686  break;
687 
688  out = ff_get_audio_buffer(outlink, nbs + s->start_silence_end);
689  if (!out) {
690  av_frame_free(&in);
691  return AVERROR(ENOMEM);
692  }
693 
694  if (s->start_silence_end > 0) {
695  if (s->start_silence_offset < s->start_silence_end) {
696  av_samples_copy(out->extended_data, s->start_silence_hold->extended_data, 0,
697  s->start_silence_offset,
698  s->start_silence_end - s->start_silence_offset,
699  outlink->ch_layout.nb_channels, outlink->format);
700  }
701 
702  if (s->start_silence_offset > 0) {
703  av_samples_copy(out->extended_data, s->start_silence_hold->extended_data,
704  s->start_silence_end - s->start_silence_offset,
705  0, s->start_silence_offset,
706  outlink->ch_layout.nb_channels, outlink->format);
707  }
708  }
709 
710  av_samples_copy(out->extended_data, s->start_holdoff->extended_data,
711  s->start_silence_end,
712  s->start_holdoff_offset, nbs,
713  outlink->ch_layout.nb_channels, outlink->format);
714 
715  s->start_holdoff_offset += nbs;
716 
717  av_audio_fifo_write(s->fifo, (void **)out->extended_data, out->nb_samples);
718  av_frame_free(&out);
719 
720  if (s->start_holdoff_offset == s->start_holdoff_end) {
721  s->start_holdoff_offset = 0;
722  s->start_holdoff_end = 0;
723  s->start_silence_offset = 0;
724  s->start_silence_end = 0;
725  s->mode = SILENCE_COPY;
726  goto silence_copy;
727  }
728  break;
729 
730  case SILENCE_COPY:
731 silence_copy:
732  nbs = in->nb_samples - nb_samples_read;
733  if (!nbs)
734  break;
735 
736  out = ff_get_audio_buffer(outlink, nbs);
737  if (!out) {
738  av_frame_free(&in);
739  return AVERROR(ENOMEM);
740  }
741 
742  if (s->stop_periods) {
743  for (i = 0; i < nbs; i++) {
744  if (s->stop_mode == T_ANY) {
745  threshold = 0;
746  for (j = 0; j < outlink->ch_layout.nb_channels; j++) {
747  threshold |= s->compute(s, in, j, nb_samples_read) > s->stop_threshold;
748  }
749  } else {
750  threshold = 1;
751  for (j = 0; j < outlink->ch_layout.nb_channels; j++) {
752  threshold &= s->compute(s, in, j, nb_samples_read) > s->stop_threshold;
753  }
754  }
755 
756  if (threshold && s->stop_holdoff_end && !s->stop_silence) {
757  s->mode = SILENCE_COPY_FLUSH;
758  flush(s, out, outlink, &nb_samples_written, 0);
759  s->one_period++;
760  goto silence_copy_flush;
761  } else if (threshold) {
762  for (j = 0; j < outlink->ch_layout.nb_channels; j++) {
763  s->update(s, in, j, nb_samples_read);
764  s->copy(s, out, in, j, nb_samples_written, nb_samples_read);
765  }
766 
767  s->window_offset++;
768  if (s->window_offset >= s->window_duration)
769  s->window_offset = 0;
770  nb_samples_read++;
771  nb_samples_written++;
772  s->one_period++;
773  } else if (!threshold) {
774  for (j = 0; j < outlink->ch_layout.nb_channels; j++) {
775  s->update(s, in, j, nb_samples_read);
776  if (s->stop_silence)
777  s->copy(s, s->stop_silence_hold, in, j, s->stop_silence_offset, nb_samples_read);
778 
779  s->copy(s, s->stop_holdoff, in, j, s->stop_holdoff_end, nb_samples_read);
780  }
781 
782  if (s->stop_silence) {
783  s->stop_silence_offset++;
784  s->stop_silence_end = FFMIN(s->stop_silence_end + 1, s->stop_silence);
785  if (s->stop_silence_offset >= s->stop_silence) {
786  s->stop_silence_offset = 0;
787  }
788  }
789 
790  s->window_offset++;
791  if (s->window_offset >= s->window_duration)
792  s->window_offset = 0;
793  nb_samples_read++;
794  s->stop_holdoff_end++;
795 
796  if (s->stop_holdoff_end >= s->stop_duration) {
797  s->stop_found_periods += s->one_period >= 1;
798  s->one_period = 0;
799  if (s->stop_found_periods >= s->stop_periods) {
800  s->stop_holdoff_offset = 0;
801  s->stop_holdoff_end = 0;
802 
803  if (!s->restart) {
804  s->mode = SILENCE_STOP;
805  flush(s, out, outlink, &nb_samples_written, 1);
806  goto silence_stop;
807  } else {
808  s->stop_found_periods = 0;
809  s->start_found_periods = 0;
810  s->start_holdoff_offset = 0;
811  s->start_holdoff_end = 0;
812  s->start_silence_offset = 0;
813  s->start_silence_end = 0;
814  clear_window(s);
815  s->mode = SILENCE_TRIM;
816  flush(s, out, outlink, &nb_samples_written, 1);
817  goto silence_trim;
818  }
819  }
820  s->mode = SILENCE_COPY_FLUSH;
821  flush(s, out, outlink, &nb_samples_written, 0);
822  goto silence_copy_flush;
823  }
824  }
825  }
826  s->one_period++;
827  flush(s, out, outlink, &nb_samples_written, 0);
828  } else {
829  av_samples_copy(out->extended_data, in->extended_data,
830  nb_samples_written,
831  nb_samples_read, nbs,
832  outlink->ch_layout.nb_channels, outlink->format);
833 
834  av_audio_fifo_write(s->fifo, (void **)out->extended_data, out->nb_samples);
835  av_frame_free(&out);
836  }
837  break;
838 
839  case SILENCE_COPY_FLUSH:
840 silence_copy_flush:
841  nbs = s->stop_holdoff_end - s->stop_holdoff_offset;
842  if (!nbs)
843  break;
844 
845  out = ff_get_audio_buffer(outlink, nbs);
846  if (!out) {
847  av_frame_free(&in);
848  return AVERROR(ENOMEM);
849  }
850 
851  av_samples_copy(out->extended_data, s->stop_holdoff->extended_data, 0,
852  s->stop_holdoff_offset, nbs,
853  outlink->ch_layout.nb_channels, outlink->format);
854 
855  s->stop_holdoff_offset += nbs;
856 
857  av_audio_fifo_write(s->fifo, (void **)out->extended_data, out->nb_samples);
858  av_frame_free(&out);
859 
860  if (s->stop_holdoff_offset == s->stop_holdoff_end) {
861  s->stop_holdoff_offset = 0;
862  s->stop_holdoff_end = 0;
863  s->stop_silence_offset = 0;
864  s->stop_silence_end = 0;
865  s->mode = SILENCE_COPY;
866  goto silence_copy;
867  }
868  break;
869  case SILENCE_STOP:
870 silence_stop:
871  break;
872  default:
873  ret = AVERROR_BUG;
874  }
875 
876  av_frame_free(&in);
877 
878  if (av_audio_fifo_size(s->fifo) > 0) {
879  out = ff_get_audio_buffer(outlink, av_audio_fifo_size(s->fifo));
880  if (!out)
881  return AVERROR(ENOMEM);
882 
883  av_audio_fifo_read(s->fifo, (void **)out->extended_data, out->nb_samples);
884  out->pts = s->next_pts;
885  s->next_pts += av_rescale_q(out->nb_samples,
886  (AVRational){1, outlink->sample_rate},
887  outlink->time_base);
888 
889  ret = ff_filter_frame(outlink, out);
890  }
891 
892  return ret;
893 }
894 
895 static int request_frame(AVFilterLink *outlink)
896 {
897  AVFilterContext *ctx = outlink->src;
898  SilenceRemoveContext *s = ctx->priv;
899  int ret;
900 
901  ret = ff_request_frame(ctx->inputs[0]);
902  if (ret == AVERROR_EOF && (s->mode == SILENCE_COPY_FLUSH ||
903  s->mode == SILENCE_COPY)) {
904  int nbs = s->stop_holdoff_end - s->stop_holdoff_offset;
905  if (nbs) {
906  AVFrame *frame;
907 
908  frame = ff_get_audio_buffer(outlink, nbs);
909  if (!frame)
910  return AVERROR(ENOMEM);
911 
912  av_samples_copy(frame->extended_data, s->stop_holdoff->extended_data, 0,
913  s->stop_holdoff_offset, nbs,
914  outlink->ch_layout.nb_channels, outlink->format);
915 
916  frame->pts = s->next_pts;
917  s->next_pts += av_rescale_q(frame->nb_samples,
918  (AVRational){1, outlink->sample_rate},
919  outlink->time_base);
920 
921  ret = ff_filter_frame(outlink, frame);
922  }
923  s->mode = SILENCE_STOP;
924  }
925  return ret;
926 }
927 
929 {
930  SilenceRemoveContext *s = ctx->priv;
931 
932  av_frame_free(&s->start_holdoff);
933  av_frame_free(&s->start_silence_hold);
934  av_frame_free(&s->stop_holdoff);
935  av_frame_free(&s->stop_silence_hold);
936  av_frame_free(&s->window);
937 
938  av_audio_fifo_free(s->fifo);
939  s->fifo = NULL;
940 }
941 
943  {
944  .name = "default",
945  .type = AVMEDIA_TYPE_AUDIO,
946  .config_props = config_input,
947  .filter_frame = filter_frame,
948  },
949 };
950 
952  {
953  .name = "default",
954  .type = AVMEDIA_TYPE_AUDIO,
955  .request_frame = request_frame,
956  },
957 };
958 
960  .name = "silenceremove",
961  .description = NULL_IF_CONFIG_SMALL("Remove silence."),
962  .priv_size = sizeof(SilenceRemoveContext),
963  .priv_class = &silenceremove_class,
964  .init = init,
965  .uninit = uninit,
970 };
av_audio_fifo_free
void av_audio_fifo_free(AVAudioFifo *af)
Free an AVAudioFifo.
Definition: audio_fifo.c:48
compute_rms_double
static double compute_rms_double(SilenceRemoveContext *s, AVFrame *frame, int ch, int offset)
Definition: af_silenceremove.c:233
ff_get_audio_buffer
AVFrame * ff_get_audio_buffer(AVFilterLink *link, int nb_samples)
Request an audio samples buffer with a specific set of permissions.
Definition: audio.c:100
AV_SAMPLE_FMT_FLTP
@ AV_SAMPLE_FMT_FLTP
float, planar
Definition: samplefmt.h:66
update_rms_doublep
static void update_rms_doublep(SilenceRemoveContext *s, AVFrame *frame, int ch, int offset)
Definition: af_silenceremove.c:368
SilenceRemoveContext::fifo
AVAudioFifo * fifo
Definition: af_silenceremove.c:107
update_rms_float
static void update_rms_float(SilenceRemoveContext *s, AVFrame *frame, int ch, int offset)
Definition: af_silenceremove.c:280
AVERROR
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 they are references to shared objects When the negotiation mechanism computes the intersection of the formats supported at each end of a all references to both lists are replaced with a reference to the intersection And when a single format is eventually chosen for a link amongst the remaining all references to the list are updated That means that if a filter requires that its input and output have the same format amongst a supported all it has to do is use a reference to the same list of formats query_formats can leave some formats unset and return AVERROR(EAGAIN) to cause the negotiation mechanism toagain later. That can be used by filters with complex requirements to use the format negotiated on one link to set the formats supported on another. Frame references ownership and permissions
opt.h
out
FILE * out
Definition: movenc.c:54
SilenceRemoveContext::stop_silence_offset
size_t stop_silence_offset
Definition: af_silenceremove.c:88
ff_filter_frame
int ff_filter_frame(AVFilterLink *link, AVFrame *frame)
Send a frame of data to the next filter.
Definition: avfilter.c:969
AVERROR_EOF
#define AVERROR_EOF
End of file.
Definition: error.h:57
init
static av_cold int init(AVFilterContext *ctx)
Definition: af_silenceremove.c:411
inlink
The exact code depends on how similar the blocks are and how related they are to the and needs to apply these operations to the correct inlink or outlink if there are several Macros are available to factor that when no extra processing is inlink
Definition: filter_design.txt:212
av_frame_free
void av_frame_free(AVFrame **frame)
Free the frame and any dynamically allocated objects in it, e.g.
Definition: frame.c:99
SilenceRemoveContext::start_holdoff_offset
size_t start_holdoff_offset
Definition: af_silenceremove.c:78
AVFrame
This structure describes decoded (raw) audio or video data.
Definition: frame.h:330
request_frame
static int request_frame(AVFilterLink *outlink)
Definition: af_silenceremove.c:895
AVFrame::pts
int64_t pts
Presentation timestamp in time_base units (time when frame should be shown to user).
Definition: frame.h:437
SilenceDetect
SilenceDetect
Definition: af_silenceremove.c:35
SilenceRemoveContext::stop_silence_hold
AVFrame * stop_silence_hold
Definition: af_silenceremove.c:85
AVOption
AVOption.
Definition: opt.h:251
AV_OPT_TYPE_DURATION
@ AV_OPT_TYPE_DURATION
Definition: opt.h:239
ff_request_frame
int ff_request_frame(AVFilterLink *link)
Request an input frame from the filter at the other end of the link.
Definition: avfilter.c:415
silenceremove_inputs
static const AVFilterPad silenceremove_inputs[]
Definition: af_silenceremove.c:942
SilenceRemoveContext::start_duration_opt
int64_t start_duration_opt
Definition: af_silenceremove.c:60
float.h
update_peak_float
static void update_peak_float(SilenceRemoveContext *s, AVFrame *frame, int ch, int offset)
Definition: af_silenceremove.c:220
FFMAX
#define FFMAX(a, b)
Definition: macros.h:47
AVFilter::name
const char * name
Filter name.
Definition: avfilter.h:165
SilenceRemoveContext::start_silence_opt
int64_t start_silence_opt
Definition: af_silenceremove.c:63
AVChannelLayout::nb_channels
int nb_channels
Number of channels in this layout.
Definition: channel_layout.h:311
SilenceRemoveContext::stop_silence
int64_t stop_silence
Definition: af_silenceremove.c:70
AVFILTER_DEFINE_CLASS
AVFILTER_DEFINE_CLASS(silenceremove)
AVFrame::data
uint8_t * data[AV_NUM_DATA_POINTERS]
pointer to the picture/channel planes.
Definition: frame.h:351
formats.h
compute_rms_float
static double compute_rms_float(SilenceRemoveContext *s, AVFrame *frame, int ch, int offset)
Definition: af_silenceremove.c:263
AVAudioFifo
Context for an Audio FIFO Buffer.
Definition: audio_fifo.c:37
SilenceRemoveContext::detection
int detection
Definition: af_silenceremove.c:101
SilenceRemoveContext::window_offset
int window_offset
Definition: af_silenceremove.c:93
AVFrame::ch_layout
AVChannelLayout ch_layout
Channel layout of the audio data.
Definition: frame.h:723
copy_floatp
static void copy_floatp(SilenceRemoveContext *s, AVFrame *out, AVFrame *in, int ch, int out_offset, int in_offset)
Definition: af_silenceremove.c:165
fabsf
static __device__ float fabsf(float a)
Definition: cuda_runtime.h:181
compute_peak_floatp
static double compute_peak_floatp(SilenceRemoveContext *s, AVFrame *frame, int ch, int offset)
Definition: af_silenceremove.c:322
AVFilterPad
A filter pad used for either input or output.
Definition: internal.h:49
compute_peak_doublep
static double compute_peak_doublep(SilenceRemoveContext *s, AVFrame *frame, int ch, int offset)
Definition: af_silenceremove.c:293
avassert.h
av_cold
#define av_cold
Definition: attributes.h:90
s
#define s(width, name)
Definition: cbs_vp9.c:256
flush
static void flush(SilenceRemoveContext *s, AVFrame *out, AVFilterLink *outlink, int *nb_samples_written, int flush_silence)
Definition: af_silenceremove.c:555
SilenceRemoveContext::mode
enum SilenceMode mode
Definition: af_silenceremove.c:56
SILENCE_STOP
@ SILENCE_STOP
Definition: af_silenceremove.c:50
av_audio_fifo_write
int av_audio_fifo_write(AVAudioFifo *af, void **data, int nb_samples)
Write data to an AVAudioFifo.
Definition: audio_fifo.c:119
AV_OPT_TYPE_DOUBLE
@ AV_OPT_TYPE_DOUBLE
Definition: opt.h:227
AVMEDIA_TYPE_AUDIO
@ AVMEDIA_TYPE_AUDIO
Definition: avutil.h:202
filter_frame
static int filter_frame(AVFilterLink *inlink, AVFrame *in)
Definition: af_silenceremove.c:598
ctx
AVFormatContext * ctx
Definition: movenc.c:48
update_peak_floatp
static void update_peak_floatp(SilenceRemoveContext *s, AVFrame *frame, int ch, int offset)
Definition: af_silenceremove.c:338
av_rescale_q
int64_t av_rescale_q(int64_t a, AVRational bq, AVRational cq)
Rescale a 64-bit integer by 2 rational numbers.
Definition: mathematics.c:142
SilenceRemoveContext::start_silence_end
size_t start_silence_end
Definition: af_silenceremove.c:81
SilenceRemoveContext::start_silence_hold
AVFrame * start_silence_hold
Definition: af_silenceremove.c:77
compute_rms_doublep
static double compute_rms_doublep(SilenceRemoveContext *s, AVFrame *frame, int ch, int offset)
Definition: af_silenceremove.c:351
FILTER_INPUTS
#define FILTER_INPUTS(array)
Definition: internal.h:194
AVClass
Describe the class of an AVClass context structure.
Definition: log.h:66
fabs
static __device__ float fabs(float a)
Definition: cuda_runtime.h:182
NULL
#define NULL
Definition: coverity.c:32
compute_peak_double
static double compute_peak_double(SilenceRemoveContext *s, AVFrame *frame, int ch, int offset)
Definition: af_silenceremove.c:175
AVRational
Rational number (pair of numerator and denominator).
Definition: rational.h:58
av_audio_fifo_alloc
AVAudioFifo * av_audio_fifo_alloc(enum AVSampleFormat sample_fmt, int channels, int nb_samples)
Allocate an AVAudioFifo.
Definition: audio_fifo.c:62
SilenceRemoveContext::stop_holdoff
AVFrame * stop_holdoff
Definition: af_silenceremove.c:84
sqrtf
static __device__ float sqrtf(float a)
Definition: cuda_runtime.h:184
double
double
Definition: af_crystalizer.c:132
SilenceRemoveContext::start_silence_offset
size_t start_silence_offset
Definition: af_silenceremove.c:80
SilenceRemoveContext
Definition: af_silenceremove.c:53
SilenceRemoveContext::one_period
int one_period
Definition: af_silenceremove.c:97
SILENCE_TRIM
@ SILENCE_TRIM
Definition: af_silenceremove.c:46
SilenceRemoveContext::start_threshold
double start_threshold
Definition: af_silenceremove.c:61
silenceremove_options
static const AVOption silenceremove_options[]
Definition: af_silenceremove.c:113
uninit
static av_cold void uninit(AVFilterContext *ctx)
Definition: af_silenceremove.c:928
copy_double
static void copy_double(SilenceRemoveContext *s, AVFrame *out, AVFrame *in, int ch, int out_offset, int in_offset)
Definition: af_silenceremove.c:135
SilenceRemoveContext::window_duration_opt
int64_t window_duration_opt
Definition: af_silenceremove.c:74
SILENCE_COPY_FLUSH
@ SILENCE_COPY_FLUSH
Definition: af_silenceremove.c:49
AF
#define AF
Definition: af_silenceremove.c:111
SilenceRemoveContext::start_found_periods
int start_found_periods
Definition: af_silenceremove.c:82
f
f
Definition: af_crystalizer.c:122
NULL_IF_CONFIG_SMALL
#define NULL_IF_CONFIG_SMALL(x)
Return NULL if CONFIG_SMALL is true, otherwise the argument without modification.
Definition: internal.h:115
config_input
static int config_input(AVFilterLink *inlink)
Definition: af_silenceremove.c:432
fmaxf
float fmaxf(float, float)
sample
#define sample
Definition: flacdsp_template.c:44
AV_NOPTS_VALUE
#define AV_NOPTS_VALUE
Undefined timestamp value.
Definition: avutil.h:248
SilenceRemoveContext::stop_holdoff_offset
size_t stop_holdoff_offset
Definition: af_silenceremove.c:86
update_peak_doublep
static void update_peak_doublep(SilenceRemoveContext *s, AVFrame *frame, int ch, int offset)
Definition: af_silenceremove.c:309
SilenceRemoveContext::stop_periods
int stop_periods
Definition: af_silenceremove.c:66
offset
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 offset
Definition: writing_filters.txt:86
SILENCE_COPY
@ SILENCE_COPY
Definition: af_silenceremove.c:48
av_audio_fifo_size
int av_audio_fifo_size(AVAudioFifo *af)
Get the current number of samples in the AVAudioFifo available for reading.
Definition: audio_fifo.c:221
clear_window
static void clear_window(SilenceRemoveContext *s)
Definition: af_silenceremove.c:423
SilenceRemoveContext::sum
double sum
Definition: af_silenceremove.c:95
SILENCE_TRIM_FLUSH
@ SILENCE_TRIM_FLUSH
Definition: af_silenceremove.c:47
SilenceRemoveContext::start_holdoff_end
size_t start_holdoff_end
Definition: af_silenceremove.c:79
internal.h
av_audio_fifo_read
int av_audio_fifo_read(AVAudioFifo *af, void **data, int nb_samples)
Read data from an AVAudioFifo.
Definition: audio_fifo.c:174
av_samples_copy
int av_samples_copy(uint8_t **dst, uint8_t *const *src, int dst_offset, int src_offset, int nb_samples, int nb_channels, enum AVSampleFormat sample_fmt)
Copy samples from src to dst.
Definition: samplefmt.c:222
av_assert2
#define av_assert2(cond)
assert() equivalent, that does lie in speed critical code.
Definition: avassert.h:64
update_rms_double
static void update_rms_double(SilenceRemoveContext *s, AVFrame *frame, int ch, int offset)
Definition: af_silenceremove.c:250
AVFrame::nb_samples
int nb_samples
number of audio samples (per channel) described by this frame
Definition: frame.h:410
update_peak_double
static void update_peak_double(SilenceRemoveContext *s, AVFrame *frame, int ch, int offset)
Definition: af_silenceremove.c:191
SilenceRemoveContext::stop_silence_opt
int64_t stop_silence_opt
Definition: af_silenceremove.c:71
i
#define i(width, name, range_min, range_max)
Definition: cbs_h2645.c:269
ff_af_silenceremove
const AVFilter ff_af_silenceremove
Definition: af_silenceremove.c:959
SilenceRemoveContext::stop_mode
int stop_mode
Definition: af_silenceremove.c:72
AV_TIME_BASE
#define AV_TIME_BASE
Internal time base represented as integer.
Definition: avutil.h:254
AVFrame::extended_data
uint8_t ** extended_data
pointers to the data planes/channels.
Definition: frame.h:391
SilenceMode
SilenceMode
Definition: af_silenceremove.c:45
SilenceRemoveContext::stop_duration
int64_t stop_duration
Definition: af_silenceremove.c:67
FFMIN
#define FFMIN(a, b)
Definition: macros.h:49
audio_fifo.h
SilenceRemoveContext::stop_silence_end
size_t stop_silence_end
Definition: af_silenceremove.c:89
AVFilterPad::name
const char * name
Pad name.
Definition: internal.h:55
av_rescale
int64_t av_rescale(int64_t a, int64_t b, int64_t c)
Rescale a 64-bit integer with rounding to nearest.
Definition: mathematics.c:129
SilenceRemoveContext::stop_found_periods
int stop_found_periods
Definition: af_silenceremove.c:90
update_rms_floatp
static void update_rms_floatp(SilenceRemoveContext *s, AVFrame *frame, int ch, int offset)
Definition: af_silenceremove.c:398
SilenceRemoveContext::start_mode
int start_mode
Definition: af_silenceremove.c:64
SilenceRemoveContext::update
void(* update)(struct SilenceRemoveContext *s, AVFrame *frame, int ch, int offset)
Definition: af_silenceremove.c:102
SilenceRemoveContext::compute
double(* compute)(struct SilenceRemoveContext *s, AVFrame *frame, int ch, int offset)
Definition: af_silenceremove.c:103
av_samples_set_silence
int av_samples_set_silence(uint8_t **audio_data, int offset, int nb_samples, int nb_channels, enum AVSampleFormat sample_fmt)
Fill an audio buffer with silence.
Definition: samplefmt.c:246
AVFilter
Filter definition.
Definition: avfilter.h:161
SilenceRemoveContext::stop_threshold
double stop_threshold
Definition: af_silenceremove.c:69
ret
ret
Definition: filter_design.txt:187
frame
these buffered frames must be flushed immediately if a new input produces new the filter must not call request_frame to get more It must just process the frame or queue it The task of requesting more frames is left to the filter s request_frame method or the application If a filter has several the filter must be ready for frames arriving randomly on any input any filter with several inputs will most likely require some kind of queuing mechanism It is perfectly acceptable to have a limited queue and to drop frames when the inputs are too unbalanced request_frame For filters that do not use the this method is called when a frame is wanted on an output For a it should directly call filter_frame on the corresponding output For a if there are queued frames already one of these frames should be pushed If the filter should request a frame on one of its repeatedly until at least one frame has been pushed Return or at least make progress towards producing a frame
Definition: filter_design.txt:264
SilenceRemoveContext::restart
int restart
Definition: af_silenceremove.c:98
SilenceRemoveContext::window_duration
int64_t window_duration
Definition: af_silenceremove.c:94
compute_peak_float
static double compute_peak_float(SilenceRemoveContext *s, AVFrame *frame, int ch, int offset)
Definition: af_silenceremove.c:204
fmax
double fmax(double, double)
D_PEAK
@ D_PEAK
Definition: af_silenceremove.c:36
OFFSET
#define OFFSET(x)
Definition: af_silenceremove.c:110
SilenceRemoveContext::window
AVFrame * window
Definition: af_silenceremove.c:92
SilenceRemoveContext::start_periods
int start_periods
Definition: af_silenceremove.c:58
copy_doublep
static void copy_doublep(SilenceRemoveContext *s, AVFrame *out, AVFrame *in, int ch, int out_offset, int in_offset)
Definition: af_silenceremove.c:145
AV_OPT_TYPE_INT
@ AV_OPT_TYPE_INT
Definition: opt.h:225
avfilter.h
AV_SAMPLE_FMT_DBLP
@ AV_SAMPLE_FMT_DBLP
double, planar
Definition: samplefmt.h:67
samples
Filter the word “frame” indicates either a video frame or a group of audio samples
Definition: filter_design.txt:8
AVFilterContext
An instance of a filter.
Definition: avfilter.h:392
ThresholdMode
ThresholdMode
Definition: af_silenceremove.c:40
audio.h
SilenceRemoveContext::stop_duration_opt
int64_t stop_duration_opt
Definition: af_silenceremove.c:68
SilenceRemoveContext::start_silence
int64_t start_silence
Definition: af_silenceremove.c:62
compute_rms_floatp
static double compute_rms_floatp(SilenceRemoveContext *s, AVFrame *frame, int ch, int offset)
Definition: af_silenceremove.c:381
SilenceRemoveContext::copy
void(* copy)(struct SilenceRemoveContext *s, AVFrame *out, AVFrame *in, int ch, int out_offset, int in_offset)
Definition: af_silenceremove.c:104
FILTER_OUTPUTS
#define FILTER_OUTPUTS(array)
Definition: internal.h:195
src
INIT_CLIP pixel * src
Definition: h264pred_template.c:418
silenceremove_outputs
static const AVFilterPad silenceremove_outputs[]
Definition: af_silenceremove.c:951
SilenceRemoveContext::start_holdoff
AVFrame * start_holdoff
Definition: af_silenceremove.c:76
timestamp.h
AVERROR_BUG
#define AVERROR_BUG
Internal bug, also see AVERROR_BUG2.
Definition: error.h:52
copy_float
static void copy_float(SilenceRemoveContext *s, AVFrame *out, AVFrame *in, int ch, int out_offset, int in_offset)
Definition: af_silenceremove.c:155
T_ALL
@ T_ALL
Definition: af_silenceremove.c:42
AV_SAMPLE_FMT_DBL
@ AV_SAMPLE_FMT_DBL
double
Definition: samplefmt.h:61
D_RMS
@ D_RMS
Definition: af_silenceremove.c:37
AV_OPT_TYPE_CONST
@ AV_OPT_TYPE_CONST
Definition: opt.h:234
SilenceRemoveContext::stop_holdoff_end
size_t stop_holdoff_end
Definition: af_silenceremove.c:87
AV_SAMPLE_FMT_FLT
@ AV_SAMPLE_FMT_FLT
float
Definition: samplefmt.h:60
SilenceRemoveContext::start_duration
int64_t start_duration
Definition: af_silenceremove.c:59
T_ANY
@ T_ANY
Definition: af_silenceremove.c:41
FILTER_SAMPLEFMTS
#define FILTER_SAMPLEFMTS(...)
Definition: internal.h:182
SilenceRemoveContext::next_pts
int64_t next_pts
Definition: af_silenceremove.c:99