// 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 "shill/dhcp/dhcp_config.h"

#include <memory>
#include <string>
#include <utility>

#include <base/bind.h>
#include <base/strings/stringprintf.h>
#include <chromeos/dbus/service_constants.h>

#include "shill/dhcp/mock_dhcp_provider.h"
#include "shill/dhcp/mock_dhcp_proxy.h"
#include "shill/event_dispatcher.h"
#include "shill/mock_log.h"
#include "shill/mock_process_manager.h"
#include "shill/property_store_test.h"
#include "shill/testing.h"

using testing::_;
using testing::AnyNumber;
using testing::ByMove;
using testing::ContainsRegex;
using testing::InvokeWithoutArgs;
using testing::Mock;
using testing::Return;

namespace shill {

namespace {
const char kDeviceName[] = "eth0";
const char kDhcpMethod[] = "dhcp";
const char kLeaseFileSuffix[] = "leasefilesuffix";
const bool kHasLeaseSuffix = true;
}  // namespace

class TestDHCPConfig : public DHCPConfig {
 public:
  TestDHCPConfig(ControlInterface* control_interface,
                 EventDispatcher* dispatcher,
                 DHCPProvider* provider,
                 const std::string& device_name,
                 const std::string& type,
                 const std::string& lease_file_suffix)
      : DHCPConfig(control_interface,
                   dispatcher,
                   provider,
                   device_name,
                   type,
                   lease_file_suffix) {}

  ~TestDHCPConfig() override = default;

  void ProcessEventSignal(const std::string& reason,
                          const KeyValueStore& configuration) override {}
  void ProcessStatusChangeSignal(const std::string& status) override {}

  MOCK_METHOD(bool, ShouldFailOnAcquisitionTimeout, (), (override));
  MOCK_METHOD(bool, ShouldKeepLeaseOnDisconnect, (), (override));
};

using TestDHCPConfigRefPtr = scoped_refptr<TestDHCPConfig>;

class DHCPConfigTest : public PropertyStoreTest {
 public:
  DHCPConfigTest()
      : proxy_(new MockDHCPProxy()),
        config_(new TestDHCPConfig(control_interface(),
                                   dispatcher(),
                                   &provider_,
                                   kDeviceName,
                                   kDhcpMethod,
                                   kLeaseFileSuffix)) {}

  void SetUp() override { config_->process_manager_ = &process_manager_; }

  void StopInstance() { config_->Stop("In test"); }

  TestDHCPConfigRefPtr CreateMockMinijailConfig(
      const std::string& lease_suffix);

 protected:
  static const int kPID;

  std::unique_ptr<MockDHCPProxy> proxy_;
  MockProcessManager process_manager_;
  TestDHCPConfigRefPtr config_;
  MockDHCPProvider provider_;
};

const int DHCPConfigTest::kPID = 123456;

TestDHCPConfigRefPtr DHCPConfigTest::CreateMockMinijailConfig(
    const std::string& lease_suffix) {
  TestDHCPConfigRefPtr config(
      new TestDHCPConfig(control_interface(), dispatcher(), &provider_,
                         kDeviceName, kDhcpMethod, lease_suffix));
  config->process_manager_ = &process_manager_;

  return config;
}

TEST_F(DHCPConfigTest, InitProxy) {
  static const char kService[] = ":1.200";
  EXPECT_NE(nullptr, proxy_);
  EXPECT_EQ(nullptr, config_->proxy_);
  EXPECT_CALL(*control_interface(), CreateDHCPProxy(kService))
      .WillOnce(Return(ByMove(std::move(proxy_))));
  config_->InitProxy(kService);
  EXPECT_EQ(nullptr, proxy_);
  EXPECT_NE(nullptr, config_->proxy_);

  config_->InitProxy(kService);
}

TEST_F(DHCPConfigTest, StartFail) {
  EXPECT_CALL(process_manager_,
              StartProcessInMinijail(_, _, _, _, _, _, _, _, _, _))
      .WillOnce(Return(-1));
  EXPECT_FALSE(config_->Start());
  EXPECT_EQ(0, config_->pid_);
}

MATCHER_P(IsDHCPCDArgs, has_lease_suffix, "") {
  if (arg[0] != "-B" || arg[1] != "-q") {
    return false;
  }

  int end_offset = 2;

  std::string device_arg = has_lease_suffix ? std::string(kDeviceName) + "=" +
                                                  std::string(kLeaseFileSuffix)
                                            : kDeviceName;
  return arg[end_offset] == device_arg;
}

TEST_F(DHCPConfigTest, StartWithoutLeaseSuffix) {
  TestDHCPConfigRefPtr config = CreateMockMinijailConfig(kDeviceName);
  EXPECT_CALL(process_manager_,
              StartProcessInMinijail(_, _, IsDHCPCDArgs(!kHasLeaseSuffix), _, _,
                                     _, _, _, _, _))
      .WillOnce(Return(-1));
  EXPECT_FALSE(config->Start());
}

namespace {

class DHCPConfigCallbackTest : public DHCPConfigTest {
 public:
  void SetUp() override {
    DHCPConfigTest::SetUp();
    config_->RegisterUpdateCallback(base::Bind(
        &DHCPConfigCallbackTest::SuccessCallback, base::Unretained(this)));
    config_->RegisterFailureCallback(base::Bind(
        &DHCPConfigCallbackTest::FailureCallback, base::Unretained(this)));
    ip_config_ = config_;
  }

