/*
 *  Copyright (c) 2016 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.
 */

#ifndef MODULES_AUDIO_PROCESSING_TEST_AUDIO_PROCESSING_SIMULATOR_H_
#define MODULES_AUDIO_PROCESSING_TEST_AUDIO_PROCESSING_SIMULATOR_H_

#include <algorithm>
#include <fstream>
#include <limits>
#include <memory>
#include <string>

#include "api/optional.h"
#include "common_audio/channel_buffer.h"
#include "modules/audio_processing/include/audio_processing.h"
#include "modules/audio_processing/test/fake_recording_device.h"
#include "modules/audio_processing/test/test_utils.h"
#include "rtc_base/constructormagic.h"
#include "rtc_base/task_queue.h"
#include "rtc_base/timeutils.h"

namespace webrtc {
namespace test {

// Holds all the parameters available for controlling the simulation.
struct SimulationSettings {
  SimulationSettings();
  SimulationSettings(const SimulationSettings&);
  ~SimulationSettings();
  rtc::Optional<int> stream_delay;
  rtc::Optional<bool> use_stream_delay;
  rtc::Optional<int> stream_drift_samples;
  rtc::Optional<int> output_sample_rate_hz;
  rtc::Optional<int> output_num_channels;
  rtc::Optional<int> reverse_output_sample_rate_hz;
  rtc::Optional<int> reverse_output_num_channels;
  rtc::Optional<std::string> output_filename;
  rtc::Optional<std::string> reverse_output_filename;
  rtc::Optional<std::string> input_filename;
  rtc::Optional<std::string> reverse_input_filename;
  rtc::Optional<std::string> artificial_nearend_filename;
  rtc::Optional<bool> use_aec;
  rtc::Optional<bool> use_aecm;
  rtc::Optional<bool> use_ed;  // Residual Echo Detector.
  rtc::Optional<std::string> ed_graph_output_filename;
  rtc::Optional<bool> use_agc;
  rtc::Optional<bool> use_agc2;
  rtc::Optional<bool> use_pre_amplifier;
  rtc::Optional<bool> use_hpf;
  rtc::Optional<bool> use_ns;
  rtc::Optional<bool> use_ts;
  rtc::Optional<bool> use_bf;
  rtc::Optional<bool> use_ie;
  rtc::Optional<bool> use_vad;
  rtc::Optional<bool> use_le;
  rtc::Optional<bool> use_all;
  rtc::Optional<int> aec_suppression_level;
  rtc::Optional<bool> use_delay_agnostic;
  rtc::Optional<bool> use_extended_filter;
  rtc::Optional<bool> use_drift_compensation;
  rtc::Optional<bool> use_aec3;
  rtc::Optional<bool> use_experimental_agc;
  rtc::Optional<int> aecm_routing_mode;
  rtc::Optional<bool> use_aecm_comfort_noise;
  rtc::Optional<int> agc_mode;
  rtc::Optional<int> agc_target_level;
  rtc::Optional<bool> use_agc_limiter;
  rtc::Optional<int> agc_compression_gain;
  float agc2_fixed_gain_db;
  float pre_amplifier_gain_factor;
  rtc::Optional<int> vad_likelihood;
  rtc::Optional<int> ns_level;
  rtc::Optional<bool> use_refined_adaptive_filter;
  int initial_mic_level;
  bool simulate_mic_gain = false;
  rtc::Optional<int> simulated_mic_kind;
  bool report_performance = false;
  bool report_bitexactness = false;
  bool use_verbose_logging = false;
  bool discard_all_settings_in_aecdump = true;
  rtc::Optional<std::string> aec_dump_input_filename;
  rtc::Optional<std::string> aec_dump_output_filename;
  bool fixed_interface = false;
  bool store_intermediate_output = false;
  rtc::Optional<std::string> custom_call_order_filename;
  rtc::Optional<std::string> aec3_settings_filename;
};

// Holds a few statistics about a series of TickIntervals.
struct TickIntervalStats {
  TickIntervalStats() : min(std::numeric_limits<int64_t>::max()) {}
  int64_t sum;
  int64_t max;
  int64_t min;
};

// Copies samples present in a ChannelBuffer into an AudioFrame.
void CopyToAudioFrame(const ChannelBuffer<float>& src, AudioFrame* dest);

// Provides common functionality for performing audioprocessing simulations.
class AudioProcessingSimulator {
 public:
  static const int kChunksPerSecond = 1000 / AudioProcessing::kChunkSizeMs;

