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

#include "tas5720.h"

#include <fuchsia/hardware/gpio/cpp/banjo-mock.h>
#include <lib/fake_ddk/fake_ddk.h>
#include <lib/mock-i2c/mock-i2c.h>
#include <lib/simple-codec/simple-codec-client.h>
#include <lib/simple-codec/simple-codec-helper.h>
#include <lib/sync/completion.h>

#include <lib/ddk/metadata.h>
#include <zxtest/zxtest.h>

namespace audio {

audio::DaiFormat GetDefaultDaiFormat() {
  return {
      .number_of_channels = 2,
      .channels_to_use_bitmask = 1,  // Use one channel in this mono codec.
      .sample_format = SampleFormat::PCM_SIGNED,
      .frame_format = FrameFormat::STEREO_LEFT,
      .frame_rate = 24'000,
      .bits_per_slot = 32,
      .bits_per_sample = 16,
  };
}

class Tas5720Test : public zxtest::Test {
 public:
  void SetUp() override {
    // Reset by the TAS driver initialization.
    mock_i2c_.ExpectWrite({0x01})
        .ExpectReadStop({0xff})
        .ExpectWriteStop({0x01, 0xfe})  // Enter shutdown (part of reset).
        .ExpectWrite({0x01})
        .ExpectReadStop({0xfe})
        .ExpectWriteStop({0x01, 0xff})  // Exit shutdown (part of reset).
        .ExpectWrite({0x01})
        .ExpectReadStop({0xff})
        .ExpectWriteStop({0x01, 0xfe})  // Enter shutdown (part of stop).
        .ExpectWriteStop({0x02, 0x45})  // Digital control defaults. Left justified.
        .ExpectWriteStop({0x03, 0x10})  // Digital control defaults. Slot 0, muted.
        .ExpectWriteStop({0x06, 0x5d})  // Analog defaults.
        .ExpectWriteStop({0x10, 0xff})  // clippers disabled.
        .ExpectWriteStop({0x11, 0xfc})  // clippers disabled.
        .ExpectWrite({0x01})
        .ExpectReadStop({0xfe})
        .ExpectWriteStop({0x01, 0xff})  // exit shutdown (part of start).
        .ExpectWriteStop({0x06, 0x51})  // Default gain.
        .ExpectWriteStop({0x04, 0xa1})  // Default gain.
        .ExpectWrite({0x03})
        .ExpectReadStop({0x00})
        .ExpectWriteStop({0x03, 0x10});  // Muted.
  }
  mock_i2c::MockI2c mock_i2c_;
};

struct Tas5720Codec : public Tas5720 {
  explicit Tas5720Codec(ddk::I2cChannel i2c) : Tas5720(fake_ddk::kFakeParent, std::move(i2c)) {}
  codec_protocol_t GetProto() { return {&this->codec_protocol_ops_, this}; }
};

TEST_F(Tas5720Test, CodecInitGood) {
  fake_ddk::Bind tester;
  uint32_t instance_count = 0;
  tester.SetMetadata(DEVICE_METADATA_PRIVATE, &instance_count, sizeof(instance_count));
  auto codec = SimpleCodecServer::Create<Tas5720Codec>(mock_i2c_.GetProto());
  ASSERT_NOT_NULL(codec);
  auto codec_proto = codec->GetProto();
  SimpleCodecClient client;
  client.SetProtocol(&codec_proto);

  // Shutdown.
  mock_i2c_.ExpectWrite({0x01}).ExpectReadStop({0xff}).ExpectWriteStop({0x01, 0xfe});

  codec->DdkAsyncRemove();
  ASSERT_TRUE(tester.Ok());
  codec.release()->DdkRelease();  // codec release managed by the DDK
  mock_i2c_.VerifyAndClear();
}

TEST(Tas5720Test, CodecInitBad) {
  fake_ddk::Bind tester;
  uint32_t instance_count = 0;
  tester.SetMetadata(DEVICE_METADATA_PRIVATE, &instance_count, sizeof(instance_count));

  mock_i2c::MockI2c mock_i2c;
  // Bad replies (2 retries) to enter shutdown (part of reset).
  mock_i2c.ExpectWrite({0x01}).ExpectReadStop({0xff}, ZX_ERR_TIMED_OUT);
  mock_i2c.ExpectWrite({0x01}).ExpectReadStop({0xff}, ZX_ERR_TIMED_OUT);  // Retry 1.
  mock_i2c.ExpectWrite({0x01}).ExpectReadStop({0xff}, ZX_ERR_TIMED_OUT);  // Retry 2.
  // Bad replies (2 retries) to enter shutdown (part of shutdown becuase init failed).
  mock_i2c.ExpectWrite({0x01}).ExpectReadStop({0xff}, ZX_ERR_TIMED_OUT);
  mock_i2c.ExpectWrite({0x01}).ExpectReadStop({0xff}, ZX_ERR_TIMED_OUT);  // Retry 1.
  mock_i2c.ExpectWrite({0x01}).ExpectReadStop({0xff}, ZX_ERR_TIMED_OUT);  // Retry 2.

  auto codec = SimpleCodecServer::Create<Tas5720Codec>(mock_i2c.GetProto());
  ASSERT_NULL(codec);
  mock_i2c.VerifyAndClear();
}

TEST_F(Tas5720Test, CodecGetInfo) {
  fake_ddk::Bind tester;
  uint32_t instance_count = 0;
  tester.SetMetadata(DEVICE_METADATA_PRIVATE, &instance_count, sizeof(instance_count));
  auto codec = SimpleCodecServer::Create<Tas5720Codec>(mock_i2c_.GetProto());
  ASSERT_NOT_NULL(codec);
  auto codec_proto = codec->GetProto();
  SimpleCodecClient client;
  client.SetProtocol(&codec_proto);

  auto info = client.GetInfo();
  ASSERT_EQ(info->unique_id.compare(""), 0);
  ASSERT_EQ(info->manufacturer.compare("Texas Instruments"), 0);
  ASSERT_EQ(info->product_name.compare("TAS5720"), 0);

  // Shutdown.
  mock_i2c_.ExpectWrite({0x01}).ExpectReadStop({0xff}).ExpectWriteStop({0x01, 0xfe});

  codec->DdkAsyncRemove();
  ASSERT_TRUE(tester.Ok());
  codec.release()->DdkRelease();  // codec release managed by the DDK
  mock_i2c_.VerifyAndClear();
}

TEST_F(Tas5720Test, CodecReset) {
  fake_ddk::Bind tester;
  uint32_t instance_count = 0;
  tester.SetMetadata(DEVICE_METADATA_PRIVATE, &instance_count, sizeof(instance_count));

  // We complete all i2c mock setup before executing server methods in a different thread.
  // Reset by the call to Reset.
  mock_i2c_.ExpectWrite({0x01})
      .ExpectReadStop({0xff})
      .ExpectWriteStop({0x01, 0xfe})  // Enter shutdown (part of reset).
      .ExpectWrite({0x01})
      .ExpectReadStop({0xfe})
      .ExpectWriteStop({0x01, 0xff})  // Exit shutdown (part of reset).
      .ExpectWrite({0x01})
      .ExpectReadStop({0xff})
      .ExpectWriteStop({0x01, 0xfe})  // Enter shutdown (part of stop).
      .ExpectWriteStop({0x02, 0x45})  // Digital control defaults. TODO set I2S.
      .ExpectWriteStop({0x03, 0x10})  // Digital control defaults. Slot 0, muted.
      .ExpectWriteStop({0x06, 0x5d})  // Analog defaults.
      .ExpectWriteStop({0x10, 0xff})  // clippers disabled.
      .ExpectWriteStop({0x11, 0xfc})  // clippers disabled.
      .ExpectWrite({0x01})
      .ExpectReadStop({0xfe})
      .ExpectWriteStop({0x01, 0xff})  // exit shutdown (part of start).
      .ExpectWriteStop({0x06, 0x51})  // Default gain.
      .ExpectWriteStop({0x04, 0xa1})  // Default gain.
      .ExpectWrite({0x03})
      .ExpectReadStop({0x00})
      .ExpectWriteStop({0x03, 0x10});  // Muted.

  mock_i2c_.ExpectWrite({0x01}).ExpectReadStop({0xff}).ExpectWriteStop({0x01, 0xfe});  // Shutdown.

  auto codec = SimpleCodecServer::Create<Tas5720Codec>(mock_i2c_.GetProto());
  ASSERT_NOT_NULL(codec);
  auto codec_proto = codec->GetProto();
  SimpleCodecClient client;
  client.SetProtocol(&codec_proto);
  ASSERT_OK(client.Reset());

  codec->DdkAsyncRemove();
  ASSERT_TRUE(tester.Ok());
  codec.release()->DdkRelease();  // codec release managed by the DDK
  mock_i2c_.VerifyAndClear();
}

TEST_F(Tas5720Test, CodecBridgedMode) {
  fake_ddk::Bind tester;
  uint32_t instance_count = 0;
  tester.SetMetadata(DEVICE_METADATA_PRIVATE, &instance_count, sizeof(instance_count));

  auto codec = SimpleCodecServer::Create<Tas5720Codec>(mock_i2c_.GetProto());
  ASSERT_NOT_NULL(codec);
  auto codec_proto = codec->GetProto();
  SimpleCodecClient client;
  client.SetProtocol(&codec_proto);
  {
    auto bridgeable = client.IsBridgeable();
    ASSERT_FALSE(bridgeable.value());
  }
  { client.SetBridgedMode(false); }

  // Shutdown.
  mock_i2c_.ExpectWrite({0x01}).ExpectReadStop({0xff}).ExpectWriteStop({0x01, 0xfe});

  codec->DdkAsyncRemove();
  ASSERT_TRUE(tester.Ok());
  codec.release()->DdkRelease();  // codec release managed by the DDK
  mock_i2c_.VerifyAndClear();
}

TEST_F(Tas5720Test, CodecDaiFormat) {
  fake_ddk::Bind tester;
  uint32_t instance_count = 0;
  tester.SetMetadata(DEVICE_METADATA_PRIVATE, &instance_count, sizeof(instance_count));
  auto codec = SimpleCodecServer::Create<Tas5720Codec>(mock_i2c_.GetProto());
  ASSERT_NOT_NULL(codec);
  auto codec_proto = codec->GetProto();
  SimpleCodecClient client;
  client.SetProtocol(&codec_proto);

  // We complete all i2c mock setup before executing server methods in a different thread.
  mock_i2c_.ExpectWrite({0x03}).ExpectReadStop({0xff});
  mock_i2c_.ExpectWriteStop({0x03, 0xfc});  // Set slot to 0.
  mock_i2c_.ExpectWriteStop({0x02, 0x45});  // Set rate to 48kHz.

  mock_i2c_.ExpectWrite({0x03}).ExpectReadStop({0xff});
  mock_i2c_.ExpectWriteStop({0x03, 0xfc});  // Set slot to 0.
  mock_i2c_.ExpectWriteStop({0x02, 0x4d});  // Set rate to 96kHz.

  mock_i2c_.ExpectWrite({0x03}).ExpectReadStop({0xff});
  mock_i2c_.ExpectWriteStop({0x03, 0xfc});  // Set slot to 0.

  mock_i2c_.ExpectWrite({0x01}).ExpectReadStop({0xff}).ExpectWriteStop({0x01, 0xfe});  // Shutdown.

  // Check getting DAI formats.
  {
    auto formats = client.GetDaiFormats();
    ASSERT_EQ(formats.value().number_of_channels.size(), 1);
    ASSERT_EQ(formats.value().number_of_channels[0], 2);
    ASSERT_EQ(formats.value().sample_formats.size(), 1);
    ASSERT_EQ(formats.value().sample_formats[0], SampleFormat::PCM_SIGNED);
    ASSERT_EQ(formats.value().frame_formats.size(), 2);
    ASSERT_EQ(formats.value().frame_formats[0], FrameFormat::STEREO_LEFT);
    ASSERT_EQ(formats.value().frame_formats[1], FrameFormat::I2S);
    ASSERT_EQ(formats.value().frame_rates.size(), 2);
    ASSERT_EQ(formats.value().frame_rates[0], 48000);
    ASSERT_EQ(formats.value().frame_rates[1], 96000);
    ASSERT_EQ(formats.value().bits_per_slot.size(), 1);
    ASSERT_EQ(formats.value().bits_per_slot[0], 32);
    ASSERT_EQ(formats.value().bits_per_sample.size(), 1);
    ASSERT_EQ(formats.value().bits_per_sample[0], 16);
  }

  // Check setting DAI formats.
  {
    DaiFormat format = GetDefaultDaiFormat();
    format.frame_rate = 48'000;
    auto formats = client.GetDaiFormats();
    ASSERT_TRUE(IsDaiFormatSupported(format, formats.value()));
    ASSERT_OK(client.SetDaiFormat(std::move(format)));
  }

  {
    DaiFormat format = GetDefaultDaiFormat();
    format.frame_rate = 96'000;
    auto formats = client.GetDaiFormats();
    ASSERT_TRUE(IsDaiFormatSupported(format, formats.value()));
    ASSERT_OK(client.SetDaiFormat(std::move(format)));
  }

  {
    DaiFormat format = GetDefaultDaiFormat();
    format.frame_rate = 192'000;
    auto formats = client.GetDaiFormats();
    ASSERT_FALSE(IsDaiFormatSupported(format, formats.value()));
    ASSERT_NOT_OK(client.SetDaiFormat(std::move(format)));
  }

  codec->DdkAsyncRemove();
  ASSERT_TRUE(tester.Ok());
  codec.release()->DdkRelease();  // codec release managed by the DDK
  mock_i2c_.VerifyAndClear();
}

TEST_F(Tas5720Test, CodecGain) {
  fake_ddk::Bind tester;
  uint32_t instance_count = 0;
  tester.SetMetadata(DEVICE_METADATA_PRIVATE, &instance_count, sizeof(instance_count));
  auto codec = SimpleCodecServer::Create<Tas5720Codec>(mock_i2c_.GetProto());
  ASSERT_NOT_NULL(codec);
  auto codec_proto = codec->GetProto();
  SimpleCodecClient client;
  client.SetProtocol(&codec_proto);

  mock_i2c_
      .ExpectWriteStop({0x06, 0x51})  // Analog 19.2dBV.
      .ExpectWriteStop({0x04, 0x9d})  // Digital -32dB.
      .ExpectWrite({0x03})
      .ExpectReadStop({0xff})
      .ExpectWriteStop({0x03, 0xef});  // Not muted.

  // Lower than min gain.
  mock_i2c_
      .ExpectWriteStop({0x06, 0x51})  // Analog 19.2dBV (min)
      .ExpectWriteStop({0x04, 0x00})  // Digital -110.6dB.
      .ExpectWrite({0x03})
      .ExpectReadStop({0xff})
      .ExpectWriteStop({0x03, 0xef});  // Not muted.

  // Higher than max gain.
  mock_i2c_
      .ExpectWriteStop({0x06, 0x5d})  // Analog 23.5dBV (max).
      .ExpectWriteStop({0x04, 0xff})  // Digital +24dB.
      .ExpectWrite({0x03})
      .ExpectReadStop({0xff})
      .ExpectWriteStop({0x03, 0xef});  // Not muted.

  mock_i2c_.ExpectWrite({0x01}).ExpectReadStop({0xff}).ExpectWriteStop({0x01, 0xfe});  // Shutdown.

  client.SetGainState({
      .gain = -32.f,
      .muted = false,
      .agc_enabled = false,
  });
  client.SetGainState({
      .gain = -999.f,
      .muted = false,
      .agc_enabled = false,
  });
  client.SetGainState({
      .gain = 111.f,
      .muted = false,
      .agc_enabled = false,
  });

  // Make a 2-wal call to make sure the server (we know single threaded) completed previous calls.
  auto unused = client.GetInfo();
  static_cast<void>(unused);

  codec->DdkAsyncRemove();
  ASSERT_TRUE(tester.Ok());       // Guarantees Unbind called so we can test for shutdown.
  codec.release()->DdkRelease();  // codec release managed by the DDK.
  mock_i2c_.VerifyAndClear();
}

TEST_F(Tas5720Test, CodecPlugState) {
  fake_ddk::Bind tester;
  uint32_t instance_count = 0;
  tester.SetMetadata(DEVICE_METADATA_PRIVATE, &instance_count, sizeof(instance_count));
  auto codec = SimpleCodecServer::Create<Tas5720Codec>(mock_i2c_.GetProto());
  ASSERT_NOT_NULL(codec);
  auto codec_proto = codec->GetProto();
  SimpleCodecClient client;
  client.SetProtocol(&codec_proto);

  // Shutdown.
  mock_i2c_.ExpectWrite({0x01}).ExpectReadStop({0xff}).ExpectWriteStop({0x01, 0xfe});

  codec->DdkAsyncRemove();
  ASSERT_TRUE(tester.Ok());
  codec.release()->DdkRelease();  // codec release managed by the DDK
  mock_i2c_.VerifyAndClear();
}

TEST(Tas5720Test, InstanceCount) {
  fake_ddk::Bind tester;
  uint32_t instance_count = 2;
  tester.SetMetadata(DEVICE_METADATA_PRIVATE, &instance_count, sizeof(instance_count));

  mock_i2c::MockI2c mock_i2c;

  // Reset by the TAS driver initialization setting slot to 2.
  mock_i2c.ExpectWrite({0x01})
      .ExpectReadStop({0xff})
      .ExpectWriteStop({0x01, 0xfe})  // Enter shutdown (part of reset).
      .ExpectWrite({0x01})
      .ExpectReadStop({0xfe})
      .ExpectWriteStop({0x01, 0xff})  // Exit shutdown (part of reset).
      .ExpectWrite({0x01})
      .ExpectReadStop({0xff})
      .ExpectWriteStop({0x01, 0xfe})  // Enter shutdown (part of stop).
      .ExpectWriteStop({0x02, 0x45})  // Digital control defaults. TODO set I2S.
      .ExpectWriteStop({0x03, 0x10})  // Digital control defaults. Slot 2, muted.
      .ExpectWriteStop({0x06, 0x5d})  // Analog defaults.
      .ExpectWriteStop({0x10, 0xff})  // clippers disabled.
      .ExpectWriteStop({0x11, 0xfc})  // clippers disabled.
      .ExpectWrite({0x01})
      .ExpectReadStop({0xfe})
      .ExpectWriteStop({0x01, 0xff})  // exit shutdown (part of start).
      .ExpectWriteStop({0x06, 0x51})  // Default gain.
      .ExpectWriteStop({0x04, 0xa1})  // Default gain.
      .ExpectWrite({0x03})
      .ExpectReadStop({0x00})
      .ExpectWriteStop({0x03, 0x10});  // Muted.

  auto codec = SimpleCodecServer::Create<Tas5720Codec>(mock_i2c.GetProto());
  ASSERT_NOT_NULL(codec);

  // Shutdown.
  mock_i2c.ExpectWrite({0x01}).ExpectReadStop({0xff}).ExpectWriteStop({0x01, 0xfe});

  codec->DdkAsyncRemove();
  ASSERT_TRUE(tester.Ok());
  codec.release()->DdkRelease();  // codec release managed by the DDK
  mock_i2c.VerifyAndClear();
}

}  // namespace audio
