FFmpeg
f_ebur128.c
Go to the documentation of this file.
1 /*
2  * Copyright (c) 2012 Clément Bœsch
3  *
4  * This file is part of FFmpeg.
5  *
6  * FFmpeg is free software; you can redistribute it and/or
7  * modify it under the terms of the GNU Lesser General Public
8  * License as published by the Free Software Foundation; either
9  * version 2.1 of the License, or (at your option) any later version.
10  *
11  * FFmpeg is distributed in the hope that it will be useful,
12  * but WITHOUT ANY WARRANTY; without even the implied warranty of
13  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14  * Lesser General Public License for more details.
15  *
16  * You should have received a copy of the GNU Lesser General Public
17  * License along with FFmpeg; if not, write to the Free Software
18  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
19  */
20 
21 /**
22  * @file
23  * EBU R.128 implementation
24  * @see http://tech.ebu.ch/loudness
25  * @see https://www.youtube.com/watch?v=iuEtQqC-Sqo "EBU R128 Introduction - Florian Camerer"
26  * @todo implement start/stop/reset through filter command injection
27  */
28 
29 #include <float.h>
30 #include <math.h>
31 
32 #include "libavutil/avassert.h"
33 #include "libavutil/avstring.h"
35 #include "libavutil/dict.h"
36 #include "libavutil/ffmath.h"
38 #include "libavutil/opt.h"
39 #include "libavutil/timestamp.h"
41 #include "audio.h"
42 #include "avfilter.h"
43 #include "filters.h"
44 #include "formats.h"
45 #include "internal.h"
46 #include "video.h"
47 
48 #define ABS_THRES -70 ///< silence gate: we discard anything below this absolute (LUFS) threshold
49 #define ABS_UP_THRES 10 ///< upper loud limit to consider (ABS_THRES being the minimum)
50 #define HIST_GRAIN 100 ///< defines histogram precision
51 #define HIST_SIZE ((ABS_UP_THRES - ABS_THRES) * HIST_GRAIN + 1)
52 
53 /**
54  * A histogram is an array of HIST_SIZE hist_entry storing all the energies
55  * recorded (with an accuracy of 1/HIST_GRAIN) of the loudnesses from ABS_THRES
56  * (at 0) to ABS_UP_THRES (at HIST_SIZE-1).
57  * This fixed-size system avoids the need of a list of energies growing
58  * infinitely over the time and is thus more scalable.
59  */
60 struct hist_entry {
61  unsigned count; ///< how many times the corresponding value occurred
62  double energy; ///< E = 10^((L + 0.691) / 10)
63  double loudness; ///< L = -0.691 + 10 * log10(E)
64 };
65 
66 struct integrator {
67  double **cache; ///< window of filtered samples (N ms)
68  int cache_pos; ///< focus on the last added bin in the cache array
70  double *sum; ///< sum of the last N ms filtered samples (cache content)
71  int filled; ///< 1 if the cache is completely filled, 0 otherwise
72  double rel_threshold; ///< relative threshold
73  double sum_kept_powers; ///< sum of the powers (weighted sums) above absolute threshold
74  int nb_kept_powers; ///< number of sum above absolute threshold
75  struct hist_entry *histogram; ///< histogram of the powers, used to compute LRA and I
76 };
77 
78 struct rect { int x, y, w, h; };
79 
80 typedef struct EBUR128Context {
81  const AVClass *class; ///< AVClass context for log and options purpose
82 
83  /* peak metering */
84  int peak_mode; ///< enabled peak modes
85  double true_peak; ///< global true peak
86  double *true_peaks; ///< true peaks per channel
87  double sample_peak; ///< global sample peak
88  double *sample_peaks; ///< sample peaks per channel
89  double *true_peaks_per_frame; ///< true peaks in a frame per channel
90 #if CONFIG_SWRESAMPLE
91  SwrContext *swr_ctx; ///< over-sampling context for true peak metering
92  double *swr_buf; ///< resampled audio data for true peak metering
93  int swr_linesize;
94 #endif
95 
96  /* video */
97  int do_video; ///< 1 if video output enabled, 0 otherwise
98  int w, h; ///< size of the video output
99  struct rect text; ///< rectangle for the LU legend on the left
100  struct rect graph; ///< rectangle for the main graph in the center
101  struct rect gauge; ///< rectangle for the gauge on the right
102  AVFrame *outpicref; ///< output picture reference, updated regularly
103  int meter; ///< select a EBU mode between +9 and +18
104  int scale_range; ///< the range of LU values according to the meter
105  int y_zero_lu; ///< the y value (pixel position) for 0 LU
106  int y_opt_max; ///< the y value (pixel position) for 1 LU
107  int y_opt_min; ///< the y value (pixel position) for -1 LU
108  int *y_line_ref; ///< y reference values for drawing the LU lines in the graph and the gauge
109 
110  /* audio */
111  int nb_channels; ///< number of channels in the input
112  double *ch_weighting; ///< channel weighting mapping
113  int sample_count; ///< sample count used for refresh frequency, reset at refresh
114  int nb_samples; ///< number of samples to consume per single input frame
115  int idx_insample; ///< current sample position of processed samples in single input frame
116  AVFrame *insamples; ///< input samples reference, updated regularly
117 
118  /* Filter caches.
119  * The mult by 3 in the following is for X[i], X[i-1] and X[i-2] */
120  double *x; ///< 3 input samples cache for each channel
121  double *y; ///< 3 pre-filter samples cache for each channel
122  double *z; ///< 3 RLB-filter samples cache for each channel
123  double pre_b[3]; ///< pre-filter numerator coefficients
124  double pre_a[3]; ///< pre-filter denominator coefficients
125  double rlb_b[3]; ///< rlb-filter numerator coefficients
126  double rlb_a[3]; ///< rlb-filter denominator coefficients
127 
128  struct integrator i400; ///< 400ms integrator, used for Momentary loudness (M), and Integrated loudness (I)
129  struct integrator i3000; ///< 3s integrator, used for Short term loudness (S), and Loudness Range (LRA)
130 
131  /* I and LRA specific */
132  double integrated_loudness; ///< integrated loudness in LUFS (I)
133  double loudness_range; ///< loudness range in LU (LRA)
134  double lra_low, lra_high; ///< low and high LRA values
135 
136  /* misc */
137  int loglevel; ///< log level for frame logging
138  int metadata; ///< whether or not to inject loudness results in frames
139  int dual_mono; ///< whether or not to treat single channel input files as dual-mono
140  double pan_law; ///< pan law value used to calculate dual-mono measurements
141  int target; ///< target level in LUFS used to set relative zero LU in visualization
142  int gauge_type; ///< whether gauge shows momentary or short
143  int scale; ///< display scale type of statistics
145 
146 enum {
150 };
151 
152 enum {
155 };
156 
157 enum {
160 };
161 
162 #define OFFSET(x) offsetof(EBUR128Context, x)
163 #define A AV_OPT_FLAG_AUDIO_PARAM
164 #define V AV_OPT_FLAG_VIDEO_PARAM
165 #define F AV_OPT_FLAG_FILTERING_PARAM
166 #define X AV_OPT_FLAG_EXPORT
167 #define R AV_OPT_FLAG_READONLY
168 static const AVOption ebur128_options[] = {
169  { "video", "set video output", OFFSET(do_video), AV_OPT_TYPE_BOOL, {.i64 = 0}, 0, 1, V|F },
170  { "size", "set video size", OFFSET(w), AV_OPT_TYPE_IMAGE_SIZE, {.str = "640x480"}, 0, 0, V|F },
171  { "meter", "set scale meter (+9 to +18)", OFFSET(meter), AV_OPT_TYPE_INT, {.i64 = 9}, 9, 18, V|F },
172  { "framelog", "force frame logging level", OFFSET(loglevel), AV_OPT_TYPE_INT, {.i64 = -1}, INT_MIN, INT_MAX, A|V|F, .unit = "level" },
173  { "quiet", "logging disabled", 0, AV_OPT_TYPE_CONST, {.i64 = AV_LOG_QUIET}, INT_MIN, INT_MAX, A|V|F, .unit = "level" },
174  { "info", "information logging level", 0, AV_OPT_TYPE_CONST, {.i64 = AV_LOG_INFO}, INT_MIN, INT_MAX, A|V|F, .unit = "level" },
175  { "verbose", "verbose logging level", 0, AV_OPT_TYPE_CONST, {.i64 = AV_LOG_VERBOSE}, INT_MIN, INT_MAX, A|V|F, .unit = "level" },
176  { "metadata", "inject metadata in the filtergraph", OFFSET(metadata), AV_OPT_TYPE_BOOL, {.i64 = 0}, 0, 1, A|V|F },
177  { "peak", "set peak mode", OFFSET(peak_mode), AV_OPT_TYPE_FLAGS, {.i64 = PEAK_MODE_NONE}, 0, INT_MAX, A|F, .unit = "mode" },
178  { "none", "disable any peak mode", 0, AV_OPT_TYPE_CONST, {.i64 = PEAK_MODE_NONE}, INT_MIN, INT_MAX, A|F, .unit = "mode" },
179  { "sample", "enable peak-sample mode", 0, AV_OPT_TYPE_CONST, {.i64 = PEAK_MODE_SAMPLES_PEAKS}, INT_MIN, INT_MAX, A|F, .unit = "mode" },
180  { "true", "enable true-peak mode", 0, AV_OPT_TYPE_CONST, {.i64 = PEAK_MODE_TRUE_PEAKS}, INT_MIN, INT_MAX, A|F, .unit = "mode" },
181  { "dualmono", "treat mono input files as dual-mono", OFFSET(dual_mono), AV_OPT_TYPE_BOOL, {.i64 = 0}, 0, 1, A|F },
182  { "panlaw", "set a specific pan law for dual-mono files", OFFSET(pan_law), AV_OPT_TYPE_DOUBLE, {.dbl = -3.01029995663978}, -10.0, 0.0, A|F },
183  { "target", "set a specific target level in LUFS (-23 to 0)", OFFSET(target), AV_OPT_TYPE_INT, {.i64 = -23}, -23, 0, V|F },
184  { "gauge", "set gauge display type", OFFSET(gauge_type), AV_OPT_TYPE_INT, {.i64 = 0 }, GAUGE_TYPE_MOMENTARY, GAUGE_TYPE_SHORTTERM, V|F, .unit = "gaugetype" },
185  { "momentary", "display momentary value", 0, AV_OPT_TYPE_CONST, {.i64 = GAUGE_TYPE_MOMENTARY}, INT_MIN, INT_MAX, V|F, .unit = "gaugetype" },
186  { "m", "display momentary value", 0, AV_OPT_TYPE_CONST, {.i64 = GAUGE_TYPE_MOMENTARY}, INT_MIN, INT_MAX, V|F, .unit = "gaugetype" },
187  { "shortterm", "display short-term value", 0, AV_OPT_TYPE_CONST, {.i64 = GAUGE_TYPE_SHORTTERM}, INT_MIN, INT_MAX, V|F, .unit = "gaugetype" },
188  { "s", "display short-term value", 0, AV_OPT_TYPE_CONST, {.i64 = GAUGE_TYPE_SHORTTERM}, INT_MIN, INT_MAX, V|F, .unit = "gaugetype" },
189  { "scale", "sets display method for the stats", OFFSET(scale), AV_OPT_TYPE_INT, {.i64 = 0}, SCALE_TYPE_ABSOLUTE, SCALE_TYPE_RELATIVE, V|F, .unit = "scaletype" },
190  { "absolute", "display absolute values (LUFS)", 0, AV_OPT_TYPE_CONST, {.i64 = SCALE_TYPE_ABSOLUTE}, INT_MIN, INT_MAX, V|F, .unit = "scaletype" },
191  { "LUFS", "display absolute values (LUFS)", 0, AV_OPT_TYPE_CONST, {.i64 = SCALE_TYPE_ABSOLUTE}, INT_MIN, INT_MAX, V|F, .unit = "scaletype" },
192  { "relative", "display values relative to target (LU)", 0, AV_OPT_TYPE_CONST, {.i64 = SCALE_TYPE_RELATIVE}, INT_MIN, INT_MAX, V|F, .unit = "scaletype" },
193  { "LU", "display values relative to target (LU)", 0, AV_OPT_TYPE_CONST, {.i64 = SCALE_TYPE_RELATIVE}, INT_MIN, INT_MAX, V|F, .unit = "scaletype" },
194  { "integrated", "integrated loudness (LUFS)", OFFSET(integrated_loudness), AV_OPT_TYPE_DOUBLE, {.dbl = 0}, -DBL_MAX, DBL_MAX, A|F|X|R },
195  { "range", "loudness range (LU)", OFFSET(loudness_range), AV_OPT_TYPE_DOUBLE, {.dbl = 0}, -DBL_MAX, DBL_MAX, A|F|X|R },
196  { "lra_low", "LRA low (LUFS)", OFFSET(lra_low), AV_OPT_TYPE_DOUBLE, {.dbl = 0}, -DBL_MAX, DBL_MAX, A|F|X|R },
197  { "lra_high", "LRA high (LUFS)", OFFSET(lra_high), AV_OPT_TYPE_DOUBLE, {.dbl = 0}, -DBL_MAX, DBL_MAX, A|F|X|R },
198  { "sample_peak", "sample peak (dBFS)", OFFSET(sample_peak), AV_OPT_TYPE_DOUBLE, {.dbl = 0}, -DBL_MAX, DBL_MAX, A|F|X|R },
199  { "true_peak", "true peak (dBFS)", OFFSET(true_peak), AV_OPT_TYPE_DOUBLE, {.dbl = 0}, -DBL_MAX, DBL_MAX, A|F|X|R },
200  { NULL },
201 };
202 
203 AVFILTER_DEFINE_CLASS(ebur128);
204 
205 static const uint8_t graph_colors[] = {
206  0xdd, 0x66, 0x66, // value above 1LU non reached below -1LU (impossible)
207  0x66, 0x66, 0xdd, // value below 1LU non reached below -1LU
208  0x96, 0x33, 0x33, // value above 1LU reached below -1LU (impossible)
209  0x33, 0x33, 0x96, // value below 1LU reached below -1LU
210  0xdd, 0x96, 0x96, // value above 1LU line non reached below -1LU (impossible)
211  0x96, 0x96, 0xdd, // value below 1LU line non reached below -1LU
212  0xdd, 0x33, 0x33, // value above 1LU line reached below -1LU (impossible)
213  0x33, 0x33, 0xdd, // value below 1LU line reached below -1LU
214  0xdd, 0x66, 0x66, // value above 1LU non reached above -1LU
215  0x66, 0xdd, 0x66, // value below 1LU non reached above -1LU
216  0x96, 0x33, 0x33, // value above 1LU reached above -1LU
217  0x33, 0x96, 0x33, // value below 1LU reached above -1LU
218  0xdd, 0x96, 0x96, // value above 1LU line non reached above -1LU
219  0x96, 0xdd, 0x96, // value below 1LU line non reached above -1LU
220  0xdd, 0x33, 0x33, // value above 1LU line reached above -1LU
221  0x33, 0xdd, 0x33, // value below 1LU line reached above -1LU
222 };
223 
224 static const uint8_t *get_graph_color(const EBUR128Context *ebur128, int v, int y)
225 {
226  const int above_opt_max = y > ebur128->y_opt_max;
227  const int below_opt_min = y < ebur128->y_opt_min;
228  const int reached = y >= v;
229  const int line = ebur128->y_line_ref[y] || y == ebur128->y_zero_lu;
230  const int colorid = 8*below_opt_min+ 4*line + 2*reached + above_opt_max;
231  return graph_colors + 3*colorid;
232 }
233 
234 static inline int lu_to_y(const EBUR128Context *ebur128, double v)
235 {
236  v += 2 * ebur128->meter; // make it in range [0;...]
237  v = av_clipf(v, 0, ebur128->scale_range); // make sure it's in the graph scale
238  v = ebur128->scale_range - v; // invert value (y=0 is on top)
239  return v * ebur128->graph.h / ebur128->scale_range; // rescale from scale range to px height
240 }
241 
242 #define FONT8 0
243 #define FONT16 1
244 
245 static const uint8_t font_colors[] = {
246  0xdd, 0xdd, 0x00,
247  0x00, 0x96, 0x96,
248 };
249 
250 static void drawtext(AVFrame *pic, int x, int y, int ftid, const uint8_t *color, const char *fmt, ...)
251 {
252  int i;
253  char buf[128] = {0};
254  const uint8_t *font;
255  int font_height;
256  va_list vl;
257 
258  if (ftid == FONT16) font = avpriv_vga16_font, font_height = 16;
259  else if (ftid == FONT8) font = avpriv_cga_font, font_height = 8;
260  else return;
261 
262  va_start(vl, fmt);
263  vsnprintf(buf, sizeof(buf), fmt, vl);
264  va_end(vl);
265 
266  for (i = 0; buf[i]; i++) {
267  int char_y, mask;
268  uint8_t *p = pic->data[0] + y*pic->linesize[0] + (x + i*8)*3;
269 
270  for (char_y = 0; char_y < font_height; char_y++) {
271  for (mask = 0x80; mask; mask >>= 1) {
272  if (font[buf[i] * font_height + char_y] & mask)
273  memcpy(p, color, 3);
274  else
275  memcpy(p, "\x00\x00\x00", 3);
276  p += 3;
277  }
278  p += pic->linesize[0] - 8*3;
279  }
280  }
281 }
282 
283 static void drawline(AVFrame *pic, int x, int y, int len, int step)
284 {
285  int i;
286  uint8_t *p = pic->data[0] + y*pic->linesize[0] + x*3;
287 
288  for (i = 0; i < len; i++) {
289  memcpy(p, "\x00\xff\x00", 3);
290  p += step;
291  }
292 }
293 
294 static int config_video_output(AVFilterLink *outlink)
295 {
296  int i, x, y;
297  uint8_t *p;
298  AVFilterContext *ctx = outlink->src;
299  EBUR128Context *ebur128 = ctx->priv;
300  AVFrame *outpicref;
301 
302  /* check if there is enough space to represent everything decently */
303  if (ebur128->w < 640 || ebur128->h < 480) {
304  av_log(ctx, AV_LOG_ERROR, "Video size %dx%d is too small, "
305  "minimum size is 640x480\n", ebur128->w, ebur128->h);
306  return AVERROR(EINVAL);
307  }
308  outlink->w = ebur128->w;
309  outlink->h = ebur128->h;
310  outlink->sample_aspect_ratio = (AVRational){1,1};
311  outlink->frame_rate = av_make_q(10, 1);
312  outlink->time_base = av_inv_q(outlink->frame_rate);
313 
314 #define PAD 8
315 
316  /* configure text area position and size */
317  ebur128->text.x = PAD;
318  ebur128->text.y = 40;
319  ebur128->text.w = 3 * 8; // 3 characters
320  ebur128->text.h = ebur128->h - PAD - ebur128->text.y;
321 
322  /* configure gauge position and size */
323  ebur128->gauge.w = 20;
324  ebur128->gauge.h = ebur128->text.h;
325  ebur128->gauge.x = ebur128->w - PAD - ebur128->gauge.w;
326  ebur128->gauge.y = ebur128->text.y;
327 
328  /* configure graph position and size */
329  ebur128->graph.x = ebur128->text.x + ebur128->text.w + PAD;
330  ebur128->graph.y = ebur128->gauge.y;
331  ebur128->graph.w = ebur128->gauge.x - ebur128->graph.x - PAD;
332  ebur128->graph.h = ebur128->gauge.h;
333 
334  /* graph and gauge share the LU-to-pixel code */
335  av_assert0(ebur128->graph.h == ebur128->gauge.h);
336 
337  /* prepare the initial picref buffer */
338  av_frame_free(&ebur128->outpicref);
339  ebur128->outpicref = outpicref =
340  ff_get_video_buffer(outlink, outlink->w, outlink->h);
341  if (!outpicref)
342  return AVERROR(ENOMEM);
343  outpicref->sample_aspect_ratio = (AVRational){1,1};
344 
345  /* init y references values (to draw LU lines) */
346  ebur128->y_line_ref = av_calloc(ebur128->graph.h + 1, sizeof(*ebur128->y_line_ref));
347  if (!ebur128->y_line_ref)
348  return AVERROR(ENOMEM);
349 
350  /* black background */
351  for (int y = 0; y < ebur128->h; y++)
352  memset(outpicref->data[0] + y * outpicref->linesize[0], 0, ebur128->w * 3);
353 
354  /* draw LU legends */
355  drawtext(outpicref, PAD, PAD+16, FONT8, font_colors+3, " LU");
356  for (i = ebur128->meter; i >= -ebur128->meter * 2; i--) {
357  y = lu_to_y(ebur128, i);
358  x = PAD + (i < 10 && i > -10) * 8;
359  ebur128->y_line_ref[y] = i;
360  y -= 4; // -4 to center vertically
361  drawtext(outpicref, x, y + ebur128->graph.y, FONT8, font_colors+3,
362  "%c%d", i < 0 ? '-' : i > 0 ? '+' : ' ', FFABS(i));
363  }
364 
365  /* draw graph */
366  ebur128->y_zero_lu = lu_to_y(ebur128, 0);
367  ebur128->y_opt_max = lu_to_y(ebur128, 1);
368  ebur128->y_opt_min = lu_to_y(ebur128, -1);
369  p = outpicref->data[0] + ebur128->graph.y * outpicref->linesize[0]
370  + ebur128->graph.x * 3;
371  for (y = 0; y < ebur128->graph.h; y++) {
372  const uint8_t *c = get_graph_color(ebur128, INT_MAX, y);
373 
374  for (x = 0; x < ebur128->graph.w; x++)
375  memcpy(p + x*3, c, 3);
376  p += outpicref->linesize[0];
377  }
378 
379  /* draw fancy rectangles around the graph and the gauge */
380 #define DRAW_RECT(r) do { \
381  drawline(outpicref, r.x, r.y - 1, r.w, 3); \
382  drawline(outpicref, r.x, r.y + r.h, r.w, 3); \
383  drawline(outpicref, r.x - 1, r.y, r.h, outpicref->linesize[0]); \
384  drawline(outpicref, r.x + r.w, r.y, r.h, outpicref->linesize[0]); \
385 } while (0)
386  DRAW_RECT(ebur128->graph);
387  DRAW_RECT(ebur128->gauge);
388 
389  return 0;
390 }
391 
393 {
394  AVFilterContext *ctx = inlink->dst;
395  EBUR128Context *ebur128 = ctx->priv;
396 
397  /* Unofficial reversed parametrization of PRE
398  * and RLB from 48kHz */
399 
400  double f0 = 1681.974450955533;
401  double G = 3.999843853973347;
402  double Q = 0.7071752369554196;
403 
404  double K = tan(M_PI * f0 / (double)inlink->sample_rate);
405  double Vh = pow(10.0, G / 20.0);
406  double Vb = pow(Vh, 0.4996667741545416);
407 
408  double a0 = 1.0 + K / Q + K * K;
409 
410  ebur128->pre_b[0] = (Vh + Vb * K / Q + K * K) / a0;
411  ebur128->pre_b[1] = 2.0 * (K * K - Vh) / a0;
412  ebur128->pre_b[2] = (Vh - Vb * K / Q + K * K) / a0;
413  ebur128->pre_a[1] = 2.0 * (K * K - 1.0) / a0;
414  ebur128->pre_a[2] = (1.0 - K / Q + K * K) / a0;
415 
416  f0 = 38.13547087602444;
417  Q = 0.5003270373238773;
418  K = tan(M_PI * f0 / (double)inlink->sample_rate);
419 
420  ebur128->rlb_b[0] = 1.0;
421  ebur128->rlb_b[1] = -2.0;
422  ebur128->rlb_b[2] = 1.0;
423  ebur128->rlb_a[1] = 2.0 * (K * K - 1.0) / (1.0 + K / Q + K * K);
424  ebur128->rlb_a[2] = (1.0 - K / Q + K * K) / (1.0 + K / Q + K * K);
425 
426  /* Force 100ms framing in case of metadata injection: the frames must have
427  * a granularity of the window overlap to be accurately exploited.
428  * As for the true peaks mode, it just simplifies the resampling buffer
429  * allocation and the lookup in it (since sample buffers differ in size, it
430  * can be more complex to integrate in the one-sample loop of
431  * filter_frame()). */
432  if (ebur128->metadata || (ebur128->peak_mode & PEAK_MODE_TRUE_PEAKS))
433  ebur128->nb_samples = FFMAX(inlink->sample_rate / 10, 1);
434  return 0;
435 }
436 
437 static int config_audio_output(AVFilterLink *outlink)
438 {
439  int i;
440  AVFilterContext *ctx = outlink->src;
441  EBUR128Context *ebur128 = ctx->priv;
442  const int nb_channels = outlink->ch_layout.nb_channels;
443 
444 #define BACK_MASK (AV_CH_BACK_LEFT |AV_CH_BACK_CENTER |AV_CH_BACK_RIGHT| \
445  AV_CH_TOP_BACK_LEFT|AV_CH_TOP_BACK_CENTER|AV_CH_TOP_BACK_RIGHT| \
446  AV_CH_SIDE_LEFT |AV_CH_SIDE_RIGHT| \
447  AV_CH_SURROUND_DIRECT_LEFT |AV_CH_SURROUND_DIRECT_RIGHT)
448 
449  ebur128->nb_channels = nb_channels;
450  ebur128->x = av_calloc(nb_channels, 3 * sizeof(*ebur128->x));
451  ebur128->y = av_calloc(nb_channels, 3 * sizeof(*ebur128->y));
452  ebur128->z = av_calloc(nb_channels, 3 * sizeof(*ebur128->z));
453  ebur128->ch_weighting = av_calloc(nb_channels, sizeof(*ebur128->ch_weighting));
454  if (!ebur128->ch_weighting || !ebur128->x || !ebur128->y || !ebur128->z)
455  return AVERROR(ENOMEM);
456 
457 #define I400_BINS(x) ((x) * 4 / 10)
458 #define I3000_BINS(x) ((x) * 3)
459 
460  ebur128->i400.sum = av_calloc(nb_channels, sizeof(*ebur128->i400.sum));
461  ebur128->i3000.sum = av_calloc(nb_channels, sizeof(*ebur128->i3000.sum));
462  ebur128->i400.cache = av_calloc(nb_channels, sizeof(*ebur128->i400.cache));
463  ebur128->i3000.cache = av_calloc(nb_channels, sizeof(*ebur128->i3000.cache));
464  if (!ebur128->i400.sum || !ebur128->i3000.sum ||
465  !ebur128->i400.cache || !ebur128->i3000.cache)
466  return AVERROR(ENOMEM);
467 
468  for (i = 0; i < nb_channels; i++) {
469  /* channel weighting */
470  const enum AVChannel chl = av_channel_layout_channel_from_index(&outlink->ch_layout, i);
471  if (chl == AV_CHAN_LOW_FREQUENCY || chl == AV_CHAN_LOW_FREQUENCY_2) {
472  ebur128->ch_weighting[i] = 0;
473  } else if (chl < 64 && (1ULL << chl) & BACK_MASK) {
474  ebur128->ch_weighting[i] = 1.41;
475  } else {
476  ebur128->ch_weighting[i] = 1.0;
477  }
478 
479  if (!ebur128->ch_weighting[i])
480  continue;
481 
482  /* bins buffer for the two integration window (400ms and 3s) */
483  ebur128->i400.cache_size = I400_BINS(outlink->sample_rate);
484  ebur128->i3000.cache_size = I3000_BINS(outlink->sample_rate);
485  ebur128->i400.cache[i] = av_calloc(ebur128->i400.cache_size, sizeof(*ebur128->i400.cache[0]));
486  ebur128->i3000.cache[i] = av_calloc(ebur128->i3000.cache_size, sizeof(*ebur128->i3000.cache[0]));
487  if (!ebur128->i400.cache[i] || !ebur128->i3000.cache[i])
488  return AVERROR(ENOMEM);
489  }
490 
491 #if CONFIG_SWRESAMPLE
492  if (ebur128->peak_mode & PEAK_MODE_TRUE_PEAKS) {
493  int ret;
494 
495  ebur128->swr_buf = av_malloc_array(nb_channels, 19200 * sizeof(double));
496  ebur128->true_peaks = av_calloc(nb_channels, sizeof(*ebur128->true_peaks));
497  ebur128->true_peaks_per_frame = av_calloc(nb_channels, sizeof(*ebur128->true_peaks_per_frame));
498  ebur128->swr_ctx = swr_alloc();
499  if (!ebur128->swr_buf || !ebur128->true_peaks ||
500  !ebur128->true_peaks_per_frame || !ebur128->swr_ctx)
501  return AVERROR(ENOMEM);
502 
503  av_opt_set_chlayout(ebur128->swr_ctx, "in_chlayout", &outlink->ch_layout, 0);
504  av_opt_set_int(ebur128->swr_ctx, "in_sample_rate", outlink->sample_rate, 0);
505  av_opt_set_sample_fmt(ebur128->swr_ctx, "in_sample_fmt", outlink->format, 0);
506 
507  av_opt_set_chlayout(ebur128->swr_ctx, "out_chlayout", &outlink->ch_layout, 0);
508  av_opt_set_int(ebur128->swr_ctx, "out_sample_rate", 192000, 0);
509  av_opt_set_sample_fmt(ebur128->swr_ctx, "out_sample_fmt", outlink->format, 0);
510 
511  ret = swr_init(ebur128->swr_ctx);
512  if (ret < 0)
513  return ret;
514  }
515 #endif
516 
517  if (ebur128->peak_mode & PEAK_MODE_SAMPLES_PEAKS) {
518  ebur128->sample_peaks = av_calloc(nb_channels, sizeof(*ebur128->sample_peaks));
519  if (!ebur128->sample_peaks)
520  return AVERROR(ENOMEM);
521  }
522 
523  return 0;
524 }
525 
526 #define ENERGY(loudness) (ff_exp10(((loudness) + 0.691) / 10.))
527 #define LOUDNESS(energy) (-0.691 + 10 * log10(energy))
528 #define DBFS(energy) (20 * log10(energy))
529 
530 static struct hist_entry *get_histogram(void)
531 {
532  int i;
533  struct hist_entry *h = av_calloc(HIST_SIZE, sizeof(*h));
534 
535  if (!h)
536  return NULL;
537  for (i = 0; i < HIST_SIZE; i++) {
538  h[i].loudness = i / (double)HIST_GRAIN + ABS_THRES;
539  h[i].energy = ENERGY(h[i].loudness);
540  }
541  return h;
542 }
543 
545 {
546  EBUR128Context *ebur128 = ctx->priv;
547  AVFilterPad pad;
548  int ret;
549 
550  if (ebur128->loglevel != AV_LOG_INFO &&
551  ebur128->loglevel != AV_LOG_QUIET &&
552  ebur128->loglevel != AV_LOG_VERBOSE) {
553  if (ebur128->do_video || ebur128->metadata)
554  ebur128->loglevel = AV_LOG_VERBOSE;
555  else
556  ebur128->loglevel = AV_LOG_INFO;
557  }
558 
559  if (!CONFIG_SWRESAMPLE && (ebur128->peak_mode & PEAK_MODE_TRUE_PEAKS)) {
561  "True-peak mode requires libswresample to be performed\n");
562  return AVERROR(EINVAL);
563  }
564 
565  // if meter is +9 scale, scale range is from -18 LU to +9 LU (or 3*9)
566  // if meter is +18 scale, scale range is from -36 LU to +18 LU (or 3*18)
567  ebur128->scale_range = 3 * ebur128->meter;
568 
569  ebur128->i400.histogram = get_histogram();
570  ebur128->i3000.histogram = get_histogram();
571  if (!ebur128->i400.histogram || !ebur128->i3000.histogram)
572  return AVERROR(ENOMEM);
573 
574  ebur128->integrated_loudness = ABS_THRES;
575  ebur128->loudness_range = 0;
576 
577  /* insert output pads */
578  if (ebur128->do_video) {
579  pad = (AVFilterPad){
580  .name = "out0",
581  .type = AVMEDIA_TYPE_VIDEO,
582  .config_props = config_video_output,
583  };
584  ret = ff_append_outpad(ctx, &pad);
585  if (ret < 0)
586  return ret;
587  }
588  pad = (AVFilterPad){
589  .name = ebur128->do_video ? "out1" : "out0",
590  .type = AVMEDIA_TYPE_AUDIO,
591  .config_props = config_audio_output,
592  };
593  ret = ff_append_outpad(ctx, &pad);
594  if (ret < 0)
595  return ret;
596 
597  /* summary */
598  av_log(ctx, AV_LOG_VERBOSE, "EBU +%d scale\n", ebur128->meter);
599 
600  return 0;
601 }
602 
603 #define HIST_POS(power) (int)(((power) - ABS_THRES) * HIST_GRAIN)
604 
605 /* loudness and power should be set such as loudness = -0.691 +
606  * 10*log10(power), we just avoid doing that calculus two times */
607 static int gate_update(struct integrator *integ, double power,
608  double loudness, int gate_thres)
609 {
610  int ipower;
611  double relative_threshold;
612  int gate_hist_pos;
613 
614  /* update powers histograms by incrementing current power count */
615  ipower = av_clip(HIST_POS(loudness), 0, HIST_SIZE - 1);
616  integ->histogram[ipower].count++;
617 
618  /* compute relative threshold and get its position in the histogram */
619  integ->sum_kept_powers += power;
620  integ->nb_kept_powers++;
621  relative_threshold = integ->sum_kept_powers / integ->nb_kept_powers;
622  if (!relative_threshold)
623  relative_threshold = 1e-12;
624  integ->rel_threshold = LOUDNESS(relative_threshold) + gate_thres;
625  gate_hist_pos = av_clip(HIST_POS(integ->rel_threshold), 0, HIST_SIZE - 1);
626 
627  return gate_hist_pos;
628 }
629 
630 static int filter_frame(AVFilterLink *inlink, AVFrame *insamples)
631 {
632  int i, ch, idx_insample, ret;
633  AVFilterContext *ctx = inlink->dst;
634  EBUR128Context *ebur128 = ctx->priv;
635  const int nb_channels = ebur128->nb_channels;
636  const int nb_samples = insamples->nb_samples;
637  const double *samples = (double *)insamples->data[0];
638  AVFrame *pic;
639 
640 #if CONFIG_SWRESAMPLE
641  if (ebur128->peak_mode & PEAK_MODE_TRUE_PEAKS && ebur128->idx_insample == 0) {
642  const double *swr_samples = ebur128->swr_buf;
643  int ret = swr_convert(ebur128->swr_ctx, (uint8_t**)&ebur128->swr_buf, 19200,
644  (const uint8_t **)insamples->data, nb_samples);
645  if (ret < 0)
646  return ret;
647  for (ch = 0; ch < nb_channels; ch++)
648  ebur128->true_peaks_per_frame[ch] = 0.0;
649  for (idx_insample = 0; idx_insample < ret; idx_insample++) {
650  for (ch = 0; ch < nb_channels; ch++) {
651  ebur128->true_peaks[ch] = FFMAX(ebur128->true_peaks[ch], fabs(*swr_samples));
652  ebur128->true_peaks_per_frame[ch] = FFMAX(ebur128->true_peaks_per_frame[ch],
653  fabs(*swr_samples));
654  swr_samples++;
655  }
656  }
657  }
658 #endif
659 
660  for (idx_insample = ebur128->idx_insample; idx_insample < nb_samples; idx_insample++) {
661  const int bin_id_400 = ebur128->i400.cache_pos;
662  const int bin_id_3000 = ebur128->i3000.cache_pos;
663 
664 #define MOVE_TO_NEXT_CACHED_ENTRY(time) do { \
665  ebur128->i##time.cache_pos++; \
666  if (ebur128->i##time.cache_pos == \
667  ebur128->i##time.cache_size) { \
668  ebur128->i##time.filled = 1; \
669  ebur128->i##time.cache_pos = 0; \
670  } \
671 } while (0)
672 
675 
676  for (ch = 0; ch < nb_channels; ch++) {
677  double bin;
678 
679  if (ebur128->peak_mode & PEAK_MODE_SAMPLES_PEAKS)
680  ebur128->sample_peaks[ch] = FFMAX(ebur128->sample_peaks[ch], fabs(samples[idx_insample * nb_channels + ch]));
681 
682  ebur128->x[ch * 3] = samples[idx_insample * nb_channels + ch]; // set X[i]
683 
684  if (!ebur128->ch_weighting[ch])
685  continue;
686 
687  /* Y[i] = X[i]*b0 + X[i-1]*b1 + X[i-2]*b2 - Y[i-1]*a1 - Y[i-2]*a2 */
688 #define FILTER(Y, X, NUM, DEN) do { \
689  double *dst = ebur128->Y + ch*3; \
690  double *src = ebur128->X + ch*3; \
691  dst[2] = dst[1]; \
692  dst[1] = dst[0]; \
693  dst[0] = src[0]*NUM[0] + src[1]*NUM[1] + src[2]*NUM[2] \
694  - dst[1]*DEN[1] - dst[2]*DEN[2]; \
695 } while (0)
696 
697  // TODO: merge both filters in one?
698  FILTER(y, x, ebur128->pre_b, ebur128->pre_a); // apply pre-filter
699  ebur128->x[ch * 3 + 2] = ebur128->x[ch * 3 + 1];
700  ebur128->x[ch * 3 + 1] = ebur128->x[ch * 3 ];
701  FILTER(z, y, ebur128->rlb_b, ebur128->rlb_a); // apply RLB-filter
702 
703  bin = ebur128->z[ch * 3] * ebur128->z[ch * 3];
704 
705  /* add the new value, and limit the sum to the cache size (400ms or 3s)
706  * by removing the oldest one */
707  ebur128->i400.sum [ch] = ebur128->i400.sum [ch] + bin - ebur128->i400.cache [ch][bin_id_400];
708  ebur128->i3000.sum[ch] = ebur128->i3000.sum[ch] + bin - ebur128->i3000.cache[ch][bin_id_3000];
709 
710  /* override old cache entry with the new value */
711  ebur128->i400.cache [ch][bin_id_400 ] = bin;
712  ebur128->i3000.cache[ch][bin_id_3000] = bin;
713  }
714 
715 #define FIND_PEAK(global, sp, ptype) do { \
716  int ch; \
717  double maxpeak; \
718  maxpeak = 0.0; \
719  if (ebur128->peak_mode & PEAK_MODE_ ## ptype ## _PEAKS) { \
720  for (ch = 0; ch < ebur128->nb_channels; ch++) \
721  maxpeak = FFMAX(maxpeak, sp[ch]); \
722  global = DBFS(maxpeak); \
723  } \
724 } while (0)
725 
726  FIND_PEAK(ebur128->sample_peak, ebur128->sample_peaks, SAMPLES);
727  FIND_PEAK(ebur128->true_peak, ebur128->true_peaks, TRUE);
728 
729  /* For integrated loudness, gating blocks are 400ms long with 75%
730  * overlap (see BS.1770-2 p5), so a re-computation is needed each 100ms
731  * (4800 samples at 48kHz). */
732  if (++ebur128->sample_count == inlink->sample_rate / 10) {
733  double loudness_400, loudness_3000;
734  double power_400 = 1e-12, power_3000 = 1e-12;
735  AVFilterLink *outlink = ctx->outputs[0];
736  const int64_t pts = insamples->pts +
737  av_rescale_q(idx_insample, (AVRational){ 1, inlink->sample_rate },
738  ctx->outputs[ebur128->do_video]->time_base);
739 
740  ebur128->sample_count = 0;
741 
742 #define COMPUTE_LOUDNESS(m, time) do { \
743  if (ebur128->i##time.filled) { \
744  /* weighting sum of the last <time> ms */ \
745  for (ch = 0; ch < nb_channels; ch++) \
746  power_##time += ebur128->ch_weighting[ch] * ebur128->i##time.sum[ch]; \
747  power_##time /= I##time##_BINS(inlink->sample_rate); \
748  } \
749  loudness_##time = LOUDNESS(power_##time); \
750 } while (0)
751 
752  COMPUTE_LOUDNESS(M, 400);
753  COMPUTE_LOUDNESS(S, 3000);
754 
755  /* Integrated loudness */
756 #define I_GATE_THRES -10 // initially defined to -8 LU in the first EBU standard
757 
758  if (loudness_400 >= ABS_THRES) {
759  double integrated_sum = 0.0;
760  uint64_t nb_integrated = 0;
761  int gate_hist_pos = gate_update(&ebur128->i400, power_400,
762  loudness_400, I_GATE_THRES);
763 
764  /* compute integrated loudness by summing the histogram values
765  * above the relative threshold */
766  for (i = gate_hist_pos; i < HIST_SIZE; i++) {
767  const unsigned nb_v = ebur128->i400.histogram[i].count;
768  nb_integrated += nb_v;
769  integrated_sum += nb_v * ebur128->i400.histogram[i].energy;
770  }
771  if (nb_integrated) {
772  ebur128->integrated_loudness = LOUDNESS(integrated_sum / nb_integrated);
773  /* dual-mono correction */
774  if (nb_channels == 1 && ebur128->dual_mono) {
775  ebur128->integrated_loudness -= ebur128->pan_law;
776  }
777  }
778  }
779 
780  /* LRA */
781 #define LRA_GATE_THRES -20
782 #define LRA_LOWER_PRC 10
783 #define LRA_HIGHER_PRC 95
784 
785  /* XXX: example code in EBU 3342 is ">=" but formula in BS.1770
786  * specs is ">" */
787  if (loudness_3000 >= ABS_THRES) {
788  uint64_t nb_powers = 0;
789  int gate_hist_pos = gate_update(&ebur128->i3000, power_3000,
790  loudness_3000, LRA_GATE_THRES);
791 
792  for (i = gate_hist_pos; i < HIST_SIZE; i++)
793  nb_powers += ebur128->i3000.histogram[i].count;
794  if (nb_powers) {
795  uint64_t n, nb_pow;
796 
797  /* get lower loudness to consider */
798  n = 0;
799  nb_pow = LRA_LOWER_PRC * nb_powers * 0.01 + 0.5;
800  for (i = gate_hist_pos; i < HIST_SIZE; i++) {
801  n += ebur128->i3000.histogram[i].count;
802  if (n >= nb_pow) {
803  ebur128->lra_low = ebur128->i3000.histogram[i].loudness;
804  break;
805  }
806  }
807 
808  /* get higher loudness to consider */
809  n = nb_powers;
810  nb_pow = LRA_HIGHER_PRC * nb_powers * 0.01 + 0.5;
811  for (i = HIST_SIZE - 1; i >= 0; i--) {
812  n -= FFMIN(n, ebur128->i3000.histogram[i].count);
813  if (n < nb_pow) {
814  ebur128->lra_high = ebur128->i3000.histogram[i].loudness;
815  break;
816  }
817  }
818 
819  // XXX: show low & high on the graph?
820  ebur128->loudness_range = ebur128->lra_high - ebur128->lra_low;
821  }
822  }
823 
824  /* dual-mono correction */
825  if (nb_channels == 1 && ebur128->dual_mono) {
826  loudness_400 -= ebur128->pan_law;
827  loudness_3000 -= ebur128->pan_law;
828  }
829 
830 #define LOG_FMT "TARGET:%d LUFS M:%6.1f S:%6.1f I:%6.1f %s LRA:%6.1f LU"
831 
832  /* push one video frame */
833  if (ebur128->do_video) {
834  AVFrame *clone;
835  int x, y;
836  uint8_t *p;
837  double gauge_value;
838  int y_loudness_lu_graph, y_loudness_lu_gauge;
839 
840  if (ebur128->gauge_type == GAUGE_TYPE_MOMENTARY) {
841  gauge_value = loudness_400 - ebur128->target;
842  } else {
843  gauge_value = loudness_3000 - ebur128->target;
844  }
845 
846  y_loudness_lu_graph = lu_to_y(ebur128, loudness_3000 - ebur128->target);
847  y_loudness_lu_gauge = lu_to_y(ebur128, gauge_value);
848 
849  ret = ff_inlink_make_frame_writable(outlink, &ebur128->outpicref);
850  if (ret < 0) {
851  av_frame_free(&insamples);
852  ebur128->insamples = NULL;
853  return ret;
854  }
855  pic = ebur128->outpicref;
856  /* draw the graph using the short-term loudness */
857  p = pic->data[0] + ebur128->graph.y*pic->linesize[0] + ebur128->graph.x*3;
858  for (y = 0; y < ebur128->graph.h; y++) {
859  const uint8_t *c = get_graph_color(ebur128, y_loudness_lu_graph, y);
860 
861  memmove(p, p + 3, (ebur128->graph.w - 1) * 3);
862  memcpy(p + (ebur128->graph.w - 1) * 3, c, 3);
863  p += pic->linesize[0];
864  }
865 
866  /* draw the gauge using either momentary or short-term loudness */
867  p = pic->data[0] + ebur128->gauge.y*pic->linesize[0] + ebur128->gauge.x*3;
868  for (y = 0; y < ebur128->gauge.h; y++) {
869  const uint8_t *c = get_graph_color(ebur128, y_loudness_lu_gauge, y);
870 
871  for (x = 0; x < ebur128->gauge.w; x++)
872  memcpy(p + x*3, c, 3);
873  p += pic->linesize[0];
874  }
875 
876  /* draw textual info */
877  if (ebur128->scale == SCALE_TYPE_ABSOLUTE) {
878  drawtext(pic, PAD, PAD - PAD/2, FONT16, font_colors,
879  LOG_FMT " ", // padding to erase trailing characters
880  ebur128->target, loudness_400, loudness_3000,
881  ebur128->integrated_loudness, "LUFS", ebur128->loudness_range);
882  } else {
883  drawtext(pic, PAD, PAD - PAD/2, FONT16, font_colors,
884  LOG_FMT " ", // padding to erase trailing characters
885  ebur128->target, loudness_400-ebur128->target, loudness_3000-ebur128->target,
886  ebur128->integrated_loudness-ebur128->target, "LU", ebur128->loudness_range);
887  }
888 
889  /* set pts and push frame */
890  pic->pts = av_rescale_q(pts, inlink->time_base, outlink->time_base);
891  pic->duration = 1;
892  clone = av_frame_clone(pic);
893  if (!clone)
894  return AVERROR(ENOMEM);
895  ebur128->idx_insample = idx_insample + 1;
896  ff_filter_set_ready(ctx, 100);
897  return ff_filter_frame(outlink, clone);
898  }
899 
900  if (ebur128->metadata) { /* happens only once per filter_frame call */
901  char metabuf[128];
902 #define META_PREFIX "lavfi.r128."
903 
904 #define SET_META(name, var) do { \
905  snprintf(metabuf, sizeof(metabuf), "%.3f", var); \
906  av_dict_set(&insamples->metadata, name, metabuf, 0); \
907 } while (0)
908 
909 #define SET_META_PEAK(name, ptype) do { \
910  if (ebur128->peak_mode & PEAK_MODE_ ## ptype ## _PEAKS) { \
911  double max_peak = 0.0; \
912  char key[64]; \
913  for (ch = 0; ch < nb_channels; ch++) { \
914  snprintf(key, sizeof(key), \
915  META_PREFIX AV_STRINGIFY(name) "_peaks_ch%d", ch); \
916  max_peak = fmax(max_peak, ebur128->name##_peaks[ch]); \
917  SET_META(key, ebur128->name##_peaks[ch]); \
918  } \
919  snprintf(key, sizeof(key), \
920  META_PREFIX AV_STRINGIFY(name) "_peak"); \
921  SET_META(key, max_peak); \
922  } \
923 } while (0)
924 
925  SET_META(META_PREFIX "M", loudness_400);
926  SET_META(META_PREFIX "S", loudness_3000);
928  SET_META(META_PREFIX "LRA", ebur128->loudness_range);
929  SET_META(META_PREFIX "LRA.low", ebur128->lra_low);
930  SET_META(META_PREFIX "LRA.high", ebur128->lra_high);
931 
933  SET_META_PEAK(true, TRUE);
934  }
935 
936  if (ebur128->loglevel != AV_LOG_QUIET) {
937  if (ebur128->scale == SCALE_TYPE_ABSOLUTE) {
938  av_log(ctx, ebur128->loglevel, "t: %-10s " LOG_FMT,
939  av_ts2timestr(pts, &outlink->time_base),
940  ebur128->target, loudness_400, loudness_3000,
941  ebur128->integrated_loudness, "LUFS", ebur128->loudness_range);
942  } else {
943  av_log(ctx, ebur128->loglevel, "t: %-10s " LOG_FMT,
944  av_ts2timestr(pts, &outlink->time_base),
945  ebur128->target, loudness_400-ebur128->target, loudness_3000-ebur128->target,
946  ebur128->integrated_loudness-ebur128->target, "LU", ebur128->loudness_range);
947  }
948 
949 #define PRINT_PEAKS(str, sp, ptype) do { \
950  if (ebur128->peak_mode & PEAK_MODE_ ## ptype ## _PEAKS) { \
951  av_log(ctx, ebur128->loglevel, " " str ":"); \
952  for (ch = 0; ch < nb_channels; ch++) \
953  av_log(ctx, ebur128->loglevel, " %5.1f", DBFS(sp[ch])); \
954  av_log(ctx, ebur128->loglevel, " dBFS"); \
955  } \
956 } while (0)
957 
958  PRINT_PEAKS("SPK", ebur128->sample_peaks, SAMPLES);
959  PRINT_PEAKS("FTPK", ebur128->true_peaks_per_frame, TRUE);
960  PRINT_PEAKS("TPK", ebur128->true_peaks, TRUE);
961  av_log(ctx, ebur128->loglevel, "\n");
962  }
963  }
964  }
965 
966  ebur128->idx_insample = 0;
967  ebur128->insamples = NULL;
968 
969  return ff_filter_frame(ctx->outputs[ebur128->do_video], insamples);
970 }
971 
973 {
974  AVFilterLink *inlink = ctx->inputs[0];
975  EBUR128Context *ebur128 = ctx->priv;
976  AVFilterLink *voutlink = ctx->outputs[0];
977  AVFilterLink *outlink = ctx->outputs[ebur128->do_video];
978  int ret;
979 
981  if (ebur128->do_video)
983 
984  if (!ebur128->insamples) {
985  AVFrame *in;
986 
987  if (ebur128->nb_samples > 0) {
988  ret = ff_inlink_consume_samples(inlink, ebur128->nb_samples, ebur128->nb_samples, &in);
989  } else {
991  }
992  if (ret < 0)
993  return ret;
994  if (ret > 0)
995  ebur128->insamples = in;
996  }
997 
998  if (ebur128->insamples)
999  ret = filter_frame(inlink, ebur128->insamples);
1000 
1002  FF_FILTER_FORWARD_WANTED(outlink, inlink);
1003  if (ebur128->do_video)
1004  FF_FILTER_FORWARD_WANTED(voutlink, inlink);
1005 
1006  return ret;
1007 }
1008 
1010 {
1011  EBUR128Context *ebur128 = ctx->priv;
1014  AVFilterLink *inlink = ctx->inputs[0];
1015  AVFilterLink *outlink = ctx->outputs[0];
1016  int ret;
1017 
1019  static const enum AVPixelFormat pix_fmts[] = { AV_PIX_FMT_RGB24, AV_PIX_FMT_NONE };
1020 
1021  /* set optional output video format */
1022  if (ebur128->do_video) {
1024  if ((ret = ff_formats_ref(formats, &outlink->incfg.formats)) < 0)
1025  return ret;
1026  outlink = ctx->outputs[1];
1027  }
1028 
1029  /* set input and output audio formats
1030  * Note: ff_set_common_* functions are not used because they affect all the
1031  * links, and thus break the video format negotiation */
1033  if ((ret = ff_formats_ref(formats, &inlink->outcfg.formats)) < 0 ||
1034  (ret = ff_formats_ref(formats, &outlink->incfg.formats)) < 0)
1035  return ret;
1036 
1038  if ((ret = ff_channel_layouts_ref(layouts, &inlink->outcfg.channel_layouts)) < 0 ||
1040  return ret;
1041 
1043  if ((ret = ff_formats_ref(formats, &inlink->outcfg.samplerates)) < 0 ||
1044  (ret = ff_formats_ref(formats, &outlink->incfg.samplerates)) < 0)
1045  return ret;
1046 
1047  return 0;
1048 }
1049 
1051 {
1052  EBUR128Context *ebur128 = ctx->priv;
1053 
1054  /* dual-mono correction */
1055  if (ebur128->nb_channels == 1 && ebur128->dual_mono) {
1056  ebur128->i400.rel_threshold -= ebur128->pan_law;
1057  ebur128->i3000.rel_threshold -= ebur128->pan_law;
1058  ebur128->lra_low -= ebur128->pan_law;
1059  ebur128->lra_high -= ebur128->pan_law;
1060  }
1061 
1062  if (ebur128->nb_channels > 0) {
1063  av_log(ctx, AV_LOG_INFO, "Summary:\n\n"
1064  " Integrated loudness:\n"
1065  " I: %5.1f LUFS\n"
1066  " Threshold: %5.1f LUFS\n\n"
1067  " Loudness range:\n"
1068  " LRA: %5.1f LU\n"
1069  " Threshold: %5.1f LUFS\n"
1070  " LRA low: %5.1f LUFS\n"
1071  " LRA high: %5.1f LUFS",
1072  ebur128->integrated_loudness, ebur128->i400.rel_threshold,
1073  ebur128->loudness_range, ebur128->i3000.rel_threshold,
1074  ebur128->lra_low, ebur128->lra_high);
1075 
1076 #define PRINT_PEAK_SUMMARY(str, value, ptype) do { \
1077  if (ebur128->peak_mode & PEAK_MODE_ ## ptype ## _PEAKS) { \
1078  av_log(ctx, AV_LOG_INFO, "\n\n " str " peak:\n" \
1079  " Peak: %5.1f dBFS", value); \
1080  } \
1081 } while (0)
1082 
1083  PRINT_PEAK_SUMMARY("Sample", ebur128->sample_peak, SAMPLES);
1084  PRINT_PEAK_SUMMARY("True", ebur128->true_peak, TRUE);
1085  av_log(ctx, AV_LOG_INFO, "\n");
1086  }
1087 
1088  av_freep(&ebur128->y_line_ref);
1089  av_freep(&ebur128->x);
1090  av_freep(&ebur128->y);
1091  av_freep(&ebur128->z);
1092  av_freep(&ebur128->ch_weighting);
1093  av_freep(&ebur128->true_peaks);
1094  av_freep(&ebur128->sample_peaks);
1095  av_freep(&ebur128->true_peaks_per_frame);
1096  av_freep(&ebur128->i400.sum);
1097  av_freep(&ebur128->i3000.sum);
1098  av_freep(&ebur128->i400.histogram);
1099  av_freep(&ebur128->i3000.histogram);
1100  for (int i = 0; i < ebur128->nb_channels; i++) {
1101  if (ebur128->i400.cache)
1102  av_freep(&ebur128->i400.cache[i]);
1103  if (ebur128->i3000.cache)
1104  av_freep(&ebur128->i3000.cache[i]);
1105  }
1106  av_freep(&ebur128->i400.cache);
1107  av_freep(&ebur128->i3000.cache);
1108  av_frame_free(&ebur128->outpicref);
1109 #if CONFIG_SWRESAMPLE
1110  av_freep(&ebur128->swr_buf);
1111  swr_free(&ebur128->swr_ctx);
1112 #endif
1113 }
1114 
1115 static const AVFilterPad ebur128_inputs[] = {
1116  {
1117  .name = "default",
1118  .type = AVMEDIA_TYPE_AUDIO,
1119  .config_props = config_audio_input,
1120  },
1121 };
1122 
1124  .name = "ebur128",
1125  .description = NULL_IF_CONFIG_SMALL("EBU R128 scanner."),
1126  .priv_size = sizeof(EBUR128Context),
1127  .init = init,
1128  .uninit = uninit,
1129  .activate = activate,
1131  .outputs = NULL,
1133  .priv_class = &ebur128_class,
1135 };
M
#define M(a, b)
Definition: vp3dsp.c:48
formats
formats
Definition: signature.h:48
rect::w
int w
Definition: f_ebur128.c:78
ff_get_video_buffer
AVFrame * ff_get_video_buffer(AVFilterLink *link, int w, int h)
Request a picture buffer with a specific set of permissions.
Definition: video.c:112
AVFilterChannelLayouts
A list of supported channel layouts.
Definition: formats.h:85
AVPixelFormat
AVPixelFormat
Pixel format.
Definition: pixfmt.h:71
AVFilterFormatsConfig::samplerates
AVFilterFormats * samplerates
Lists of supported sample rates, only for audio.
Definition: avfilter.h:522
EBUR128Context::dual_mono
int dual_mono
whether or not to treat single channel input files as dual-mono
Definition: f_ebur128.c:139
EBUR128Context::z
double * z
3 RLB-filter samples cache for each channel
Definition: f_ebur128.c:122
av_clip
#define av_clip
Definition: common.h:98
V
#define V
Definition: f_ebur128.c:164
EBUR128Context::ch_weighting
double * ch_weighting
channel weighting mapping
Definition: f_ebur128.c:112
EBUR128Context::y_opt_min
int y_opt_min
the y value (pixel position) for -1 LU
Definition: f_ebur128.c:107
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
integrator::filled
int filled
1 if the cache is completely filled, 0 otherwise
Definition: f_ebur128.c:71
integrator
Definition: f_ebur128.c:66
EBUR128Context::gauge_type
int gauge_type
whether gauge shows momentary or short
Definition: f_ebur128.c:142
ff_make_format_list
AVFilterFormats * ff_make_format_list(const int *fmts)
Create a list of supported formats.
Definition: formats.c:435
EBUR128Context::y_opt_max
int y_opt_max
the y value (pixel position) for 1 LU
Definition: f_ebur128.c:106
SET_META_PEAK
#define SET_META_PEAK(name, ptype)
AVFilterFormatsConfig::channel_layouts
AVFilterChannelLayouts * channel_layouts
Lists of supported channel layouts, only for audio.
Definition: avfilter.h:527
PRINT_PEAKS
#define PRINT_PEAKS(str, sp, ptype)
get_graph_color
static const uint8_t * get_graph_color(const EBUR128Context *ebur128, int v, int y)
Definition: f_ebur128.c:224
A
#define A
Definition: f_ebur128.c:163
color
Definition: vf_paletteuse.c:511
AV_LOG_QUIET
#define AV_LOG_QUIET
Print no output.
Definition: log.h:162
ff_filter_frame
int ff_filter_frame(AVFilterLink *link, AVFrame *frame)
Send a frame of data to the next filter.
Definition: avfilter.c:1007
sample_fmts
static enum AVSampleFormat sample_fmts[]
Definition: adpcmenc.c:947
ff_channel_layouts_ref
int ff_channel_layouts_ref(AVFilterChannelLayouts *f, AVFilterChannelLayouts **ref)
Add *ref as a new reference to f.
Definition: formats.c:673
layouts
enum MovChannelLayoutTag * layouts
Definition: mov_chan.c:326
EBUR128Context::do_video
int do_video
1 if video output enabled, 0 otherwise
Definition: f_ebur128.c:97
rect
Definition: f_ebur128.c:78
HIST_SIZE
#define HIST_SIZE
Definition: f_ebur128.c:51
EBUR128Context::sample_count
int sample_count
sample count used for refresh frequency, reset at refresh
Definition: f_ebur128.c:113
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
rect::y
int y
Definition: f_ebur128.c:78
av_frame_free
void av_frame_free(AVFrame **frame)
Free the frame and any dynamically allocated objects in it, e.g.
Definition: frame.c:100
AVFrame
This structure describes decoded (raw) audio or video data.
Definition: frame.h:340
AVFrame::pts
int64_t pts
Presentation timestamp in time_base units (time when frame should be shown to user).
Definition: frame.h:452
step
trying all byte sequences megabyte in length and selecting the best looking sequence will yield cases to try But a word about which is also called distortion Distortion can be quantified by almost any quality measurement one chooses the sum of squared differences is used but more complex methods that consider psychovisual effects can be used as well It makes no difference in this discussion First step
Definition: rate_distortion.txt:58
w
uint8_t w
Definition: llviddspenc.c:38
av_channel_layout_channel_from_index
enum AVChannel av_channel_layout_channel_from_index(const AVChannelLayout *channel_layout, unsigned int idx)
Get the channel with the given index in a channel layout.
Definition: channel_layout.c:867
AVOption
AVOption.
Definition: opt.h:251
AVFILTER_DEFINE_CLASS
AVFILTER_DEFINE_CLASS(ebur128)
I_GATE_THRES
#define I_GATE_THRES
FILTER_QUERY_FUNC
#define FILTER_QUERY_FUNC(func)
Definition: internal.h:159
ebur128_options
static const AVOption ebur128_options[]
Definition: f_ebur128.c:168
F
#define F
Definition: f_ebur128.c:165
AV_LOG_VERBOSE
#define AV_LOG_VERBOSE
Detailed information.
Definition: log.h:196
float.h
FIND_PEAK
#define FIND_PEAK(global, sp, ptype)
GAUGE_TYPE_SHORTTERM
@ GAUGE_TYPE_SHORTTERM
Definition: f_ebur128.c:154
init
static av_cold int init(AVFilterContext *ctx)
Definition: f_ebur128.c:544
FFMAX
#define FFMAX(a, b)
Definition: macros.h:47
AVFilter::name
const char * name
Filter name.
Definition: avfilter.h:170
config_audio_output
static int config_audio_output(AVFilterLink *outlink)
Definition: f_ebur128.c:437
integrator::sum_kept_powers
double sum_kept_powers
sum of the powers (weighted sums) above absolute threshold
Definition: f_ebur128.c:73
AVChannelLayout::nb_channels
int nb_channels
Number of channels in this layout.
Definition: channel_layout.h:323
video.h
FF_FILTER_FORWARD_STATUS_BACK
#define FF_FILTER_FORWARD_STATUS_BACK(outlink, inlink)
Forward the status on an output link to an input link.
Definition: filters.h:199
LRA_HIGHER_PRC
#define LRA_HIGHER_PRC
AVFrame::data
uint8_t * data[AV_NUM_DATA_POINTERS]
pointer to the picture/channel planes.
Definition: frame.h:361
AVFilterFormats
A list of supported formats for one end of a filter link.
Definition: formats.h:64
formats.h
S
#define S(s, c, i)
Definition: flacdsp_template.c:46
uninit
static av_cold void uninit(AVFilterContext *ctx)
Definition: f_ebur128.c:1050
FONT8
#define FONT8
Definition: f_ebur128.c:242
EBUR128Context::pan_law
double pan_law
pan law value used to calculate dual-mono measurements
Definition: f_ebur128.c:140
ff_inlink_consume_frame
int ff_inlink_consume_frame(AVFilterLink *link, AVFrame **rframe)
Take a frame from the link's FIFO and update the link's stats.
Definition: avfilter.c:1438
EBUR128Context::rlb_b
double rlb_b[3]
rlb-filter numerator coefficients
Definition: f_ebur128.c:125
drawline
static void drawline(AVFrame *pic, int x, int y, int len, int step)
Definition: f_ebur128.c:283
Q
#define Q(x)
Definition: vvc_filter_template.c:433
get_histogram
static struct hist_entry * get_histogram(void)
Definition: f_ebur128.c:530
R
#define R
Definition: f_ebur128.c:167
EBUR128Context::scale
int scale
display scale type of statistics
Definition: f_ebur128.c:143
query_formats
static int query_formats(AVFilterContext *ctx)
Definition: f_ebur128.c:1009
LRA_GATE_THRES
#define LRA_GATE_THRES
EBUR128Context::rlb_a
double rlb_a[3]
rlb-filter denominator coefficients
Definition: f_ebur128.c:126
pts
static int64_t pts
Definition: transcode_aac.c:643
integrator::cache_pos
int cache_pos
focus on the last added bin in the cache array
Definition: f_ebur128.c:68
EBUR128Context::nb_samples
int nb_samples
number of samples to consume per single input frame
Definition: f_ebur128.c:114
AVFilterPad
A filter pad used for either input or output.
Definition: internal.h:33
font_colors
static const uint8_t font_colors[]
Definition: f_ebur128.c:245
avassert.h
EBUR128Context::metadata
int metadata
whether or not to inject loudness results in frames
Definition: f_ebur128.c:138
AV_LOG_ERROR
#define AV_LOG_ERROR
Something went wrong and cannot losslessly be recovered.
Definition: log.h:180
MOVE_TO_NEXT_CACHED_ENTRY
#define MOVE_TO_NEXT_CACHED_ENTRY(time)
av_cold
#define av_cold
Definition: attributes.h:90
FILTER
#define FILTER(Y, X, NUM, DEN)
EBUR128Context::graph
struct rect graph
rectangle for the main graph in the center
Definition: f_ebur128.c:100
filter_frame
static int filter_frame(AVFilterLink *inlink, AVFrame *insamples)
Definition: f_ebur128.c:630
OFFSET
#define OFFSET(x)
Definition: f_ebur128.c:162
swr_init
av_cold int swr_init(struct SwrContext *s)
Initialize context after user parameters have been set.
Definition: swresample.c:193
config_video_output
static int config_video_output(AVFilterLink *outlink)
Definition: f_ebur128.c:294
mask
static const uint16_t mask[17]
Definition: lzw.c:38
EBUR128Context::integrated_loudness
double integrated_loudness
integrated loudness in LUFS (I)
Definition: f_ebur128.c:132
EBUR128Context::w
int w
Definition: f_ebur128.c:98
FONT16
#define FONT16
Definition: f_ebur128.c:243
AV_OPT_TYPE_DOUBLE
@ AV_OPT_TYPE_DOUBLE
Definition: opt.h:227
AVMEDIA_TYPE_AUDIO
@ AVMEDIA_TYPE_AUDIO
Definition: avutil.h:202
ff_formats_ref
int ff_formats_ref(AVFilterFormats *f, AVFilterFormats **ref)
Add *ref as a new reference to formats.
Definition: formats.c:678
EBUR128Context::target
int target
target level in LUFS used to set relative zero LU in visualization
Definition: f_ebur128.c:141
swr_alloc
av_cold struct SwrContext * swr_alloc(void)
Allocate SwrContext.
Definition: options.c:169
av_assert0
#define av_assert0(cond)
assert() equivalent, that is always enabled.
Definition: avassert.h:40
filters.h
pix_fmts
static enum AVPixelFormat pix_fmts[]
Definition: libkvazaar.c:304
ctx
AVFormatContext * ctx
Definition: movenc.c:48
av_frame_clone
AVFrame * av_frame_clone(const AVFrame *src)
Create a new frame that references the same data as src.
Definition: frame.c:609
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
drawtext
static void drawtext(AVFrame *pic, int x, int y, int ftid, const uint8_t *color, const char *fmt,...)
Definition: f_ebur128.c:250
X
#define X
Definition: f_ebur128.c:166
SwrContext
The libswresample context.
Definition: swresample_internal.h:95
hist_entry::loudness
double loudness
L = -0.691 + 10 * log10(E)
Definition: f_ebur128.c:63
FILTER_INPUTS
#define FILTER_INPUTS(array)
Definition: internal.h:182
ff_inlink_make_frame_writable
int ff_inlink_make_frame_writable(AVFilterLink *link, AVFrame **rframe)
Make sure a frame is writable.
Definition: avfilter.c:1485
EBUR128Context::true_peaks_per_frame
double * true_peaks_per_frame
true peaks in a frame per channel
Definition: f_ebur128.c:89
FFABS
#define FFABS(a)
Absolute value, Note, INT_MIN / INT64_MIN result in undefined behavior as they are not representable ...
Definition: common.h:72
if
if(ret)
Definition: filter_design.txt:179
EBUR128Context::sample_peaks
double * sample_peaks
sample peaks per channel
Definition: f_ebur128.c:88
HIST_GRAIN
#define HIST_GRAIN
defines histogram precision
Definition: f_ebur128.c:50
I400_BINS
#define I400_BINS(x)
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
ff_inlink_consume_samples
int ff_inlink_consume_samples(AVFilterLink *link, unsigned min, unsigned max, AVFrame **rframe)
Take samples from the link's FIFO and update the link's stats.
Definition: avfilter.c:1458
NULL
#define NULL
Definition: coverity.c:32
EBUR128Context::peak_mode
int peak_mode
enabled peak modes
Definition: f_ebur128.c:84
HIST_POS
#define HIST_POS(power)
Definition: f_ebur128.c:603
AVRational
Rational number (pair of numerator and denominator).
Definition: rational.h:58
AV_OPT_TYPE_IMAGE_SIZE
@ AV_OPT_TYPE_IMAGE_SIZE
offset must point to two consecutive integers
Definition: opt.h:235
EBUR128Context::pre_b
double pre_b[3]
pre-filter numerator coefficients
Definition: f_ebur128.c:123
LOG_FMT
#define LOG_FMT
EBUR128Context::gauge
struct rect gauge
rectangle for the gauge on the right
Definition: f_ebur128.c:101
double
double
Definition: af_crystalizer.c:131
SCALE_TYPE_RELATIVE
@ SCALE_TYPE_RELATIVE
Definition: f_ebur128.c:159
av_clipf
av_clipf
Definition: af_crystalizer.c:121
swresample.h
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
av_opt_set_int
int av_opt_set_int(void *obj, const char *name, int64_t val, int search_flags)
Definition: opt.c:624
EBUR128Context
Definition: f_ebur128.c:80
AVFILTER_FLAG_DYNAMIC_OUTPUTS
#define AVFILTER_FLAG_DYNAMIC_OUTPUTS
The number of the filter outputs is not determined just by AVFilter.outputs.
Definition: avfilter.h:112
hist_entry::count
unsigned count
how many times the corresponding value occurred
Definition: f_ebur128.c:61
EBUR128Context::pre_a
double pre_a[3]
pre-filter denominator coefficients
Definition: f_ebur128.c:124
EBUR128Context::y_zero_lu
int y_zero_lu
the y value (pixel position) for 0 LU
Definition: f_ebur128.c:105
EBUR128Context::i3000
struct integrator i3000
3s integrator, used for Short term loudness (S), and Loudness Range (LRA)
Definition: f_ebur128.c:129
ENERGY
#define ENERGY(loudness)
Definition: f_ebur128.c:526
activate
static int activate(AVFilterContext *ctx)
Definition: f_ebur128.c:972
AV_PIX_FMT_RGB24
@ AV_PIX_FMT_RGB24
packed RGB 8:8:8, 24bpp, RGBRGB...
Definition: pixfmt.h:75
av_ts2timestr
#define av_ts2timestr(ts, tb)
Convenience macro, the return value should be used only directly in function arguments but never stan...
Definition: timestamp.h:76
scale
static void scale(int *out, const int *in, const int w, const int h, const int shift)
Definition: vvc_intra.c:290
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:106
PEAK_MODE_TRUE_PEAKS
@ PEAK_MODE_TRUE_PEAKS
Definition: f_ebur128.c:149
av_opt_set_chlayout
int av_opt_set_chlayout(void *obj, const char *name, const AVChannelLayout *channel_layout, int search_flags)
Definition: opt.c:786
for
for(k=2;k<=8;++k)
Definition: h264pred_template.c:425
AV_SAMPLE_FMT_NONE
@ AV_SAMPLE_FMT_NONE
Definition: samplefmt.h:56
sample
#define sample
Definition: flacdsp_template.c:44
AV_CHAN_LOW_FREQUENCY
@ AV_CHAN_LOW_FREQUENCY
Definition: channel_layout.h:53
av_make_q
static AVRational av_make_q(int num, int den)
Create an AVRational.
Definition: rational.h:71
rect::h
int h
Definition: f_ebur128.c:78
swr_free
av_cold void swr_free(SwrContext **ss)
Free the given SwrContext and set the pointer to NULL.
Definition: swresample.c:174
swr_convert
int attribute_align_arg swr_convert(struct SwrContext *s, uint8_t **out_arg, int out_count, const uint8_t **in_arg, int in_count)
Convert audio.
Definition: swresample.c:837
EBUR128Context::true_peak
double true_peak
global true peak
Definition: f_ebur128.c:85
PEAK_MODE_NONE
@ PEAK_MODE_NONE
Definition: f_ebur128.c:147
EBUR128Context::sample_peak
double sample_peak
global sample peak
Definition: f_ebur128.c:87
EBUR128Context::outpicref
AVFrame * outpicref
output picture reference, updated regularly
Definition: f_ebur128.c:102
line
Definition: graph2dot.c:48
FF_FILTER_FORWARD_WANTED
FF_FILTER_FORWARD_WANTED(outlink, inlink)
xga_font_data.h
ff_all_channel_layouts
AVFilterChannelLayouts * ff_all_channel_layouts(void)
Construct an empty AVFilterChannelLayouts/AVFilterFormats struct – representing any channel layout (w...
Definition: formats.c:612
rect::x
int x
Definition: f_ebur128.c:78
EBUR128Context::h
int h
size of the video output
Definition: f_ebur128.c:98
a0
#define a0
Definition: regdef.h:46
M_PI
#define M_PI
Definition: mathematics.h:67
I3000_BINS
#define I3000_BINS(x)
AV_LOG_INFO
#define AV_LOG_INFO
Standard information.
Definition: log.h:191
internal.h
AVChannel
AVChannel
Definition: channel_layout.h:47
AVFrame::nb_samples
int nb_samples
number of audio samples (per channel) described by this frame
Definition: frame.h:420
avpriv_vga16_font
const uint8_t avpriv_vga16_font[4096]
Definition: xga_font_data.c:160
i
#define i(width, name, range_min, range_max)
Definition: cbs_h2645.c:245
EBUR128Context::y
double * y
3 pre-filter samples cache for each channel
Definition: f_ebur128.c:121
EBUR128Context::text
struct rect text
rectangle for the LU legend on the left
Definition: f_ebur128.c:99
EBUR128Context::y_line_ref
int * y_line_ref
y reference values for drawing the LU lines in the graph and the gauge
Definition: f_ebur128.c:108
av_malloc_array
#define av_malloc_array(a, b)
Definition: tableprint_vlc.h:31
vsnprintf
#define vsnprintf
Definition: snprintf.h:36
PEAK_MODE_SAMPLES_PEAKS
@ PEAK_MODE_SAMPLES_PEAKS
Definition: f_ebur128.c:148
AVSampleFormat
AVSampleFormat
Audio sample formats.
Definition: samplefmt.h:55
FFMIN
#define FFMIN(a, b)
Definition: macros.h:49
integrator::rel_threshold
double rel_threshold
relative threshold
Definition: f_ebur128.c:72
av_inv_q
static av_always_inline AVRational av_inv_q(AVRational q)
Invert a rational.
Definition: rational.h:159
ABS_THRES
#define ABS_THRES
silence gate: we discard anything below this absolute (LUFS) threshold
Definition: f_ebur128.c:48
len
int len
Definition: vorbis_enc_data.h:426
AVFilterPad::name
const char * name
Pad name.
Definition: internal.h:39
integrator::nb_kept_powers
int nb_kept_powers
number of sum above absolute threshold
Definition: f_ebur128.c:74
EBUR128Context::true_peaks
double * true_peaks
true peaks per channel
Definition: f_ebur128.c:86
av_calloc
void * av_calloc(size_t nmemb, size_t size)
Definition: mem.c:262
EBUR128Context::loudness_range
double loudness_range
loudness range in LU (LRA)
Definition: f_ebur128.c:133
SCALE_TYPE_ABSOLUTE
@ SCALE_TYPE_ABSOLUTE
Definition: f_ebur128.c:158
AVFilter
Filter definition.
Definition: avfilter.h:166
hist_entry::energy
double energy
E = 10^((L + 0.691) / 10)
Definition: f_ebur128.c:62
graph_colors
static const uint8_t graph_colors[]
Definition: f_ebur128.c:205
ret
ret
Definition: filter_design.txt:187
EBUR128Context::lra_low
double lra_low
Definition: f_ebur128.c:134
LRA_LOWER_PRC
#define LRA_LOWER_PRC
dict.h
integrator::sum
double * sum
sum of the last N ms filtered samples (cache content)
Definition: f_ebur128.c:70
EBUR128Context::lra_high
double lra_high
low and high LRA values
Definition: f_ebur128.c:134
AVFrame::sample_aspect_ratio
AVRational sample_aspect_ratio
Sample aspect ratio for the video frame, 0/1 if unknown/unspecified.
Definition: frame.h:447
ff_af_ebur128
const AVFilter ff_af_ebur128
Definition: f_ebur128.c:1123
EBUR128Context::scale_range
int scale_range
the range of LU values according to the meter
Definition: f_ebur128.c:104
ff_all_samplerates
AVFilterFormats * ff_all_samplerates(void)
Definition: formats.c:606
META_PREFIX
#define META_PREFIX
power
static float power(float r, float g, float b, float max)
Definition: preserve_color.h:45
SET_META
#define SET_META(name, var)
channel_layout.h
AV_CHAN_LOW_FREQUENCY_2
@ AV_CHAN_LOW_FREQUENCY_2
Definition: channel_layout.h:76
SAMPLES
#define SAMPLES
LOUDNESS
#define LOUDNESS(energy)
Definition: f_ebur128.c:527
EBUR128Context::meter
int meter
select a EBU mode between +9 and +18
Definition: f_ebur128.c:103
PAD
#define PAD
AV_PIX_FMT_NONE
@ AV_PIX_FMT_NONE
Definition: pixfmt.h:72
AV_OPT_TYPE_INT
@ AV_OPT_TYPE_INT
Definition: opt.h:225
avfilter.h
EBUR128Context::insamples
AVFrame * insamples
input samples reference, updated regularly
Definition: f_ebur128.c:116
samples
Filter the word “frame” indicates either a video frame or a group of audio samples
Definition: filter_design.txt:8
integrator::cache
double ** cache
window of filtered samples (N ms)
Definition: f_ebur128.c:67
ffmath.h
G
#define G
Definition: huffyuv.h:43
AVFilterContext
An instance of a filter.
Definition: avfilter.h:409
GAUGE_TYPE_MOMENTARY
@ GAUGE_TYPE_MOMENTARY
Definition: f_ebur128.c:153
AVMEDIA_TYPE_VIDEO
@ AVMEDIA_TYPE_VIDEO
Definition: avutil.h:201
audio.h
AVFilterFormatsConfig::formats
AVFilterFormats * formats
List of supported formats (pixel or sample).
Definition: avfilter.h:517
ebur128_inputs
static const AVFilterPad ebur128_inputs[]
Definition: f_ebur128.c:1115
ff_append_outpad
int ff_append_outpad(AVFilterContext *f, AVFilterPad *p)
Definition: avfilter.c:137
avpriv_cga_font
const uint8_t avpriv_cga_font[2048]
Definition: xga_font_data.c:29
DRAW_RECT
#define DRAW_RECT(r)
AV_OPT_TYPE_BOOL
@ AV_OPT_TYPE_BOOL
Definition: opt.h:244
EBUR128Context::nb_channels
int nb_channels
number of channels in the input
Definition: f_ebur128.c:111
av_freep
#define av_freep(p)
Definition: tableprint_vlc.h:34
EBUR128Context::idx_insample
int idx_insample
current sample position of processed samples in single input frame
Definition: f_ebur128.c:115
FF_FILTER_FORWARD_STATUS_ALL
#define FF_FILTER_FORWARD_STATUS_ALL(inlink, filter)
Acknowledge the status on an input link and forward it to an output link.
Definition: filters.h:239
EBUR128Context::i400
struct integrator i400
400ms integrator, used for Momentary loudness (M), and Integrated loudness (I)
Definition: f_ebur128.c:128
K
#define K
Definition: palette.c:25
AV_OPT_TYPE_FLAGS
@ AV_OPT_TYPE_FLAGS
Definition: opt.h:224
timestamp.h
AVFrame::linesize
int linesize[AV_NUM_DATA_POINTERS]
For video, a positive or negative value, which is typically indicating the size in bytes of each pict...
Definition: frame.h:385
config_audio_input
static int config_audio_input(AVFilterLink *inlink)
Definition: f_ebur128.c:392
integrator::histogram
struct hist_entry * histogram
histogram of the powers, used to compute LRA and I
Definition: f_ebur128.c:75
integrator::cache_size
int cache_size
Definition: f_ebur128.c:69
av_log
#define av_log(a,...)
Definition: tableprint_vlc.h:27
EBUR128Context::x
double * x
3 input samples cache for each channel
Definition: f_ebur128.c:120
PRINT_PEAK_SUMMARY
#define PRINT_PEAK_SUMMARY(str, value, ptype)
h
h
Definition: vp9dsp_template.c:2038
BACK_MASK
#define BACK_MASK
AV_SAMPLE_FMT_DBL
@ AV_SAMPLE_FMT_DBL
double
Definition: samplefmt.h:61
avstring.h
lu_to_y
static int lu_to_y(const EBUR128Context *ebur128, double v)
Definition: f_ebur128.c:234
av_opt_set_sample_fmt
int av_opt_set_sample_fmt(void *obj, const char *name, enum AVSampleFormat fmt, int search_flags)
Definition: opt.c:742
AV_OPT_TYPE_CONST
@ AV_OPT_TYPE_CONST
Definition: opt.h:234
EBUR128Context::loglevel
int loglevel
log level for frame logging
Definition: f_ebur128.c:137
gate_update
static int gate_update(struct integrator *integ, double power, double loudness, int gate_thres)
Definition: f_ebur128.c:607
COMPUTE_LOUDNESS
#define COMPUTE_LOUDNESS(m, time)
ff_filter_set_ready
void ff_filter_set_ready(AVFilterContext *filter, unsigned priority)
Mark a filter ready and schedule it for activation.
Definition: avfilter.c:223
hist_entry
A histogram is an array of HIST_SIZE hist_entry storing all the energies recorded (with an accuracy o...
Definition: f_ebur128.c:60