/*
 *  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 "modules/audio_processing/test/test_utils.h"

#include <algorithm>
#include <cstddef>
#include <cstdint>
#include <cstdio>
#include <cstdlib>
#include <cstring>
#include <memory>
#include <string>
#include <utility>
#include <vector>

#include "absl/strings/string_view.h"
#include "api/audio/audio_view.h"
#include "common_audio/channel_buffer.h"
#include "common_audio/include/audio_util.h"
#include "common_audio/wav_file.h"
#include "rtc_base/checks.h"

namespace webrtc {

void Int16FrameData::CopyFrom(const Int16FrameData& src) {
  sample_rate_hz = src.sample_rate_hz;
  view_ = InterleavedView<int16_t>(data.data(), src.samples_per_channel(),
                                   src.num_channels());
  RTC_CHECK_LE(view_.size(), kMaxDataSizeSamples);
  CopySamples(view_, src.view());
}

bool Int16FrameData::IsEqual(const Int16FrameData& frame) const {
  return samples_per_channel() == frame.samples_per_channel() &&
         num_channels() == num_channels() &&
         memcmp(data.data(), frame.data.data(),
                samples_per_channel() * num_channels() * sizeof(int16_t)) == 0;
}

void Int16FrameData::Scale(float f) {
  std::for_each(data.begin(), data.end(),
                [f](int16_t& sample) { sample = FloatS16ToS16(sample * f); });
}

void Int16FrameData::SetProperties(size_t samples_per_channel,
                                   size_t num_channels) {
  sample_rate_hz = samples_per_channel * 100;
  view_ =
      InterleavedView<int16_t>(data.data(), samples_per_channel, num_channels);
  RTC_CHECK_LE(view_.size(), kMaxDataSizeSamples);
}

void Int16FrameData::set_num_channels(size_t num_channels) {
  view_ = InterleavedView<int16_t>(data.data(), samples_per_channel(),
                                   num_channels);
  RTC_CHECK_LE(view_.size(), kMaxDataSizeSamples);
}

void Int16FrameData::FillData(int16_t value) {
  std::fill(&data[0], &data[size()], value);
}

void Int16FrameData::FillStereoData(int16_t left, int16_t right) {
  RTC_DCHECK_EQ(num_channels(), 2u);
  for (size_t i = 0; i < samples_per_channel() * 2u; i += 2u) {
    data[i] = left;
    data[i + 1] = right;
  }
}

ChannelBufferWavReader::ChannelBufferWavReader(std::unique_ptr<WavReader> file)
    : file_(std::move(file)) {}

ChannelBufferWavReader::~ChannelBufferWavReader() = default;

bool ChannelBufferWavReader::Read(ChannelBuffer<float>* buffer) {
  RTC_CHECK_EQ(file_->num_channels(), buffer->num_channels());
  interleaved_.resize(buffer->size());
  if (file_->ReadSamples(interleaved_.size(), &interleaved_[0]) !=
      interleaved_.size()) {
    return false;
  }

  FloatS16ToFloat(&interleaved_[0], interleaved_.size(), &interleaved_[0]);
  Deinterleave(&interleaved_[0], buffer->num_frames(), buffer->num_channels(),
               buffer->channels());
  return true;
}

ChannelBufferWavWriter::ChannelBufferWavWriter(std::unique_ptr<WavWriter> file)
    : file_(std::move(file)) {}

ChannelBufferWavWriter::~ChannelBufferWavWriter() = default;

void ChannelBufferWavWriter::Write(const ChannelBuffer<float>& buffer) {
  RTC_CHECK_EQ(file_->num_channels(), buffer.num_channels());
  interleaved_.resize(buffer.size());
  InterleavedView<float> view(&interleaved_[0], buffer.num_frames(),
                              buffer.num_channels());
  const float* samples = buffer.channels()[0];
  DeinterleavedView<const float> source(samples, buffer.num_frames(),
                                        buffer.num_channels());
  Interleave(source, view);
  FloatToFloatS16(&interleaved_[0], interleaved_.size(), &interleaved_[0]);
  file_->WriteSamples(&interleaved_[0], interleaved_.size());
}


FILE* OpenFile(absl::string_view filename, absl::string_view mode) {
  std::string filename_str(filename);
  FILE* file = fopen(filename_str.c_str(), std::string(mode).c_str());
  if (!file) {
    printf("Unable to open file %s\n", filename_str.c_str());
    exit(1);
  }
  return file;
}

}  // namespace webrtc