  MOCK_METHOD(void, SuccessCallback, (const IPConfigRefPtr&, bool));
  MOCK_METHOD(void, FailureCallback, (const IPConfigRefPtr&));

  // The mock methods above take IPConfigRefPtr because this is the type
  // that the registered callbacks take.  This conversion of the DHCP
  // config ref pointer eases our work in setting up expectations.
  const IPConfigRefPtr& ConfigRef() { return ip_config_; }

 private:
  IPConfigRefPtr ip_config_;
};

void DoNothing() {}

}  // namespace

TEST_F(DHCPConfigCallbackTest, NotifyFailure) {
  EXPECT_CALL(*this, SuccessCallback(_, _)).Times(0);
  EXPECT_CALL(*this, FailureCallback(ConfigRef()));
  config_->lease_acquisition_timeout_callback_.Reset(base::Bind(&DoNothing));
  config_->lease_expiration_callback_.Reset(base::Bind(&DoNothing));
  config_->NotifyFailure();
  Mock::VerifyAndClearExpectations(this);
  EXPECT_TRUE(config_->properties().address.empty());
  EXPECT_TRUE(config_->lease_acquisition_timeout_callback_.IsCancelled());
  EXPECT_TRUE(config_->lease_expiration_callback_.IsCancelled());
}

TEST_F(DHCPConfigCallbackTest, StoppedDuringFailureCallback) {
  // Stop the DHCP config while it is calling the failure callback.  We
  // need to ensure that no callbacks are left running inadvertently as
  // a result.
  EXPECT_CALL(*this, FailureCallback(ConfigRef()))
      .WillOnce(InvokeWithoutArgs(this, &DHCPConfigTest::StopInstance));
  config_->NotifyFailure();
  EXPECT_TRUE(Mock::VerifyAndClearExpectations(this));
  EXPECT_TRUE(config_->lease_acquisition_timeout_callback_.IsCancelled());
  EXPECT_TRUE(config_->lease_expiration_callback_.IsCancelled());
}

TEST_F(DHCPConfigCallbackTest, StoppedDuringSuccessCallback) {
  IPConfig::Properties properties;
  properties.address = "1.2.3.4";
  properties.lease_duration_seconds = 1;
  // Stop the DHCP config while it is calling the success callback.  This
  // can happen if the device has a static IP configuration and releases
  // the lease after accepting other network parameters from the DHCP
  // IPConfig properties.  We need to ensure that no callbacks are left
  // running inadvertently as a result.
  EXPECT_CALL(*this, SuccessCallback(ConfigRef(), true))
      .WillOnce(InvokeWithoutArgs(this, &DHCPConfigTest::StopInstance));
  config_->UpdateProperties(properties, true);
  EXPECT_TRUE(Mock::VerifyAndClearExpectations(this));
  EXPECT_TRUE(config_->lease_acquisition_timeout_callback_.IsCancelled());
  EXPECT_TRUE(config_->lease_expiration_callback_.IsCancelled());
}

TEST_F(DHCPConfigCallbackTest, ProcessAcquisitionTimeout) {
  // Do not fail on acquisition timeout (e.g. ARP gateway is active).
  EXPECT_CALL(*config_, ShouldFailOnAcquisitionTimeout())
      .WillOnce(Return(false));
  EXPECT_CALL(*this, FailureCallback(_)).Times(0);
  config_->ProcessAcquisitionTimeout();
  Mock::VerifyAndClearExpectations(this);
  Mock::VerifyAndClearExpectations(config_.get());

  // Fail on acquisition timeout.
  EXPECT_CALL(*config_, ShouldFailOnAcquisitionTimeout())
      .WillOnce(Return(true));
  EXPECT_CALL(*this, FailureCallback(_)).Times(1);
  config_->ProcessAcquisitionTimeout();
  Mock::VerifyAndClearExpectations(this);
  Mock::VerifyAndClearExpectations(config_.get());
}

TEST_F(DHCPConfigTest, ReleaseIP) {
  config_->pid_ = 1 << 18;  // Ensure unknown positive PID.
  EXPECT_CALL(*proxy_, Release(kDeviceName)).Times(1);
  config_->proxy_ = std::move(proxy_);
  EXPECT_TRUE(config_->ReleaseIP(IPConfig::kReleaseReasonDisconnect));
  config_->pid_ = 0;
}

TEST_F(DHCPConfigTest, KeepLeaseOnDisconnect) {
  config_->pid_ = 1 << 18;  // Ensure unknown positive PID.

  // Keep lease on disconnect (e.g. ARP gateway is enabled).
  EXPECT_CALL(*config_, ShouldKeepLeaseOnDisconnect()).WillOnce(Return(true));
  EXPECT_CALL(*proxy_, Release(kDeviceName)).Times(0);
  config_->proxy_ = std::move(proxy_);
  EXPECT_TRUE(config_->ReleaseIP(IPConfig::kReleaseReasonDisconnect));
  config_->pid_ = 0;
}

TEST_F(DHCPConfigTest, ReleaseLeaseOnDisconnect) {
  config_->pid_ = 1 << 18;  // Ensure unknown positive PID.

  // Release lease on disconnect.
  EXPECT_CALL(*config_, ShouldKeepLeaseOnDisconnect()).WillOnce(Return(false));
  EXPECT_CALL(*proxy_, Release(kDeviceName)).Times(1);
  config_->proxy_ = std::move(proxy_);
  EXPECT_TRUE(config_->ReleaseIP(IPConfig::kReleaseReasonDisconnect));
  config_->pid_ = 0;
}

TEST_F(DHCPConfigTest, ReleaseIPStaticIPWithLease) {
  config_->pid_ = 1 << 18;  // Ensure unknown positive PID.
  config_->is_lease_active_ = true;
  EXPECT_CALL(*proxy_, Release(kDeviceName));
  config_->proxy_ = std::move(proxy_);
  EXPECT_TRUE(config_->ReleaseIP(IPConfig::kReleaseReasonStaticIP));
  EXPECT_EQ(nullptr, config_->proxy_);
  config_->pid_ = 0;
}

TEST_F(DHCPConfigTest, ReleaseIPStaticIPWithoutLease) {
  config_->pid_ = 1 << 18;  // Ensure unknown positive PID.
  config_->is_lease_active_ = false;
  EXPECT_CALL(*proxy_, Release(kDeviceName)).Times(0);
  MockDHCPProxy* proxy_pointer = proxy_.get();
  config_->proxy_ = std::move(proxy_);
  EXPECT_TRUE(config_->ReleaseIP(IPConfig::kReleaseReasonStaticIP));
  // Expect that proxy has not been released.
  EXPECT_EQ(proxy_pointer, config_->proxy_.get());
  config_->pid_ = 0;
}

TEST_F(DHCPConfigTest, RenewIP) {
  EXPECT_CALL(process_manager_,
              StartProcessInMinijail(_, _, _, _, _, _, _, _, _, _))
      .WillOnce(Return(-1));
  config_->pid_ = 0;
  EXPECT_FALSE(config_->RenewIP());  // Expect a call to Start() if pid_ is 0.
  Mock::VerifyAndClearExpectations(&process_manager_);
  EXPECT_CALL(process_manager_,
              StartProcessInMinijail(_, _, _, _, _, _, _, _, _, _))
      .Times(0);
  EXPECT_TRUE(config_->lease_acquisition_timeout_callback_.IsCancelled());
  config_->lease_expiration_callback_.Reset(base::Bind(&DoNothing));
  config_->pid_ = 456;
  EXPECT_FALSE(config_->RenewIP());  // Expect no crash with NULL proxy.
  EXPECT_CALL(*proxy_, Rebind(kDeviceName)).Times(1);
  config_->proxy_ = std::move(proxy_);
  EXPECT_TRUE(config_->RenewIP());
  EXPECT_FALSE(config_->lease_acquisition_timeout_callback_.IsCancelled());
  EXPECT_TRUE(config_->lease_expiration_callback_.IsCancelled());
  config_->pid_ = 0;
}

TEST_F(DHCPConfigTest, RequestIP) {
  EXPECT_TRUE(config_->lease_acquisition_timeout_callback_.IsCancelled());
  config_->pid_ = 567;
  EXPECT_CALL(*proxy_, Rebind(kDeviceName)).Times(1);
  config_->proxy_ = std::move(proxy_);
  EXPECT_TRUE(config_->RenewIP());
  EXPECT_FALSE(config_->lease_acquisition_timeout_callback_.IsCancelled());
  config_->pid_ = 0;
}

TEST_F(DHCPConfigCallbackTest, RequestIPTimeout) {
  EXPECT_CALL(*config_, ShouldFailOnAcquisitionTimeout())
      .WillOnce(Return(true));
  EXPECT_CALL(*this, SuccessCallback(_, _)).Times(0);
  EXPECT_CALL(*this, FailureCallback(ConfigRef()));
  config_->lease_acquisition_timeout_seconds_ = 0;
  config_->pid_ = 567;
  EXPECT_CALL(*proxy_, Rebind(kDeviceName)).Times(1);
  config_->proxy_ = std::move(proxy_);
  config_->RenewIP();
  config_->dispatcher_->DispatchPendingEvents();
  Mock::VerifyAndClearExpectations(this);
  Mock::VerifyAndClearExpectations(config_.get());
  config_->pid_ = 0;
}

TEST_F(DHCPConfigTest, Restart) {
  const int kPID1 = 1 << 17;  // Ensure unknown positive PID.
  const int kPID2 = 987;
  config_->pid_ = kPID1;
  EXPECT_CALL(provider_, UnbindPID(kPID1));
  EXPECT_CALL(process_manager_, StopProcessAndBlock(kPID1))
      .WillOnce(Return(true));
  EXPECT_CALL(process_manager_,
              StartProcessInMinijail(_, _, _, _, _, _, _, _, _, _))
      .WillOnce(Return(kPID2));
  EXPECT_CALL(provider_, BindPID(kPID2, IsRefPtrTo(config_)));
  EXPECT_TRUE(config_->Restart());
  EXPECT_EQ(kPID2, config_->pid_);
  config_->pid_ = 0;
}

TEST_F(DHCPConfigTest, RestartNoClient) {
  const int kPID = 777;
  EXPECT_CALL(process_manager_, StopProcessAndBlock(_)).Times(0);
  EXPECT_CALL(process_manager_,
              StartProcessInMinijail(_, _, _, _, _, _, _, _, _, _))
      .WillOnce(Return(kPID));
  EXPECT_CALL(provider_, BindPID(kPID, IsRefPtrTo(config_)));
  EXPECT_TRUE(config_->Restart());
  EXPECT_EQ(kPID, config_->pid_);
  config_->pid_ = 0;
}

TEST_F(DHCPConfigCallbackTest, StartTimeout) {
  EXPECT_CALL(*config_, ShouldFailOnAcquisitionTimeout())
      .WillOnce(Return(true));
  EXPECT_CALL(*this, SuccessCallback(_, _)).Times(0);
  EXPECT_CALL(*this, FailureCallback(ConfigRef()));
  config_->lease_acquisition_timeout_seconds_ = 0;
  config_->proxy_ = std::move(proxy_);
  EXPECT_CALL(process_manager_,
              StartProcessInMinijail(_, _, _, _, _, _, _, _, _, _))
      .WillOnce(Return(0));
  config_->Start();
  config_->dispatcher_->DispatchPendingEvents();
  Mock::VerifyAndClearExpectations(this);
  Mock::VerifyAndClearExpectations(config_.get());
}

TEST_F(DHCPConfigTest, Stop) {
  const int kPID = 1 << 17;  // Ensure unknown positive PID.
  ScopedMockLog log;
  EXPECT_CALL(log, Log(_, _, _)).Times(AnyNumber());
  EXPECT_CALL(
      log,
      Log(_, _, ContainsRegex(base::StringPrintf("Stopping.+%s", __func__))));
  config_->pid_ = kPID;
  config_->lease_acquisition_timeout_callback_.Reset(base::Bind(&DoNothing));
  config_->lease_expiration_callback_.Reset(base::Bind(&DoNothing));
  EXPECT_CALL(provider_, UnbindPID(kPID));
  config_->Stop(__func__);
  EXPECT_TRUE(config_->lease_acquisition_timeout_callback_.IsCancelled());
  EXPECT_TRUE(config_->lease_expiration_callback_.IsCancelled());
  EXPECT_FALSE(config_->pid_);
}

TEST_F(DHCPConfigTest, StopDuringRequestIP) {
  config_->pid_ = 567;
  EXPECT_CALL(*proxy_, Rebind(kDeviceName)).Times(1);
  config_->proxy_ = std::move(proxy_);
  EXPECT_TRUE(config_->RenewIP());
  EXPECT_FALSE(config_->lease_acquisition_timeout_callback_.IsCancelled());
  config_->pid_ = 0;  // Keep Stop from killing a real process.
  config_->Stop(__func__);
  EXPECT_TRUE(config_->lease_acquisition_timeout_callback_.IsCancelled());
}

TEST_F(DHCPConfigTest, SetProperty) {
  Error error;
  // Ensure that an attempt to write a R/O property returns InvalidArgs error.
  EXPECT_FALSE(config_->mutable_store()->SetAnyProperty(
      kAddressProperty, PropertyStoreTest::kStringV, &error));
  EXPECT_TRUE(error.IsFailure());
  EXPECT_EQ(Error::kInvalidArguments, error.type());
}

}  // namespace shill
