// Copyright (c) 2012 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

// TODO(henrika): add test which included |start_frame| in Consume() call.

#include "media/base/audio_fifo.h"
#include "testing/gtest/include/gtest/gtest.h"

namespace media {

class AudioFifoTest : public testing::Test {
 public:
  AudioFifoTest() {}
  virtual ~AudioFifoTest() {}

  void VerifyValue(const float data[], int size, float value) {
    for (int i = 0; i < size; ++i)
      ASSERT_FLOAT_EQ(value, data[i]) << "i=" << i;
  }

 protected:
  DISALLOW_COPY_AND_ASSIGN(AudioFifoTest);
};

// Verify that construction works as intended.
TEST_F(AudioFifoTest, Construct) {
  static const int kChannels = 6;
  static const int kMaxFrameCount = 128;
  AudioFifo fifo(kChannels, kMaxFrameCount);
  EXPECT_EQ(fifo.frames(), 0);
}

// Pushes audio bus objects to a FIFO and fill it up to different degrees.
TEST_F(AudioFifoTest, Push) {
  static const int kChannels = 2;
  static const int kMaxFrameCount = 128;
  AudioFifo fifo(kChannels, kMaxFrameCount);
  {
    SCOPED_TRACE("Push 50%");
    scoped_ptr<AudioBus> bus = AudioBus::Create(kChannels, kMaxFrameCount / 2);
    EXPECT_EQ(fifo.frames(), 0);
    fifo.Push(bus.get());
    EXPECT_EQ(fifo.frames(), bus->frames());
    fifo.Clear();
  }
  {
    SCOPED_TRACE("Push 100%");
    scoped_ptr<AudioBus> bus = AudioBus::Create(kChannels, kMaxFrameCount);
    EXPECT_EQ(fifo.frames(), 0);
    fifo.Push(bus.get());
    EXPECT_EQ(fifo.frames(), bus->frames());
    fifo.Clear();
  }
}

// Consumes audio bus objects from a FIFO and empty it to different degrees.
TEST_F(AudioFifoTest, Consume) {
  static const int kChannels = 2;
  static const int kMaxFrameCount = 128;
  AudioFifo fifo(kChannels, kMaxFrameCount);
  {
    scoped_ptr<AudioBus> bus = AudioBus::Create(kChannels, kMaxFrameCount);
    fifo.Push(bus.get());
    EXPECT_EQ(fifo.frames(), kMaxFrameCount);
  }
  {
    SCOPED_TRACE("Consume 50%");
    scoped_ptr<AudioBus> bus = AudioBus::Create(kChannels, kMaxFrameCount / 2);
    fifo.Consume(bus.get(), 0, bus->frames());
    EXPECT_TRUE(fifo.frames() == bus->frames());
    fifo.Push(bus.get());
    EXPECT_EQ(fifo.frames(), kMaxFrameCount);
  }
  {
    SCOPED_TRACE("Consume 100%");
    scoped_ptr<AudioBus> bus = AudioBus::Create(kChannels, kMaxFrameCount);
    fifo.Consume(bus.get(), 0, bus->frames());
    EXPECT_EQ(fifo.frames(), 0);
    fifo.Push(bus.get());
    EXPECT_EQ(fifo.frames(), kMaxFrameCount);
  }
}

// Verify that the frames() method of the FIFO works as intended while
// appending and removing audio bus elements to/from the FIFO.
TEST_F(AudioFifoTest, FramesInFifo) {
  static const int kChannels = 2;
  static const int kMaxFrameCount = 64;
  AudioFifo fifo(kChannels, kMaxFrameCount);

  // Fill up the FIFO and verify that the size grows as it should while adding
  // one audio frame each time.
  scoped_ptr<AudioBus> bus = AudioBus::Create(kChannels, 1);
  int n = 0;
  while (fifo.frames() < kMaxFrameCount) {
    fifo.Push(bus.get());
    EXPECT_EQ(fifo.frames(), ++n);
  }
  EXPECT_EQ(fifo.frames(), kMaxFrameCount);

  // Empty the FIFO and verify that the size decreases as it should.
  // Reduce the size of the FIFO by one frame each time.
  while (fifo.frames() > 0) {
    fifo.Consume(bus.get(), 0, bus->frames());
    EXPECT_EQ(fifo.frames(), --n);
  }
  EXPECT_EQ(fifo.frames(), 0);

  // Verify that a steady-state size of #frames in the FIFO is maintained
  // during a sequence of Push/Consume calls which involves wrapping. We ensure
  // wrapping by selecting a buffer size which does divides the FIFO size
  // with a remainder of one.
  scoped_ptr<AudioBus> bus2 =
      AudioBus::Create(kChannels, (kMaxFrameCount / 4) - 1);
  const int frames_in_fifo = bus2->frames();
  fifo.Push(bus2.get());
  EXPECT_EQ(fifo.frames(), frames_in_fifo);
  for (int n = 0; n < kMaxFrameCount; ++n) {
    fifo.Push(bus2.get());
    fifo.Consume(bus2.get(), 0, frames_in_fifo);
    EXPECT_EQ(fifo.frames(), frames_in_fifo);
  }
}

// Perform a sequence of Push/Consume calls and verify that the data written
// to the FIFO is correctly retrieved, i.e., that the order is correct and the
// values are correct.
TEST_F(AudioFifoTest, VerifyDataValues) {
  static const int kChannels = 2;
  static const int kFrameCount = 2;
  static const int kFifoFrameCount = 5 * kFrameCount;

  AudioFifo fifo(kChannels, kFifoFrameCount);
  scoped_ptr<AudioBus> bus = AudioBus::Create(kChannels, kFrameCount);
  EXPECT_EQ(fifo.frames(), 0);
  EXPECT_EQ(bus->frames(), kFrameCount);

  // Start by filling up the FIFO with audio frames. The first audio frame
  // will contain all 1's, the second all 2's etc. All channels contain the
  // same value.
  int value = 1;
  while (fifo.frames() < kFifoFrameCount) {
    for (int j = 0; j < bus->channels(); ++j)
      std::fill(bus->channel(j), bus->channel(j) + bus->frames(), value);
    fifo.Push(bus.get());
    EXPECT_EQ(fifo.frames(), bus->frames() * value);
    ++value;
  }

  // FIFO should be full now.
  EXPECT_EQ(fifo.frames(), kFifoFrameCount);

  // Consume all audio frames in the FIFO and verify that the stored values
  // are correct. In this example, we shall read out: 1, 2, 3, 4, 5 in that
  // order. Note that we set |frames_to_consume| to half the size of the bus.
  // It means that we shall read out the same value two times in row.
  value = 1;
  int n = 1;
  const int frames_to_consume = bus->frames() / 2;
  while (fifo.frames() > 0) {
    fifo.Consume(bus.get(), 0, frames_to_consume);
    for (int j = 0; j < bus->channels(); ++j)
      VerifyValue(bus->channel(j), frames_to_consume, value);
    if (n++ % 2 == 0)
      ++value;  // counts 1, 1, 2, 2, 3, 3,...
  }

  // FIFO should be empty now.
  EXPECT_EQ(fifo.frames(), 0);

  // Push one audio bus to the FIFO and fill it with 1's.
  value = 1;
  for (int j = 0; j < bus->channels(); ++j)
    std::fill(bus->channel(j), bus->channel(j) + bus->frames(), value);
  fifo.Push(bus.get());
  EXPECT_EQ(fifo.frames(), bus->frames());

  // Keep calling Consume/Push a few rounds and verify that we read out the
  // correct values. The number of elements shall be fixed (kFrameCount) during
  // this phase.
  for (int i = 0; i < 5 * kFifoFrameCount; i++) {
    fifo.Consume(bus.get(), 0, bus->frames());
    for (int j = 0; j < bus->channels(); ++j) {
      VerifyValue(bus->channel(j), bus->channels(), value);
      std::fill(bus->channel(j), bus->channel(j) + bus->frames(), value + 1);
    }
    fifo.Push(bus.get());
    EXPECT_EQ(fifo.frames(), bus->frames());
    ++value;
  }
}

}  // namespace media