  AudioProcessingSimulator(const SimulationSettings& settings,
                           std::unique_ptr<AudioProcessingBuilder> ap_builder);
  virtual ~AudioProcessingSimulator();

  // Processes the data in the input.
  virtual void Process() = 0;

  // Returns the execution time of all AudioProcessing calls.
  const TickIntervalStats& proc_time() const { return proc_time_; }

  // Reports whether the processed recording was bitexact.
  bool OutputWasBitexact() { return bitexact_output_; }

  size_t get_num_process_stream_calls() { return num_process_stream_calls_; }
  size_t get_num_reverse_process_stream_calls() {
    return num_reverse_process_stream_calls_;
  }

 protected:
  // RAII class for execution time measurement. Updates the provided
  // TickIntervalStats based on the time between ScopedTimer creation and
  // leaving the enclosing scope.
  class ScopedTimer {
   public:
    explicit ScopedTimer(TickIntervalStats* proc_time)
        : proc_time_(proc_time), start_time_(rtc::TimeNanos()) {}

    ~ScopedTimer();

   private:
    TickIntervalStats* const proc_time_;
    int64_t start_time_;
  };

  TickIntervalStats* mutable_proc_time() { return &proc_time_; }
  void ProcessStream(bool fixed_interface);
  void ProcessReverseStream(bool fixed_interface);
  void CreateAudioProcessor();
  void DestroyAudioProcessor();
  void SetupBuffersConfigsOutputs(int input_sample_rate_hz,
                                  int output_sample_rate_hz,
                                  int reverse_input_sample_rate_hz,
                                  int reverse_output_sample_rate_hz,
                                  int input_num_channels,
                                  int output_num_channels,
                                  int reverse_input_num_channels,
                                  int reverse_output_num_channels);

  const SimulationSettings settings_;
  std::unique_ptr<AudioProcessing> ap_;
  std::unique_ptr<AudioProcessingBuilder> ap_builder_;

  std::unique_ptr<ChannelBuffer<float>> in_buf_;
  std::unique_ptr<ChannelBuffer<float>> out_buf_;
  std::unique_ptr<ChannelBuffer<float>> reverse_in_buf_;
  std::unique_ptr<ChannelBuffer<float>> reverse_out_buf_;
  StreamConfig in_config_;
  StreamConfig out_config_;
  StreamConfig reverse_in_config_;
  StreamConfig reverse_out_config_;
  std::unique_ptr<ChannelBufferWavReader> buffer_reader_;
  std::unique_ptr<ChannelBufferWavReader> reverse_buffer_reader_;
  AudioFrame rev_frame_;
  AudioFrame fwd_frame_;
  bool bitexact_output_ = true;
  int aec_dump_mic_level_ = 0;

 private:
  void SetupOutput();

  size_t num_process_stream_calls_ = 0;
  size_t num_reverse_process_stream_calls_ = 0;
  size_t output_reset_counter_ = 0;
  std::unique_ptr<ChannelBufferWavWriter> buffer_writer_;
  std::unique_ptr<ChannelBufferWavWriter> reverse_buffer_writer_;
  TickIntervalStats proc_time_;
  std::ofstream residual_echo_likelihood_graph_writer_;
  int analog_mic_level_;
  FakeRecordingDevice fake_recording_device_;

  rtc::TaskQueue worker_queue_;

  RTC_DISALLOW_IMPLICIT_CONSTRUCTORS(AudioProcessingSimulator);
};

}  // namespace test
}  // namespace webrtc

#endif  // MODULES_AUDIO_PROCESSING_TEST_AUDIO_PROCESSING_SIMULATOR_H_
