tor-browser

The Tor Browser
git clone https://git.dasho.dev/tor-browser.git
Log | Files | Refs | README | LICENSE

clipping_predictor_unittest.cc (23055B)


      1 /*
      2 *  Copyright (c) 2021 The WebRTC project authors. All Rights Reserved.
      3 *
      4 *  Use of this source code is governed by a BSD-style license
      5 *  that can be found in the LICENSE file in the root of the source
      6 *  tree. An additional intellectual property rights grant can be found
      7 *  in the file PATENTS.  All contributing project authors may
      8 *  be found in the AUTHORS file in the root of the source tree.
      9 */
     10 
     11 #include "modules/audio_processing/agc2/clipping_predictor.h"
     12 
     13 #include <cstdint>
     14 #include <limits>
     15 #include <optional>
     16 #include <tuple>
     17 #include <vector>
     18 
     19 #include "api/audio/audio_processing.h"
     20 #include "modules/audio_processing/include/audio_frame_view.h"
     21 #include "rtc_base/checks.h"
     22 #include "test/gmock.h"
     23 #include "test/gtest.h"
     24 
     25 namespace webrtc {
     26 namespace {
     27 
     28 using ::testing::Eq;
     29 using ::testing::Optional;
     30 using ClippingPredictorConfig = AudioProcessing::Config::GainController1::
     31    AnalogGainController::ClippingPredictor;
     32 using ClippingPredictorMode = AudioProcessing::Config::GainController1::
     33    AnalogGainController::ClippingPredictor::Mode;
     34 
     35 constexpr int kSampleRateHz = 32000;
     36 constexpr int kNumChannels = 1;
     37 constexpr int kSamplesPerChannel = kSampleRateHz / 100;
     38 constexpr int kMaxMicLevel = 255;
     39 constexpr int kMinMicLevel = 12;
     40 constexpr int kDefaultClippedLevelStep = 15;
     41 constexpr float kMaxSampleS16 =
     42    static_cast<float>(std::numeric_limits<int16_t>::max());
     43 
     44 // Threshold in dB corresponding to a signal with an amplitude equal to 99% of
     45 // the dynamic range - i.e., computed as `20*log10(0.99)`.
     46 constexpr float kClippingThresholdDb = -0.08729610804900176f;
     47 
     48 void CallAnalyze(int num_calls,
     49                 const AudioFrameView<const float>& frame,
     50                 ClippingPredictor& predictor) {
     51  for (int i = 0; i < num_calls; ++i) {
     52    predictor.Analyze(frame);
     53  }
     54 }
     55 
     56 // Creates and analyzes an audio frame with a non-zero (approx. 4.15dB) crest
     57 // factor.
     58 void AnalyzeNonZeroCrestFactorAudio(int num_calls,
     59                                    int num_channels,
     60                                    float peak_ratio,
     61                                    ClippingPredictor& predictor) {
     62  RTC_DCHECK_GT(num_calls, 0);
     63  RTC_DCHECK_GT(num_channels, 0);
     64  RTC_DCHECK_LE(peak_ratio, 1.0f);
     65  std::vector<float*> audio(num_channels);
     66  std::vector<float> audio_data(num_channels * kSamplesPerChannel, 0.0f);
     67  for (int channel = 0; channel < num_channels; ++channel) {
     68    audio[channel] = &audio_data[channel * kSamplesPerChannel];
     69    for (int sample = 0; sample < kSamplesPerChannel; sample += 10) {
     70      audio[channel][sample] = 0.1f * peak_ratio * kMaxSampleS16;
     71      audio[channel][sample + 1] = 0.2f * peak_ratio * kMaxSampleS16;
     72      audio[channel][sample + 2] = 0.3f * peak_ratio * kMaxSampleS16;
     73      audio[channel][sample + 3] = 0.4f * peak_ratio * kMaxSampleS16;
     74      audio[channel][sample + 4] = 0.5f * peak_ratio * kMaxSampleS16;
     75      audio[channel][sample + 5] = 0.6f * peak_ratio * kMaxSampleS16;
     76      audio[channel][sample + 6] = 0.7f * peak_ratio * kMaxSampleS16;
     77      audio[channel][sample + 7] = 0.8f * peak_ratio * kMaxSampleS16;
     78      audio[channel][sample + 8] = 0.9f * peak_ratio * kMaxSampleS16;
     79      audio[channel][sample + 9] = 1.0f * peak_ratio * kMaxSampleS16;
     80    }
     81  }
     82  AudioFrameView<const float> frame(audio.data(), num_channels,
     83                                    kSamplesPerChannel);
     84  CallAnalyze(num_calls, frame, predictor);
     85 }
     86 
     87 void CheckChannelEstimatesWithValue(int num_channels,
     88                                    int level,
     89                                    int default_step,
     90                                    int min_mic_level,
     91                                    int max_mic_level,
     92                                    const ClippingPredictor& predictor,
     93                                    int expected) {
     94  for (int i = 0; i < num_channels; ++i) {
     95    SCOPED_TRACE(i);
     96    EXPECT_THAT(predictor.EstimateClippedLevelStep(
     97                    i, level, default_step, min_mic_level, max_mic_level),
     98                Optional(Eq(expected)));
     99  }
    100 }
    101 
    102 void CheckChannelEstimatesWithoutValue(int num_channels,
    103                                       int level,
    104                                       int default_step,
    105                                       int min_mic_level,
    106                                       int max_mic_level,
    107                                       const ClippingPredictor& predictor) {
    108  for (int i = 0; i < num_channels; ++i) {
    109    SCOPED_TRACE(i);
    110    EXPECT_EQ(predictor.EstimateClippedLevelStep(i, level, default_step,
    111                                                 min_mic_level, max_mic_level),
    112              std::nullopt);
    113  }
    114 }
    115 
    116 // Creates and analyzes an audio frame with a zero crest factor.
    117 void AnalyzeZeroCrestFactorAudio(int num_calls,
    118                                 int num_channels,
    119                                 float peak_ratio,
    120                                 ClippingPredictor& predictor) {
    121  RTC_DCHECK_GT(num_calls, 0);
    122  RTC_DCHECK_GT(num_channels, 0);
    123  RTC_DCHECK_LE(peak_ratio, 1.f);
    124  std::vector<float*> audio(num_channels);
    125  std::vector<float> audio_data(num_channels * kSamplesPerChannel, 0.f);
    126  for (int channel = 0; channel < num_channels; ++channel) {
    127    audio[channel] = &audio_data[channel * kSamplesPerChannel];
    128    for (int sample = 0; sample < kSamplesPerChannel; ++sample) {
    129      audio[channel][sample] = peak_ratio * kMaxSampleS16;
    130    }
    131  }
    132  auto frame = AudioFrameView<const float>(audio.data(), num_channels,
    133                                           kSamplesPerChannel);
    134  CallAnalyze(num_calls, frame, predictor);
    135 }
    136 
    137 TEST(ClippingPeakPredictorTest, NoPredictorCreated) {
    138  auto predictor =
    139      CreateClippingPredictor(kNumChannels, /*config=*/{.enabled = false});
    140  EXPECT_FALSE(predictor);
    141 }
    142 
    143 TEST(ClippingPeakPredictorTest, ClippingEventPredictionCreated) {
    144  // TODO(bugs.webrtc.org/12874): Use designated initializers one fixed.
    145  auto predictor = CreateClippingPredictor(
    146      kNumChannels,
    147      /*config=*/{.enabled = true,
    148                  .mode = ClippingPredictorMode::kClippingEventPrediction});
    149  EXPECT_TRUE(predictor);
    150 }
    151 
    152 TEST(ClippingPeakPredictorTest, AdaptiveStepClippingPeakPredictionCreated) {
    153  // TODO(bugs.webrtc.org/12874): Use designated initializers one fixed.
    154  auto predictor = CreateClippingPredictor(
    155      kNumChannels, /*config=*/{
    156          .enabled = true,
    157          .mode = ClippingPredictorMode::kAdaptiveStepClippingPeakPrediction});
    158  EXPECT_TRUE(predictor);
    159 }
    160 
    161 TEST(ClippingPeakPredictorTest, FixedStepClippingPeakPredictionCreated) {
    162  // TODO(bugs.webrtc.org/12874): Use designated initializers one fixed.
    163  auto predictor = CreateClippingPredictor(
    164      kNumChannels,
    165      /*config=*/{
    166          .enabled = true,
    167          .mode = ClippingPredictorMode::kFixedStepClippingPeakPrediction});
    168  EXPECT_TRUE(predictor);
    169 }
    170 
    171 class ClippingPredictorParameterization
    172    : public ::testing::TestWithParam<std::tuple<int, int, int, int>> {
    173 protected:
    174  int num_channels() const { return std::get<0>(GetParam()); }
    175  ClippingPredictorConfig GetConfig(ClippingPredictorMode mode) const {
    176    // TODO(bugs.webrtc.org/12874): Use designated initializers one fixed.
    177    return {/*enabled=*/true,
    178            /*mode=*/mode,
    179            /*window_length=*/std::get<1>(GetParam()),
    180            /*reference_window_length=*/std::get<2>(GetParam()),
    181            /*reference_window_delay=*/std::get<3>(GetParam()),
    182            /*clipping_threshold=*/-1.0f,
    183            /*crest_factor_margin=*/0.5f};
    184  }
    185 };
    186 
    187 TEST_P(ClippingPredictorParameterization,
    188       CheckClippingEventPredictorEstimateAfterCrestFactorDrop) {
    189  const ClippingPredictorConfig config =
    190      GetConfig(ClippingPredictorMode::kClippingEventPrediction);
    191  if (config.reference_window_length + config.reference_window_delay <=
    192      config.window_length) {
    193    return;
    194  }
    195  auto predictor = CreateClippingPredictor(num_channels(), config);
    196  AnalyzeNonZeroCrestFactorAudio(
    197      /*num_calls=*/config.reference_window_length +
    198          config.reference_window_delay - config.window_length,
    199      num_channels(), /*peak_ratio=*/0.99f, *predictor);
    200  CheckChannelEstimatesWithoutValue(num_channels(), /*level=*/255,
    201                                    kDefaultClippedLevelStep, kMinMicLevel,
    202                                    kMaxMicLevel, *predictor);
    203  AnalyzeZeroCrestFactorAudio(config.window_length, num_channels(),
    204                              /*peak_ratio=*/0.99f, *predictor);
    205  CheckChannelEstimatesWithValue(
    206      num_channels(), /*level=*/255, kDefaultClippedLevelStep, kMinMicLevel,
    207      kMaxMicLevel, *predictor, kDefaultClippedLevelStep);
    208 }
    209 
    210 TEST_P(ClippingPredictorParameterization,
    211       CheckClippingEventPredictorNoEstimateAfterConstantCrestFactor) {
    212  const ClippingPredictorConfig config =
    213      GetConfig(ClippingPredictorMode::kClippingEventPrediction);
    214  if (config.reference_window_length + config.reference_window_delay <=
    215      config.window_length) {
    216    return;
    217  }
    218  auto predictor = CreateClippingPredictor(num_channels(), config);
    219  AnalyzeNonZeroCrestFactorAudio(
    220      /*num_calls=*/config.reference_window_length +
    221          config.reference_window_delay - config.window_length,
    222      num_channels(), /*peak_ratio=*/0.99f, *predictor);
    223  CheckChannelEstimatesWithoutValue(num_channels(), /*level=*/255,
    224                                    kDefaultClippedLevelStep, kMinMicLevel,
    225                                    kMaxMicLevel, *predictor);
    226  AnalyzeNonZeroCrestFactorAudio(/*num_calls=*/config.window_length,
    227                                 num_channels(),
    228                                 /*peak_ratio=*/0.99f, *predictor);
    229  CheckChannelEstimatesWithoutValue(num_channels(), /*level=*/255,
    230                                    kDefaultClippedLevelStep, kMinMicLevel,
    231                                    kMaxMicLevel, *predictor);
    232 }
    233 
    234 TEST_P(ClippingPredictorParameterization,
    235       CheckClippingPeakPredictorEstimateAfterHighCrestFactor) {
    236  const ClippingPredictorConfig config =
    237      GetConfig(ClippingPredictorMode::kAdaptiveStepClippingPeakPrediction);
    238  if (config.reference_window_length + config.reference_window_delay <=
    239      config.window_length) {
    240    return;
    241  }
    242  auto predictor = CreateClippingPredictor(num_channels(), config);
    243  AnalyzeNonZeroCrestFactorAudio(
    244      /*num_calls=*/config.reference_window_length +
    245          config.reference_window_delay - config.window_length,
    246      num_channels(), /*peak_ratio=*/0.99f, *predictor);
    247  CheckChannelEstimatesWithoutValue(num_channels(), /*level=*/255,
    248                                    kDefaultClippedLevelStep, kMinMicLevel,
    249                                    kMaxMicLevel, *predictor);
    250  AnalyzeNonZeroCrestFactorAudio(/*num_calls=*/config.window_length,
    251                                 num_channels(),
    252                                 /*peak_ratio=*/0.99f, *predictor);
    253  CheckChannelEstimatesWithValue(
    254      num_channels(), /*level=*/255, kDefaultClippedLevelStep, kMinMicLevel,
    255      kMaxMicLevel, *predictor, kDefaultClippedLevelStep);
    256 }
    257 
    258 TEST_P(ClippingPredictorParameterization,
    259       CheckClippingPeakPredictorNoEstimateAfterLowCrestFactor) {
    260  const ClippingPredictorConfig config =
    261      GetConfig(ClippingPredictorMode::kAdaptiveStepClippingPeakPrediction);
    262  if (config.reference_window_length + config.reference_window_delay <=
    263      config.window_length) {
    264    return;
    265  }
    266  auto predictor = CreateClippingPredictor(num_channels(), config);
    267  AnalyzeZeroCrestFactorAudio(
    268      /*num_calls=*/config.reference_window_length +
    269          config.reference_window_delay - config.window_length,
    270      num_channels(), /*peak_ratio=*/0.99f, *predictor);
    271  CheckChannelEstimatesWithoutValue(num_channels(), /*level=*/255,
    272                                    kDefaultClippedLevelStep, kMinMicLevel,
    273                                    kMaxMicLevel, *predictor);
    274  AnalyzeNonZeroCrestFactorAudio(/*num_calls=*/config.window_length,
    275                                 num_channels(),
    276                                 /*peak_ratio=*/0.99f, *predictor);
    277  CheckChannelEstimatesWithoutValue(num_channels(), /*level=*/255,
    278                                    kDefaultClippedLevelStep, kMinMicLevel,
    279                                    kMaxMicLevel, *predictor);
    280 }
    281 
    282 INSTANTIATE_TEST_SUITE_P(GainController1ClippingPredictor,
    283                         ClippingPredictorParameterization,
    284                         ::testing::Combine(::testing::Values(1, 5),
    285                                            ::testing::Values(1, 5, 10),
    286                                            ::testing::Values(1, 5),
    287                                            ::testing::Values(0, 1, 5)));
    288 
    289 class ClippingEventPredictorParameterization
    290    : public ::testing::TestWithParam<std::tuple<float, float>> {
    291 protected:
    292  ClippingPredictorConfig GetConfig() const {
    293    // TODO(bugs.webrtc.org/12874): Use designated initializers one fixed.
    294    return {/*enabled=*/true,
    295            /*mode=*/ClippingPredictorMode::kClippingEventPrediction,
    296            /*window_length=*/5,
    297            /*reference_window_length=*/5,
    298            /*reference_window_delay=*/5,
    299            /*clipping_threshold=*/std::get<0>(GetParam()),
    300            /*crest_factor_margin=*/std::get<1>(GetParam())};
    301  }
    302 };
    303 
    304 TEST_P(ClippingEventPredictorParameterization,
    305       CheckEstimateAfterCrestFactorDrop) {
    306  const ClippingPredictorConfig config = GetConfig();
    307  auto predictor = CreateClippingPredictor(kNumChannels, config);
    308  AnalyzeNonZeroCrestFactorAudio(/*num_calls=*/config.reference_window_length,
    309                                 kNumChannels, /*peak_ratio=*/0.99f,
    310                                 *predictor);
    311  CheckChannelEstimatesWithoutValue(kNumChannels, /*level=*/255,
    312                                    kDefaultClippedLevelStep, kMinMicLevel,
    313                                    kMaxMicLevel, *predictor);
    314  AnalyzeZeroCrestFactorAudio(config.window_length, kNumChannels,
    315                              /*peak_ratio=*/0.99f, *predictor);
    316  // TODO(bugs.webrtc.org/12774): Add clarifying comment.
    317  // TODO(bugs.webrtc.org/12774): Remove 4.15f threshold and split tests.
    318  if (config.clipping_threshold < kClippingThresholdDb &&
    319      config.crest_factor_margin < 4.15f) {
    320    CheckChannelEstimatesWithValue(
    321        kNumChannels, /*level=*/255, kDefaultClippedLevelStep, kMinMicLevel,
    322        kMaxMicLevel, *predictor, kDefaultClippedLevelStep);
    323  } else {
    324    CheckChannelEstimatesWithoutValue(kNumChannels, /*level=*/255,
    325                                      kDefaultClippedLevelStep, kMinMicLevel,
    326                                      kMaxMicLevel, *predictor);
    327  }
    328 }
    329 
    330 INSTANTIATE_TEST_SUITE_P(GainController1ClippingPredictor,
    331                         ClippingEventPredictorParameterization,
    332                         ::testing::Combine(::testing::Values(-1.0f, 0.0f),
    333                                            ::testing::Values(3.0f, 4.16f)));
    334 
    335 class ClippingPredictorModeParameterization
    336    : public ::testing::TestWithParam<ClippingPredictorMode> {
    337 protected:
    338  ClippingPredictorConfig GetConfig(float clipping_threshold_dbfs) const {
    339    // TODO(bugs.webrtc.org/12874): Use designated initializers one fixed.
    340    return {/*enabled=*/true,
    341            /*mode=*/GetParam(),
    342            /*window_length=*/5,
    343            /*reference_window_length=*/5,
    344            /*reference_window_delay=*/5,
    345            /*clipping_threshold=*/clipping_threshold_dbfs,
    346            /*crest_factor_margin=*/3.0f};
    347  }
    348 };
    349 
    350 TEST_P(ClippingPredictorModeParameterization,
    351       CheckEstimateAfterHighCrestFactorWithNoClippingMargin) {
    352  const ClippingPredictorConfig config = GetConfig(
    353      /*clipping_threshold_dbfs=*/0.0f);
    354  auto predictor = CreateClippingPredictor(kNumChannels, config);
    355  AnalyzeNonZeroCrestFactorAudio(/*num_calls=*/config.reference_window_length,
    356                                 kNumChannels, /*peak_ratio=*/0.99f,
    357                                 *predictor);
    358  CheckChannelEstimatesWithoutValue(kNumChannels, /*level=*/255,
    359                                    kDefaultClippedLevelStep, kMinMicLevel,
    360                                    kMaxMicLevel, *predictor);
    361  AnalyzeZeroCrestFactorAudio(config.window_length, kNumChannels,
    362                              /*peak_ratio=*/0.99f, *predictor);
    363  // Since the clipping threshold is set to 0 dBFS, `EstimateClippedLevelStep()`
    364  // is expected to return an unavailable value.
    365  CheckChannelEstimatesWithoutValue(kNumChannels, /*level=*/255,
    366                                    kDefaultClippedLevelStep, kMinMicLevel,
    367                                    kMaxMicLevel, *predictor);
    368 }
    369 
    370 TEST_P(ClippingPredictorModeParameterization,
    371       CheckEstimateAfterHighCrestFactorWithClippingMargin) {
    372  const ClippingPredictorConfig config =
    373      GetConfig(/*clipping_threshold_dbfs=*/-1.0f);
    374  auto predictor = CreateClippingPredictor(kNumChannels, config);
    375  AnalyzeNonZeroCrestFactorAudio(/*num_calls=*/config.reference_window_length,
    376                                 kNumChannels,
    377                                 /*peak_ratio=*/0.99f, *predictor);
    378  CheckChannelEstimatesWithoutValue(kNumChannels, /*level=*/255,
    379                                    kDefaultClippedLevelStep, kMinMicLevel,
    380                                    kMaxMicLevel, *predictor);
    381  AnalyzeZeroCrestFactorAudio(config.window_length, kNumChannels,
    382                              /*peak_ratio=*/0.99f, *predictor);
    383  // TODO(bugs.webrtc.org/12774): Add clarifying comment.
    384  const float expected_step =
    385      config.mode == ClippingPredictorMode::kAdaptiveStepClippingPeakPrediction
    386          ? 17
    387          : kDefaultClippedLevelStep;
    388  CheckChannelEstimatesWithValue(kNumChannels, /*level=*/255,
    389                                 kDefaultClippedLevelStep, kMinMicLevel,
    390                                 kMaxMicLevel, *predictor, expected_step);
    391 }
    392 
    393 INSTANTIATE_TEST_SUITE_P(
    394    GainController1ClippingPredictor,
    395    ClippingPredictorModeParameterization,
    396    ::testing::Values(
    397        ClippingPredictorMode::kAdaptiveStepClippingPeakPrediction,
    398        ClippingPredictorMode::kFixedStepClippingPeakPrediction));
    399 
    400 TEST(ClippingEventPredictorTest, CheckEstimateAfterReset) {
    401  // TODO(bugs.webrtc.org/12874): Use designated initializers one fixed.
    402  constexpr ClippingPredictorConfig kConfig{
    403      /*enabled=*/true,
    404      /*mode=*/ClippingPredictorMode::kClippingEventPrediction,
    405      /*window_length=*/5,
    406      /*reference_window_length=*/5,
    407      /*reference_window_delay=*/5,
    408      /*clipping_threshold=*/-1.0f,
    409      /*crest_factor_margin=*/3.0f};
    410  auto predictor = CreateClippingPredictor(kNumChannels, kConfig);
    411  AnalyzeNonZeroCrestFactorAudio(/*num_calls=*/kConfig.reference_window_length,
    412                                 kNumChannels,
    413                                 /*peak_ratio=*/0.99f, *predictor);
    414  CheckChannelEstimatesWithoutValue(kNumChannels, /*level=*/255,
    415                                    kDefaultClippedLevelStep, kMinMicLevel,
    416                                    kMaxMicLevel, *predictor);
    417  predictor->Reset();
    418  AnalyzeZeroCrestFactorAudio(kConfig.window_length, kNumChannels,
    419                              /*peak_ratio=*/0.99f, *predictor);
    420  CheckChannelEstimatesWithoutValue(kNumChannels, /*level=*/255,
    421                                    kDefaultClippedLevelStep, kMinMicLevel,
    422                                    kMaxMicLevel, *predictor);
    423 }
    424 
    425 TEST(ClippingPeakPredictorTest, CheckNoEstimateAfterReset) {
    426  // TODO(bugs.webrtc.org/12874): Use designated initializers one fixed.
    427  constexpr ClippingPredictorConfig kConfig{
    428      /*enabled=*/true,
    429      /*mode=*/ClippingPredictorMode::kAdaptiveStepClippingPeakPrediction,
    430      /*window_length=*/5,
    431      /*reference_window_length=*/5,
    432      /*reference_window_delay=*/5,
    433      /*clipping_threshold=*/-1.0f};
    434  auto predictor = CreateClippingPredictor(kNumChannels, kConfig);
    435  AnalyzeNonZeroCrestFactorAudio(/*num_calls=*/kConfig.reference_window_length,
    436                                 kNumChannels,
    437                                 /*peak_ratio=*/0.99f, *predictor);
    438  CheckChannelEstimatesWithoutValue(kNumChannels, /*level=*/255,
    439                                    kDefaultClippedLevelStep, kMinMicLevel,
    440                                    kMaxMicLevel, *predictor);
    441  predictor->Reset();
    442  AnalyzeZeroCrestFactorAudio(kConfig.window_length, kNumChannels,
    443                              /*peak_ratio=*/0.99f, *predictor);
    444  CheckChannelEstimatesWithoutValue(kNumChannels, /*level=*/255,
    445                                    kDefaultClippedLevelStep, kMinMicLevel,
    446                                    kMaxMicLevel, *predictor);
    447 }
    448 
    449 TEST(ClippingPeakPredictorTest, CheckAdaptiveStepEstimate) {
    450  // TODO(bugs.webrtc.org/12874): Use designated initializers one fixed.
    451  constexpr ClippingPredictorConfig kConfig{
    452      /*enabled=*/true,
    453      /*mode=*/ClippingPredictorMode::kAdaptiveStepClippingPeakPrediction,
    454      /*window_length=*/5,
    455      /*reference_window_length=*/5,
    456      /*reference_window_delay=*/5,
    457      /*clipping_threshold=*/-1.0f};
    458  auto predictor = CreateClippingPredictor(kNumChannels, kConfig);
    459  AnalyzeNonZeroCrestFactorAudio(/*num_calls=*/kConfig.reference_window_length,
    460                                 kNumChannels, /*peak_ratio=*/0.99f,
    461                                 *predictor);
    462  CheckChannelEstimatesWithoutValue(kNumChannels, /*level=*/255,
    463                                    kDefaultClippedLevelStep, kMinMicLevel,
    464                                    kMaxMicLevel, *predictor);
    465  AnalyzeZeroCrestFactorAudio(kConfig.window_length, kNumChannels,
    466                              /*peak_ratio=*/0.99f, *predictor);
    467  CheckChannelEstimatesWithValue(kNumChannels, /*level=*/255,
    468                                 kDefaultClippedLevelStep, kMinMicLevel,
    469                                 kMaxMicLevel, *predictor, /*expected=*/17);
    470 }
    471 
    472 TEST(ClippingPeakPredictorTest, CheckFixedStepEstimate) {
    473  // TODO(bugs.webrtc.org/12874): Use designated initializers one fixed.
    474  constexpr ClippingPredictorConfig kConfig{
    475      /*enabled=*/true,
    476      /*mode=*/ClippingPredictorMode::kFixedStepClippingPeakPrediction,
    477      /*window_length=*/5,
    478      /*reference_window_length=*/5,
    479      /*reference_window_delay=*/5,
    480      /*clipping_threshold=*/-1.0f};
    481  auto predictor = CreateClippingPredictor(kNumChannels, kConfig);
    482  AnalyzeNonZeroCrestFactorAudio(/*num_calls=*/kConfig.reference_window_length,
    483                                 kNumChannels, /*peak_ratio=*/0.99f,
    484                                 *predictor);
    485  CheckChannelEstimatesWithoutValue(kNumChannels, /*level=*/255,
    486                                    kDefaultClippedLevelStep, kMinMicLevel,
    487                                    kMaxMicLevel, *predictor);
    488  AnalyzeZeroCrestFactorAudio(kConfig.window_length, kNumChannels,
    489                              /*peak_ratio=*/0.99f, *predictor);
    490  CheckChannelEstimatesWithValue(
    491      kNumChannels, /*level=*/255, kDefaultClippedLevelStep, kMinMicLevel,
    492      kMaxMicLevel, *predictor, kDefaultClippedLevelStep);
    493 }
    494 
    495 }  // namespace
    496 }  // namespace webrtc