// Copyright 2018 The Chromium OS 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 "power_manager/powerd/system/audio_client.h"

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

#include <base/bind.h>
#include <base/files/file_util.h>
#include <base/files/scoped_temp_dir.h>
#include <base/macros.h>
#include <base/run_loop.h>
#include <chromeos/dbus/service_constants.h>
#include <gtest/gtest.h>

#include "power_manager/powerd/system/audio_observer.h"
#include "power_manager/powerd/system/dbus_wrapper_stub.h"

namespace power_manager {
namespace system {
namespace {

// Trivial implementation of AudioObserver for unit tests.
class TestObserver : public AudioObserver {
 public:
  explicit TestObserver(AudioClient* client) : client_(client) {
    client_->AddObserver(this);
  }
  TestObserver(const TestObserver&) = delete;
  TestObserver& operator=(const TestObserver&) = delete;

  ~TestObserver() override { client_->RemoveObserver(this); }

  bool audio_active() const { return audio_active_; }
  int num_changes() const { return num_changes_; }

  // AudioObserver:
  void OnAudioStateChange(bool active) override {
    audio_active_ = active;
    num_changes_++;
  }

 private:
  AudioClient* client_;  // Not owned.

  bool audio_active_ = false;
  int num_changes_ = 0;
};

}  // namespace

class AudioClientTest : public testing::Test {
 public:
  AudioClientTest() {
    cras_proxy_ = dbus_wrapper_.GetObjectProxy(cras::kCrasServiceName,
                                               cras::kCrasServicePath);
    dbus_wrapper_.SetMethodCallback(
        base::Bind(&AudioClientTest::HandleMethodCall, base::Unretained(this)));
    CHECK(run_dir_.CreateUniqueTempDir());
    CHECK(run_dir_.IsValid());
  }
  AudioClientTest(const AudioClientTest&) = delete;
  AudioClientTest& operator=(const AudioClientTest&) = delete;

  ~AudioClientTest() override {}

  void Init() { audio_client_.Init(&dbus_wrapper_, run_dir_.GetPath()); }

 protected:
  DBusWrapperStub dbus_wrapper_;
  dbus::ObjectProxy* cras_proxy_ = nullptr;
  AudioClient audio_client_;
  // Run directory passed to |audio_client_|.
  base::ScopedTempDir run_dir_;

  // Number of output streams to report from GetNumberOfActiveOutputStreams.
  int num_output_streams_ = 0;

  // State to return from IsAudioOutputActive.
  bool output_active_ = false;

  // Audio nodes to be returned by GetNodes.
  struct Node {
    std::string type;
    bool active = false;
  };
  std::vector<Node> nodes_;

  // Most recent state set via SetSuspendAudio.
  bool audio_suspended_ = false;

 private:
  // DBusWrapperStub::MethodCallback implementation used to handle D-Bus calls
  // from |audio_client_|.
  std::unique_ptr<dbus::Response> HandleMethodCall(
      dbus::ObjectProxy* proxy, dbus::MethodCall* method_call) {
    if (proxy != cras_proxy_) {
      ADD_FAILURE() << "Unhandled method call to proxy " << proxy;
      return nullptr;
    }
    if (method_call->GetInterface() != cras::kCrasControlInterface) {
      ADD_FAILURE() << "Unhandled method call to interface "
                    << method_call->GetInterface();
      return nullptr;
    }

    std::unique_ptr<dbus::Response> response =
        dbus::Response::FromMethodCall(method_call);
    const std::string member = method_call->GetMember();
    if (member == cras::kGetNodes) {
      WriteNodes(response.get());
    } else if (member == cras::kGetNumberOfActiveOutputStreams) {
      dbus::MessageWriter(response.get()).AppendInt32(num_output_streams_);
    } else if (member == cras::kIsAudioOutputActive) {
      dbus::MessageWriter(response.get()).AppendInt32(output_active_);
    } else if (member == cras::kSetSuspendAudio) {
      if (!dbus::MessageReader(method_call).PopBool(&audio_suspended_))
        ADD_FAILURE() << "Couldn't read " << cras::kSetSuspendAudio << " arg";
    } else {
      ADD_FAILURE() << "Unhandled method call to member " << member;
      return nullptr;
    }
    return response;
  }

