/*
 *  Copyright (c) 2017 The WebRTC project authors. All Rights Reserved.
 *
 *  Use of this source code is governed by a BSD-style license
 *  that can be found in the LICENSE file in the root of the source
 *  tree. An additional intellectual property rights grant can be found
 *  in the file PATENTS.  All contributing project authors may
 *  be found in the AUTHORS file in the root of the source tree.
  */

#include "webrtc/modules/audio_processing/aec3/matched_filter_lag_aggregator.h"

#include <sstream>
#include <string>
#include <vector>

#include "webrtc/modules/audio_processing/aec3/aec3_common.h"
#include "webrtc/modules/audio_processing/logging/apm_data_dumper.h"
#include "webrtc/rtc_base/array_view.h"
#include "webrtc/test/gtest.h"

namespace webrtc {
namespace {

void VerifyNoAggregateOutputForRepeatedLagAggregation(
    size_t num_repetitions,
    rtc::ArrayView<const MatchedFilter::LagEstimate> lag_estimates,
    MatchedFilterLagAggregator* aggregator) {
  for (size_t k = 0; k < num_repetitions; ++k) {
    EXPECT_FALSE(aggregator->Aggregate(lag_estimates));
  }
}

constexpr size_t kThresholdForRequiredLagUpdatesInARow = 10;
constexpr size_t kThresholdForRequiredIdenticalLagAggregates = 15;

}  // namespace

// Verifies that the most accurate lag estimate is chosen.
TEST(MatchedFilterLagAggregator, MostAccurateLagChosen) {
  constexpr size_t kArtificialLag1 = 5;
  constexpr size_t kArtificialLag2 = 10;
  ApmDataDumper data_dumper(0);
  std::vector<MatchedFilter::LagEstimate> lag_estimates(2);
  MatchedFilterLagAggregator aggregator(&data_dumper, lag_estimates.size());
  lag_estimates[0] =
      MatchedFilter::LagEstimate(1.f, true, kArtificialLag1, true);
  lag_estimates[1] =
      MatchedFilter::LagEstimate(0.5f, true, kArtificialLag2, true);

  VerifyNoAggregateOutputForRepeatedLagAggregation(
      kThresholdForRequiredLagUpdatesInARow +
          kThresholdForRequiredIdenticalLagAggregates,
      lag_estimates, &aggregator);
  rtc::Optional<size_t> aggregated_lag = aggregator.Aggregate(lag_estimates);
  EXPECT_TRUE(aggregated_lag);
  EXPECT_EQ(kArtificialLag1, *aggregated_lag);

  lag_estimates[0] =
      MatchedFilter::LagEstimate(0.5f, true, kArtificialLag1, true);
  lag_estimates[1] =
      MatchedFilter::LagEstimate(1.f, true, kArtificialLag2, true);

  VerifyNoAggregateOutputForRepeatedLagAggregation(
      kThresholdForRequiredIdenticalLagAggregates, lag_estimates, &aggregator);
  aggregated_lag = aggregator.Aggregate(lag_estimates);
  EXPECT_TRUE(aggregated_lag);
  EXPECT_EQ(kArtificialLag2, *aggregated_lag);
}

// Verifies that varying lag estimates causes lag estimates to not be deemed
// reliable.
TEST(MatchedFilterLagAggregator,
     LagEstimateInvarianceRequiredForAggregatedLag) {
  constexpr size_t kArtificialLag1 = 5;
  constexpr size_t kArtificialLag2 = 10;
  ApmDataDumper data_dumper(0);
  std::vector<MatchedFilter::LagEstimate> lag_estimates(1);
  MatchedFilterLagAggregator aggregator(&data_dumper, lag_estimates.size());
  lag_estimates[0] =
      MatchedFilter::LagEstimate(1.f, true, kArtificialLag1, true);
  VerifyNoAggregateOutputForRepeatedLagAggregation(
      kThresholdForRequiredLagUpdatesInARow +
          kThresholdForRequiredIdenticalLagAggregates,
      lag_estimates, &aggregator);
  rtc::Optional<size_t> aggregated_lag = aggregator.Aggregate(lag_estimates);
  EXPECT_TRUE(aggregated_lag);
  EXPECT_EQ(kArtificialLag1, *aggregated_lag);

  lag_estimates[0] =
      MatchedFilter::LagEstimate(1.f, true, kArtificialLag2, true);

  VerifyNoAggregateOutputForRepeatedLagAggregation(
      kThresholdForRequiredIdenticalLagAggregates, lag_estimates, &aggregator);
  aggregated_lag = aggregator.Aggregate(lag_estimates);
  EXPECT_TRUE(aggregated_lag);
  EXPECT_EQ(kArtificialLag2, *aggregated_lag);
}

// Verifies that lag estimate updates are required to produce an updated lag
// aggregate.
TEST(MatchedFilterLagAggregator, LagEstimateUpdatesRequiredForAggregatedLag) {
  constexpr size_t kArtificialLag1 = 5;
  constexpr size_t kArtificialLag2 = 10;
  ApmDataDumper data_dumper(0);
  std::vector<MatchedFilter::LagEstimate> lag_estimates(1);
  MatchedFilterLagAggregator aggregator(&data_dumper, lag_estimates.size());
  lag_estimates[0] =
      MatchedFilter::LagEstimate(1.f, true, kArtificialLag1, true);
  VerifyNoAggregateOutputForRepeatedLagAggregation(
      kThresholdForRequiredLagUpdatesInARow +
          kThresholdForRequiredIdenticalLagAggregates,
      lag_estimates, &aggregator);
  rtc::Optional<size_t> aggregated_lag = aggregator.Aggregate(lag_estimates);
  EXPECT_TRUE(aggregated_lag);
  EXPECT_EQ(kArtificialLag1, *aggregated_lag);

  lag_estimates[0] =
      MatchedFilter::LagEstimate(1.f, true, kArtificialLag2, false);

  for (size_t k = 0; k < kThresholdForRequiredLagUpdatesInARow +
                             kThresholdForRequiredIdenticalLagAggregates + 1;
       ++k) {
    aggregated_lag = aggregator.Aggregate(lag_estimates);
    EXPECT_TRUE(aggregated_lag);
    EXPECT_EQ(kArtificialLag1, *aggregated_lag);
  }

  lag_estimates[0] =
      MatchedFilter::LagEstimate(1.f, true, kArtificialLag2, true);
  for (size_t k = 0; k < kThresholdForRequiredLagUpdatesInARow; ++k) {
    aggregated_lag = aggregator.Aggregate(lag_estimates);
    EXPECT_TRUE(aggregated_lag);
    EXPECT_EQ(kArtificialLag1, *aggregated_lag);
  }

  VerifyNoAggregateOutputForRepeatedLagAggregation(
      kThresholdForRequiredIdenticalLagAggregates, lag_estimates, &aggregator);

  aggregated_lag = aggregator.Aggregate(lag_estimates);
  EXPECT_TRUE(aggregated_lag);
  EXPECT_EQ(kArtificialLag2, *aggregated_lag);
}

// Verifies that an aggregated lag is persistent if the lag estimates do not
// change and that an aggregated lag is not produced without gaining lag
// estimate confidence.
TEST(MatchedFilterLagAggregator, PersistentAggregatedLag) {
  constexpr size_t kArtificialLag = 5;
  ApmDataDumper data_dumper(0);
  std::vector<MatchedFilter::LagEstimate> lag_estimates(1);
  MatchedFilterLagAggregator aggregator(&data_dumper, lag_estimates.size());
  lag_estimates[0] =
      MatchedFilter::LagEstimate(1.f, true, kArtificialLag, true);
  VerifyNoAggregateOutputForRepeatedLagAggregation(
      kThresholdForRequiredLagUpdatesInARow +
          kThresholdForRequiredIdenticalLagAggregates,
      lag_estimates, &aggregator);
  rtc::Optional<size_t> aggregated_lag = aggregator.Aggregate(lag_estimates);
  EXPECT_TRUE(aggregated_lag);
  EXPECT_EQ(kArtificialLag, *aggregated_lag);

  aggregated_lag = aggregator.Aggregate(lag_estimates);
  EXPECT_TRUE(aggregated_lag);
  EXPECT_EQ(kArtificialLag, *aggregated_lag);
}

#if RTC_DCHECK_IS_ON && GTEST_HAS_DEATH_TEST && !defined(WEBRTC_ANDROID)

// Verifies the check for correct number of lag estimates.
TEST(MatchedFilterLagAggregator, IncorrectNumberOfLagEstimates) {
  ApmDataDumper data_dumper(0);
  MatchedFilterLagAggregator aggregator(&data_dumper, 1);
  std::vector<MatchedFilter::LagEstimate> lag_estimates(2);

  EXPECT_DEATH(aggregator.Aggregate(lag_estimates), "");
}

// Verifies the check for non-zero number of lag estimates.
TEST(MatchedFilterLagAggregator, NonZeroLagEstimates) {
  ApmDataDumper data_dumper(0);
  EXPECT_DEATH(MatchedFilterLagAggregator(&data_dumper, 0), "");
}

// Verifies the check for non-null data dumper.
TEST(MatchedFilterLagAggregator, NullDataDumper) {
  EXPECT_DEATH(MatchedFilterLagAggregator(nullptr, 1), "");
}

#endif

}  // namespace webrtc
