/*
 *  Copyright (c) 2015 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 <stddef.h>  // size_t

#include <memory>
#include <string>
#include <vector>

#include "absl/strings/string_view.h"
#include "api/audio/builtin_audio_processing_builder.h"
#include "api/audio/echo_canceller3_factory.h"
#include "api/environment/environment_factory.h"
#include "modules/audio_coding/neteq/tools/resample_input_audio_file.h"
#include "modules/audio_processing/aec_dump/aec_dump_factory.h"
#include "modules/audio_processing/test/debug_dump_replayer.h"
#include "modules/audio_processing/test/test_utils.h"
#include "rtc_base/task_queue_for_test.h"
#include "test/gtest.h"
#include "test/testsupport/file_utils.h"

namespace webrtc {
namespace test {

namespace {

void MaybeResetBuffer(std::unique_ptr<ChannelBuffer<float>>* buffer,
                      const StreamConfig& config) {
  auto& buffer_ref = *buffer;
  if (!buffer_ref.get() || buffer_ref->num_frames() != config.num_frames() ||
      buffer_ref->num_channels() != config.num_channels()) {
    buffer_ref.reset(
        new ChannelBuffer<float>(config.num_frames(), config.num_channels()));
  }
}

class DebugDumpGenerator {
 public:
  DebugDumpGenerator(absl::string_view input_file_name,
                     int input_rate_hz,
                     int input_channels,
                     absl::string_view reverse_file_name,
                     int reverse_rate_hz,
                     int reverse_channels,
                     absl::string_view dump_file_name,
                     bool enable_pre_amplifier);

  // Constructor that uses default input files.
  explicit DebugDumpGenerator(const AudioProcessing::Config& apm_config);

  ~DebugDumpGenerator();

  // Changes the sample rate of the input audio to the APM.
  void SetInputRate(int rate_hz);

  // Sets if converts stereo input signal to mono by discarding other channels.
  void ForceInputMono(bool mono);

  // Changes the sample rate of the reverse audio to the APM.
  void SetReverseRate(int rate_hz);

  // Sets if converts stereo reverse signal to mono by discarding other
  // channels.
  void ForceReverseMono(bool mono);

  // Sets the required sample rate of the APM output.
  void SetOutputRate(int rate_hz);

  // Sets the required channels of the APM output.
  void SetOutputChannels(int channels);

  std::string dump_file_name() const { return dump_file_name_; }

  void StartRecording();
  void Process(size_t num_blocks);
  void StopRecording();
  AudioProcessing* apm() const { return apm_.get(); }

 private:
  static void ReadAndDeinterleave(ResampleInputAudioFile* audio,
                                  int channels,
                                  const StreamConfig& config,
                                  float* const* buffer);

  // APM input/output settings.
  StreamConfig input_config_;
  StreamConfig reverse_config_;
  StreamConfig output_config_;

  // Input file format.
  const std::string input_file_name_;
  ResampleInputAudioFile input_audio_;
  const int input_file_channels_;

  // Reverse file format.
  const std::string reverse_file_name_;
  ResampleInputAudioFile reverse_audio_;
  const int reverse_file_channels_;

  // Buffer for APM input/output.
  std::unique_ptr<ChannelBuffer<float>> input_;
  std::unique_ptr<ChannelBuffer<float>> reverse_;
  std::unique_ptr<ChannelBuffer<float>> output_;

  bool enable_pre_amplifier_;

  TaskQueueForTest worker_queue_;
  rtc::scoped_refptr<AudioProcessing> apm_;

  const std::string dump_file_name_;
};

DebugDumpGenerator::DebugDumpGenerator(absl::string_view input_file_name,
                                       int input_rate_hz,
                                       int input_channels,
                                       absl::string_view reverse_file_name,
                                       int reverse_rate_hz,
                                       int reverse_channels,
                                       absl::string_view dump_file_name,
                                       bool enable_pre_amplifier)
    : input_config_(input_rate_hz, input_channels),
      reverse_config_(reverse_rate_hz, reverse_channels),
      output_config_(input_rate_hz, input_channels),
      input_audio_(input_file_name, input_rate_hz, input_rate_hz),
      input_file_channels_(input_channels),
      reverse_audio_(reverse_file_name, reverse_rate_hz, reverse_rate_hz),
      reverse_file_channels_(reverse_channels),
      input_(new ChannelBuffer<float>(input_config_.num_frames(),
                                      input_config_.num_channels())),
      reverse_(new ChannelBuffer<float>(reverse_config_.num_frames(),
                                        reverse_config_.num_channels())),
      output_(new ChannelBuffer<float>(output_config_.num_frames(),
                                       output_config_.num_channels())),
      enable_pre_amplifier_(enable_pre_amplifier),
      worker_queue_("debug_dump_generator_worker_queue"),
      dump_file_name_(dump_file_name) {
  apm_ = BuiltinAudioProcessingBuilder().Build(CreateEnvironment());
}

DebugDumpGenerator::DebugDumpGenerator(
    const AudioProcessing::Config& apm_config)
    : DebugDumpGenerator(ResourcePath("near32_stereo", "pcm"),
                         32000,
                         2,
                         ResourcePath("far32_stereo", "pcm"),
                         32000,
                         2,
                         TempFilename(OutputPath(), "debug_aec"),
                         apm_config.pre_amplifier.enabled) {
  apm_->ApplyConfig(apm_config);
}

DebugDumpGenerator::~DebugDumpGenerator() {
  remove(dump_file_name_.c_str());
}

void DebugDumpGenerator::SetInputRate(int rate_hz) {
  input_audio_.set_output_rate_hz(rate_hz);
  input_config_.set_sample_rate_hz(rate_hz);
  MaybeResetBuffer(&input_, input_config_);
}

void DebugDumpGenerator::ForceInputMono(bool mono) {
  const int channels = mono ? 1 : input_file_channels_;
  input_config_.set_num_channels(channels);
  MaybeResetBuffer(&input_, input_config_);
}

void DebugDumpGenerator::SetReverseRate(int rate_hz) {
  reverse_audio_.set_output_rate_hz(rate_hz);
  reverse_config_.set_sample_rate_hz(rate_hz);
  MaybeResetBuffer(&reverse_, reverse_config_);
}

void DebugDumpGenerator::ForceReverseMono(bool mono) {
  const int channels = mono ? 1 : reverse_file_channels_;
  reverse_config_.set_num_channels(channels);
  MaybeResetBuffer(&reverse_, reverse_config_);
}

void DebugDumpGenerator::SetOutputRate(int rate_hz) {
  output_config_.set_sample_rate_hz(rate_hz);
  MaybeResetBuffer(&output_, output_config_);
}

void DebugDumpGenerator::SetOutputChannels(int channels) {
  output_config_.set_num_channels(channels);
  MaybeResetBuffer(&output_, output_config_);
}

void DebugDumpGenerator::StartRecording() {
  apm_->AttachAecDump(
      AecDumpFactory::Create(dump_file_name_.c_str(), -1, worker_queue_.Get()));
}

void DebugDumpGenerator::Process(size_t num_blocks) {
  for (size_t i = 0; i < num_blocks; ++i) {
    ReadAndDeinterleave(&reverse_audio_, reverse_file_channels_,
                        reverse_config_, reverse_->channels());
    ReadAndDeinterleave(&input_audio_, input_file_channels_, input_config_,
                        input_->channels());
    RTC_CHECK_EQ(AudioProcessing::kNoError, apm_->set_stream_delay_ms(100));
    apm_->set_stream_analog_level(100);
    if (enable_pre_amplifier_) {
      apm_->SetRuntimeSetting(
          AudioProcessing::RuntimeSetting::CreateCapturePreGain(1 + i % 10));
    }
    apm_->set_stream_key_pressed(i % 10 == 9);
    RTC_CHECK_EQ(AudioProcessing::kNoError,
                 apm_->ProcessStream(input_->channels(), input_config_,
                                     output_config_, output_->channels()));

    RTC_CHECK_EQ(
        AudioProcessing::kNoError,
        apm_->ProcessReverseStream(reverse_->channels(), reverse_config_,
                                   reverse_config_, reverse_->channels()));
  }
}

void DebugDumpGenerator::StopRecording() {
  apm_->DetachAecDump();
}

void DebugDumpGenerator::ReadAndDeinterleave(ResampleInputAudioFile* audio,
                                             int channels,
                                             const StreamConfig& config,
                                             float* const* buffer) {
  const size_t num_frames = config.num_frames();
  const int out_channels = config.num_channels();

  std::vector<int16_t> signal(channels * num_frames);

  audio->Read(num_frames * channels, &signal[0]);

  // We only allow reducing number of channels by discarding some channels.
  RTC_CHECK_LE(out_channels, channels);
  for (int channel = 0; channel < out_channels; ++channel) {
    for (size_t i = 0; i < num_frames; ++i) {
      buffer[channel][i] = S16ToFloat(signal[i * channels + channel]);
    }
  }
}

}  // namespace

class DebugDumpTest : public ::testing::Test {
 public:
  // VerifyDebugDump replays a debug dump using APM and verifies that the result
  // is bit-exact-identical to the output channel in the dump. This is only
  // guaranteed if the debug dump is started on the first frame.
  void VerifyDebugDump(absl::string_view in_filename);

 private:
  DebugDumpReplayer debug_dump_replayer_;
};

void DebugDumpTest::VerifyDebugDump(absl::string_view in_filename) {
  ASSERT_TRUE(debug_dump_replayer_.SetDumpFile(in_filename));

  while (const std::optional<audioproc::Event> event =
             debug_dump_replayer_.GetNextEvent()) {
    debug_dump_replayer_.RunNextEvent();
    if (event->type() == audioproc::Event::STREAM) {
      const audioproc::Stream* msg = &event->stream();
      const StreamConfig output_config = debug_dump_replayer_.GetOutputConfig();
      const ChannelBuffer<float>* output = debug_dump_replayer_.GetOutput();
      // Check that output of APM is bit-exact to the output in the dump.
      ASSERT_EQ(output_config.num_channels(),
                static_cast<size_t>(msg->output_channel_size()));
      ASSERT_EQ(output_config.num_frames() * sizeof(float),
                msg->output_channel(0).size());
      for (int i = 0; i < msg->output_channel_size(); ++i) {
        ASSERT_EQ(0,
                  memcmp(output->channels()[i], msg->output_channel(i).data(),
                         msg->output_channel(i).size()));
      }
    }
  }
}

TEST_F(DebugDumpTest, SimpleCase) {
  DebugDumpGenerator generator(/*apm_config=*/{});
  generator.StartRecording();
  generator.Process(100);
  generator.StopRecording();
  VerifyDebugDump(generator.dump_file_name());
}

