avfilter/f_ebur128: fix top-back channel weighting

ITU-R BS.1770 assigns a weight of 1.0 to height channels, but the
filter included the top-back channels in the 1.41 surround mask.

remove the top-back channels from that mask and add a FATE test for
the resulting loudness measurement.

fixes #23968.

Signed-off-by: Ayoub Nabil <237098474+ayoubnabil@users.noreply.github.com>
This commit is contained in:
Ayoub Nabil
2026-08-05 19:35:50 +02:00
committed by James Almer
parent 85c857a7c3
commit fc02470c62
3 changed files with 14 additions and 5 deletions

View File

@@ -433,10 +433,11 @@ static int config_audio_output(AVFilterLink *outlink)
EBUR128Context *ebur128 = ctx->priv;
const int nb_channels = outlink->ch_layout.nb_channels;
#define BACK_MASK (AV_CH_BACK_LEFT |AV_CH_BACK_CENTER |AV_CH_BACK_RIGHT| \
AV_CH_TOP_BACK_LEFT|AV_CH_TOP_BACK_CENTER|AV_CH_TOP_BACK_RIGHT| \
AV_CH_SIDE_LEFT |AV_CH_SIDE_RIGHT| \
AV_CH_SURROUND_DIRECT_LEFT |AV_CH_SURROUND_DIRECT_RIGHT)
/* Height channels always use a weight of 1.0 in ITU-R BS.1770. */
#define WEIGHT_1_41_MASK (AV_CH_BACK_LEFT |AV_CH_BACK_CENTER | \
AV_CH_BACK_RIGHT |AV_CH_SIDE_LEFT | \
AV_CH_SIDE_RIGHT |AV_CH_SURROUND_DIRECT_LEFT | \
AV_CH_SURROUND_DIRECT_RIGHT)
ebur128->nb_channels = nb_channels;
ebur128->dsp.y = av_calloc(nb_channels, 3 * sizeof(*ebur128->dsp.y));
@@ -470,7 +471,7 @@ static int config_audio_output(AVFilterLink *outlink)
const enum AVChannel chl = av_channel_layout_channel_from_index(&outlink->ch_layout, i);
if (chl == AV_CHAN_LOW_FREQUENCY || chl == AV_CHAN_LOW_FREQUENCY_2) {
ebur128->ch_weighting[i] = 0;
} else if (chl < 64 && (1ULL << chl) & BACK_MASK) {
} else if (chl < 64 && (1ULL << chl) & WEIGHT_1_41_MASK) {
ebur128->ch_weighting[i] = 1.41;
} else {
ebur128->ch_weighting[i] = 1.0;

View File

@@ -836,6 +836,10 @@ FATE_METADATA_FILTER-$(call ALLYES, $(EBUR128_METADATA_DEPS)) += fate-filter-met
fate-filter-metadata-ebur128: SRC = $(TARGET_SAMPLES)/filter/seq-3341-7_seq-3342-5-24bit.flac
fate-filter-metadata-ebur128: CMD = run $(FILTER_METADATA_COMMAND) "amovie='$(SRC)',ebur128=metadata=1"
EBUR128_HEIGHT_DEPS = FFPROBE LAVFI_INDEV AEVALSRC_FILTER EBUR128_FILTER
FATE_FILTER_FFPROBE-$(call ALLYES, $(EBUR128_HEIGHT_DEPS)) += fate-filter-metadata-ebur128-height
fate-filter-metadata-ebur128-height: CMD = run $(FILTER_METADATA_COMMAND) "aevalsrc=0.12589*sin(2*PI*997*t):channel_layout=TBL:sample_rate=48000:duration=0.4,ebur128=metadata=1"
READVITC_METADATA_DEPS = LAVFI_INDEV MOVIE_FILTER \
AVI_DEMUXER FFVHUFF_DECODER READVITC_FILTER
FATE_METADATA_FILTER-$(call ALLYES, $(READVITC_METADATA_DEPS)) += fate-filter-metadata-readvitc-def

View File

@@ -0,0 +1,4 @@
pts=0|tag:lavfi.r128.M=-120.691|tag:lavfi.r128.S=-120.691|tag:lavfi.r128.I=-70.000|tag:lavfi.r128.LRA=0.000|tag:lavfi.r128.LRA.low=0.000|tag:lavfi.r128.LRA.high=0.000
pts=4800|tag:lavfi.r128.M=-120.691|tag:lavfi.r128.S=-120.691|tag:lavfi.r128.I=-70.000|tag:lavfi.r128.LRA=0.000|tag:lavfi.r128.LRA.low=0.000|tag:lavfi.r128.LRA.high=0.000
pts=9600|tag:lavfi.r128.M=-120.691|tag:lavfi.r128.S=-120.691|tag:lavfi.r128.I=-70.000|tag:lavfi.r128.LRA=0.000|tag:lavfi.r128.LRA.low=0.000|tag:lavfi.r128.LRA.high=0.000
pts=14400|tag:lavfi.r128.M=-21.010|tag:lavfi.r128.S=-120.691|tag:lavfi.r128.I=-21.010|tag:lavfi.r128.LRA=0.000|tag:lavfi.r128.LRA.low=0.000|tag:lavfi.r128.LRA.high=0.000