  // Helper method for HandleMethodCall() that writes |nodes_| to |response|
  // as an array of dicts mapping from string to variant.
  void WriteNodes(dbus::Response* response) {
    dbus::MessageWriter top_writer(response);
    for (const Node& node : nodes_) {
      // For each node, append a dict to the array.
      dbus::MessageWriter node_writer(nullptr);
      top_writer.OpenArray("{sv}", &node_writer);

      // Write the node type.
      dbus::MessageWriter type_writer(nullptr);
      node_writer.OpenDictEntry(&type_writer);
      type_writer.AppendString(AudioClient::kTypeKey);
      type_writer.AppendVariantOfString(node.type);
      node_writer.CloseContainer(&type_writer);

      // Write the node's active state.
      dbus::MessageWriter active_writer(nullptr);
      node_writer.OpenDictEntry(&active_writer);
      active_writer.AppendString(AudioClient::kActiveKey);
      active_writer.AppendVariantOfBool(node.active);
      node_writer.CloseContainer(&active_writer);

      // Close the node dict.
      top_writer.CloseContainer(&node_writer);
    }
  }
};

TEST_F(AudioClientTest, AudioState) {
  Init();

  // CRAS should be queried when it first becomes available.
  TestObserver observer(&audio_client_);
  num_output_streams_ = 1;
  output_active_ = true;
  dbus_wrapper_.NotifyServiceAvailable(cras_proxy_, true);
  base::RunLoop().RunUntilIdle();
  EXPECT_TRUE(observer.audio_active());
  EXPECT_EQ(1, observer.num_changes());

  // The observer shouldn't be notified if the stream count just increases.
  num_output_streams_ = 2;
  dbus::Signal stream_signal(cras::kCrasControlInterface,
                             cras::kNumberOfActiveStreamsChanged);
  dbus_wrapper_.EmitRegisteredSignal(cras_proxy_, &stream_signal);
  base::RunLoop().RunUntilIdle();
  EXPECT_TRUE(observer.audio_active());
  EXPECT_EQ(1, observer.num_changes());

  // It should hear about audio stopping entirely, though.
  num_output_streams_ = 0;
  dbus_wrapper_.EmitRegisteredSignal(cras_proxy_, &stream_signal);
  base::RunLoop().RunUntilIdle();
  EXPECT_FALSE(observer.audio_active());
  EXPECT_EQ(2, observer.num_changes());

  // The stream count should be requeried if CRAS restarts, too.
  num_output_streams_ = 1;
  dbus_wrapper_.NotifyNameOwnerChanged(cras::kCrasServiceName, "", ":0");
  base::RunLoop().RunUntilIdle();
  EXPECT_TRUE(observer.audio_active());
  EXPECT_EQ(3, observer.num_changes());

  // If a stream is held open but nothing is being written to it, the observer
  // should be told that activity stopped.
  dbus::Signal active_signal(cras::kCrasControlInterface,
                             cras::kAudioOutputActiveStateChanged);
  dbus::MessageWriter(&active_signal).AppendBool(false);
  dbus_wrapper_.EmitRegisteredSignal(cras_proxy_, &active_signal);
  EXPECT_FALSE(observer.audio_active());
  EXPECT_EQ(4, observer.num_changes());
}

TEST_F(AudioClientTest, GetNodes) {
  Init();

  // With no connected nodes, nothing should be reported.
  dbus_wrapper_.NotifyNameOwnerChanged(cras::kCrasServiceName, "", ":0");
  base::RunLoop().RunUntilIdle();
  EXPECT_FALSE(audio_client_.GetHeadphoneJackPlugged());
  EXPECT_FALSE(audio_client_.GetHdmiActive());

  // Ditto for a node of an unknown type.
  nodes_.push_back(Node{"FOO", true});
  dbus::Signal nodes_changed_signal(cras::kCrasControlInterface,
                                    cras::kNodesChanged);
  dbus_wrapper_.EmitRegisteredSignal(cras_proxy_, &nodes_changed_signal);
  base::RunLoop().RunUntilIdle();
  EXPECT_FALSE(audio_client_.GetHeadphoneJackPlugged());
  EXPECT_FALSE(audio_client_.GetHdmiActive());

  // After connecting headphones, they should be reported (even if inactive).
  nodes_.clear();
  nodes_.push_back(Node{AudioClient::kHeadphoneNodeType, false});
  dbus_wrapper_.EmitRegisteredSignal(cras_proxy_, &nodes_changed_signal);
  base::RunLoop().RunUntilIdle();
  EXPECT_TRUE(audio_client_.GetHeadphoneJackPlugged());
  EXPECT_FALSE(audio_client_.GetHdmiActive());

  // An inactive HDMI node shouldn't be reported.
  nodes_[0].active = true;
  nodes_.push_back(Node{AudioClient::kHdmiNodeType, false});
  dbus_wrapper_.EmitRegisteredSignal(cras_proxy_, &nodes_changed_signal);
  base::RunLoop().RunUntilIdle();
  EXPECT_TRUE(audio_client_.GetHeadphoneJackPlugged());
  EXPECT_FALSE(audio_client_.GetHdmiActive());

  // Once the HDMI node becomes active, it should be reported.
  nodes_[0].active = false;
  nodes_[1].active = true;
  dbus::Signal active_node_signal(cras::kCrasControlInterface,
                                  cras::kActiveOutputNodeChanged);
  dbus_wrapper_.EmitRegisteredSignal(cras_proxy_, &active_node_signal);
  base::RunLoop().RunUntilIdle();
  EXPECT_TRUE(audio_client_.GetHeadphoneJackPlugged());
  EXPECT_TRUE(audio_client_.GetHdmiActive());
}

TEST_F(AudioClientTest, SuspendAudio) {
  Init();

  auto audio_suspended_path =
      run_dir_.GetPath().Append(AudioClient::kAudioSuspendedFile);
  EXPECT_FALSE(audio_suspended_);
  EXPECT_FALSE(base::PathExists(audio_suspended_path));
  audio_client_.SetSuspended(true);
  EXPECT_TRUE(audio_suspended_);
  EXPECT_TRUE(base::PathExists(audio_suspended_path));
  audio_client_.SetSuspended(false);
  EXPECT_FALSE(audio_suspended_);
  EXPECT_FALSE(base::PathExists(audio_suspended_path));
}

TEST_F(AudioClientTest, PowerdCrashAfterAudioSuspended) {
  // Create |kAudioSuspendedFile| file in the |run_dir| which indicates the
  // previous run of powerd crashed after suspending audio.
  auto audio_suspended_path =
      run_dir_.GetPath().Append(AudioClient::kAudioSuspendedFile);
  ASSERT_EQ(base::WriteFile(audio_suspended_path, nullptr, 0), 0);
  audio_suspended_ = true;
  // audio_client_ Init() should un-suspend audio if it is suspended.
  Init();
  EXPECT_FALSE(audio_suspended_);
}

}  // namespace system
}  // namespace power_manager