// TODO(bugs.webrtc.org/345674542): Fix/enable.
#if defined(__has_feature) && __has_feature(undefined_behavior_sanitizer)
TEST_F(DebugDumpTest, DISABLED_ChangeInputFormat) {
#else
TEST_F(DebugDumpTest, ChangeInputFormat) {
#endif
  DebugDumpGenerator generator(/*apm_config=*/{});

  generator.StartRecording();
  generator.Process(100);
  generator.SetInputRate(48000);

  generator.ForceInputMono(true);
  // Number of output channel should not be larger than that of input. APM will
  // fail otherwise.
  generator.SetOutputChannels(1);

  generator.Process(100);
  generator.StopRecording();
  VerifyDebugDump(generator.dump_file_name());
}

// TODO(bugs.webrtc.org/345674542): Fix/enable.
#if defined(__has_feature) && __has_feature(undefined_behavior_sanitizer)
TEST_F(DebugDumpTest, DISABLED_ChangeReverseFormat) {
#else
TEST_F(DebugDumpTest, ChangeReverseFormat) {
#endif
  DebugDumpGenerator generator(/*apm_config=*/{});
  generator.StartRecording();
  generator.Process(100);
  generator.SetReverseRate(48000);
  generator.ForceReverseMono(true);
  generator.Process(100);
  generator.StopRecording();
  VerifyDebugDump(generator.dump_file_name());
}

TEST_F(DebugDumpTest, ChangeOutputFormat) {
  DebugDumpGenerator generator(/*apm_config=*/{});
  generator.StartRecording();
  generator.Process(100);
  generator.SetOutputRate(48000);
  generator.SetOutputChannels(1);
  generator.Process(100);
  generator.StopRecording();
  VerifyDebugDump(generator.dump_file_name());
}

TEST_F(DebugDumpTest, ToggleAec) {
  AudioProcessing::Config apm_config;
  apm_config.echo_canceller.enabled = true;
  DebugDumpGenerator generator(apm_config);
  generator.StartRecording();
  generator.Process(100);

  apm_config.echo_canceller.enabled = false;
  generator.apm()->ApplyConfig(apm_config);

  generator.Process(100);
  generator.StopRecording();
  VerifyDebugDump(generator.dump_file_name());
}

TEST_F(DebugDumpTest, VerifyCombinedExperimentalStringInclusive) {
  AudioProcessing::Config apm_config;
  apm_config.echo_canceller.enabled = true;
  apm_config.gain_controller1.analog_gain_controller.enabled = true;
  apm_config.gain_controller1.analog_gain_controller.startup_min_volume = 0;
  DebugDumpGenerator generator(apm_config);
  generator.StartRecording();
  generator.Process(100);
  generator.StopRecording();

  DebugDumpReplayer debug_dump_replayer_;

  ASSERT_TRUE(debug_dump_replayer_.SetDumpFile(generator.dump_file_name()));

  while (const std::optional<audioproc::Event> event =
             debug_dump_replayer_.GetNextEvent()) {
    debug_dump_replayer_.RunNextEvent();
    if (event->type() == audioproc::Event::CONFIG) {
      const audioproc::Config* msg = &event->config();
      ASSERT_TRUE(msg->has_experiments_description());
      EXPECT_PRED_FORMAT2(::testing::IsSubstring, "EchoController",
                          msg->experiments_description().c_str());
    }
  }
}

TEST_F(DebugDumpTest, VerifyCombinedExperimentalStringExclusive) {
  AudioProcessing::Config apm_config;
  apm_config.echo_canceller.enabled = true;
  DebugDumpGenerator generator(apm_config);
  generator.StartRecording();
  generator.Process(100);
  generator.StopRecording();

  DebugDumpReplayer debug_dump_replayer_;

  ASSERT_TRUE(debug_dump_replayer_.SetDumpFile(generator.dump_file_name()));

  while (const std::optional<audioproc::Event> event =
             debug_dump_replayer_.GetNextEvent()) {
    debug_dump_replayer_.RunNextEvent();
    if (event->type() == audioproc::Event::CONFIG) {
      const audioproc::Config* msg = &event->config();
      ASSERT_TRUE(msg->has_experiments_description());
      EXPECT_PRED_FORMAT2(::testing::IsNotSubstring,
                          "AgcClippingLevelExperiment",
                          msg->experiments_description().c_str());
    }
  }
}

TEST_F(DebugDumpTest, VerifyAec3ExperimentalString) {
  AudioProcessing::Config apm_config;
  apm_config.echo_canceller.enabled = true;
  DebugDumpGenerator generator(apm_config);
  generator.StartRecording();
  generator.Process(100);
  generator.StopRecording();

  DebugDumpReplayer debug_dump_replayer_;

  ASSERT_TRUE(debug_dump_replayer_.SetDumpFile(generator.dump_file_name()));

  while (const std::optional<audioproc::Event> event =
             debug_dump_replayer_.GetNextEvent()) {
    debug_dump_replayer_.RunNextEvent();
    if (event->type() == audioproc::Event::CONFIG) {
      const audioproc::Config* msg = &event->config();
      ASSERT_TRUE(msg->has_experiments_description());
      EXPECT_PRED_FORMAT2(::testing::IsSubstring, "EchoController",
                          msg->experiments_description().c_str());
    }
  }
}

TEST_F(DebugDumpTest, VerifyEmptyExperimentalString) {
  DebugDumpGenerator generator(/*apm_config=*/{});
  generator.StartRecording();
  generator.Process(100);
  generator.StopRecording();

  DebugDumpReplayer debug_dump_replayer_;

  ASSERT_TRUE(debug_dump_replayer_.SetDumpFile(generator.dump_file_name()));

  while (const std::optional<audioproc::Event> event =
             debug_dump_replayer_.GetNextEvent()) {
    debug_dump_replayer_.RunNextEvent();
    if (event->type() == audioproc::Event::CONFIG) {
      const audioproc::Config* msg = &event->config();
      ASSERT_TRUE(msg->has_experiments_description());
      EXPECT_EQ(0u, msg->experiments_description().size());
    }
  }
}

// AGC is not supported on Android or iOS.
#if defined(WEBRTC_ANDROID) || defined(WEBRTC_IOS)
#define MAYBE_ToggleAgc DISABLED_ToggleAgc
#else
#define MAYBE_ToggleAgc ToggleAgc
#endif
TEST_F(DebugDumpTest, MAYBE_ToggleAgc) {
  DebugDumpGenerator generator(/*apm_config=*/{});
  generator.StartRecording();
  generator.Process(100);

  AudioProcessing::Config apm_config = generator.apm()->GetConfig();
  apm_config.gain_controller1.enabled = !apm_config.gain_controller1.enabled;
  generator.apm()->ApplyConfig(apm_config);

  generator.Process(100);
  generator.StopRecording();
  VerifyDebugDump(generator.dump_file_name());
}

TEST_F(DebugDumpTest, ToggleNs) {
  DebugDumpGenerator generator(/*apm_config=*/{});
  generator.StartRecording();
  generator.Process(100);

  AudioProcessing::Config apm_config = generator.apm()->GetConfig();
  apm_config.noise_suppression.enabled = !apm_config.noise_suppression.enabled;
  generator.apm()->ApplyConfig(apm_config);

  generator.Process(100);
  generator.StopRecording();
  VerifyDebugDump(generator.dump_file_name());
}

TEST_F(DebugDumpTest, TransientSuppressionOn) {
  DebugDumpGenerator generator(/*apm_config=*/{});

  AudioProcessing::Config apm_config = generator.apm()->GetConfig();
  apm_config.transient_suppression.enabled = true;
  generator.apm()->ApplyConfig(apm_config);

  generator.StartRecording();
  generator.Process(100);
  generator.StopRecording();
  VerifyDebugDump(generator.dump_file_name());
}

TEST_F(DebugDumpTest, PreAmplifierIsOn) {
  AudioProcessing::Config apm_config;
  apm_config.pre_amplifier.enabled = true;
  DebugDumpGenerator generator(apm_config);
  generator.StartRecording();
  generator.Process(100);
  generator.StopRecording();
  VerifyDebugDump(generator.dump_file_name());
}

}  // namespace test
}  // namespace webrtc
