// Copyright 2020 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 "patchpanel/network_monitor_service.h"

#include <memory>
#include <linux/rtnetlink.h>

#include <base/strings/strcat.h>
#include <base/strings/string_number_conversions.h>
#include <base/test/task_environment.h>
#include <chromeos/dbus/service_constants.h>
#include <gtest/gtest.h>

#include "patchpanel/fake_shill_client.h"
#include "shill/net/mock_rtnl_handler.h"

namespace patchpanel {

namespace {
constexpr int kTestInterfaceIndex = 1;
constexpr char kTestInterfaceName[] = "wlan0";

using ::testing::Eq;

MATCHER(IsNeighborDumpMessage, "") {
  if (!(arg->type() == shill::RTNLMessage::kTypeNeighbor &&
        arg->flags() == NLM_F_REQUEST | NLM_F_DUMP &&
        arg->mode() == shill::RTNLMessage::kModeGet &&
        arg->interface_index() == kTestInterfaceIndex))
    return false;

  return true;
}

MATCHER_P(IsNeighborProbeMessage, address, "") {
  if (!(arg->type() == shill::RTNLMessage::kTypeNeighbor &&
        arg->flags() == NLM_F_REQUEST | NLM_F_REPLACE &&
        arg->mode() == shill::RTNLMessage::kModeAdd &&
        arg->neighbor_status().state == NUD_PROBE &&
        arg->interface_index() == kTestInterfaceIndex &&
        arg->HasAttribute(NDA_DST)))
    return false;

  shill::IPAddress msg_address(arg->family(), arg->GetAttribute(NDA_DST));
  return msg_address == shill::IPAddress(address);
}

// Helper class for testing. Similar to mock class but only allowed one
// expectation set at the same time.
class FakeNeighborConnectedStateChangedHandler {
 public:
  ~FakeNeighborConnectedStateChangedHandler() {
    if (!enabled_)
      return;

    EXPECT_FALSE(expectation_set_)
        << "Expected " << ExpectationToString() << ", but not called.";
  }

  void Enable() { enabled_ = true; }

  void Disable() {
    EXPECT_TRUE(enabled_);
    EXPECT_FALSE(expectation_set_)
        << "Expected " << ExpectationToString() << ", but not called.";
    enabled_ = false;
  }

  void Expect(int ifindex,
              const std::string& ip_addr,
              NeighborLinkMonitor::NeighborRole role,
              bool connected) {
    EXPECT_TRUE(enabled_);
    EXPECT_FALSE(expectation_set_)
        << "Expected " << ExpectationToString() << ", but not called.";
    expectation_set_ = true;
    expected_ifindex_ = ifindex;
    expected_ip_addr_ = ip_addr;
    expected_role_ = role;
    expected_connected_ = connected;
  }

  void Run(int ifindex,
           const shill::IPAddress& ip_addr,
           NeighborLinkMonitor::NeighborRole role,
           bool connected) {
    if (!enabled_)
      return;

    const std::string callback_str =
        CallbackToString(ifindex, ip_addr.ToString(), role, connected);
    EXPECT_TRUE(expectation_set_)
        << callback_str << " called, but not expected.";
    expectation_set_ = false;
    EXPECT_TRUE((expected_ifindex_ == ifindex) &&
                (expected_ip_addr_ == ip_addr.ToString()) &&
                (expected_role_ == role) && (expected_connected_ == connected))
        << "Expected " << ExpectationToString() << ", but got " << callback_str;
  }

 private:
  static std::string CallbackToString(int ifindex,
                                      const std::string& ip_addr,
                                      NeighborLinkMonitor::NeighborRole role,
                                      bool connected) {
    return base::StrCat(
        {"{ ifindex: ", base::NumberToString(ifindex), ", ip_addr: ", ip_addr,
         ", role: ", NeighborLinkMonitor::NeighborRoleToString(role),
         ", connected: ", base::NumberToString(connected), " }"});
  }

  std::string ExpectationToString() {
    return CallbackToString(expected_ifindex_, expected_ip_addr_,
                            expected_role_, expected_connected_);
  }

  bool enabled_ = false;
  bool expectation_set_ = false;
  int expected_ifindex_ = -1;
  std::string expected_ip_addr_;
  NeighborLinkMonitor::NeighborRole expected_role_ =
      NeighborLinkMonitor::NeighborRole::kGateway;
  bool expected_connected_ = false;
};

}  // namespace

class NeighborLinkMonitorTest : public testing::Test {
 protected:
  void SetUp() override {
    mock_rtnl_handler_ = std::make_unique<shill::MockRTNLHandler>();
    callback_ =
        base::BindRepeating(&FakeNeighborConnectedStateChangedHandler::Run,
                            base::Unretained(&fake_neighbor_event_handler_));
    link_monitor_ = std::make_unique<NeighborLinkMonitor>(
        kTestInterfaceIndex, kTestInterfaceName, mock_rtnl_handler_.get(),
        &callback_);
    ExpectAddRTNLListener();
  }

  void TearDown() override {
    // We should make sure |mock_rtnl_handler_| is valid during the life time of
    // |link_monitor_|.
    link_monitor_ = nullptr;
    mock_rtnl_handler_ = nullptr;
    registered_listener_ = nullptr;
  }

  void ExpectAddRTNLListener() {
    EXPECT_CALL(*mock_rtnl_handler_, AddListener(_))
        .WillRepeatedly(::testing::SaveArg<0>(&registered_listener_));
  }

  void NotifyNUDStateChanged(const std::string& addr, uint16_t nud_state) {
    CreateAndSendIncomingRTNLMessage(shill::RTNLMessage::kModeAdd, addr,
                                     nud_state);
  }

  void NotifyNeighborRemoved(const std::string& addr) {
    CreateAndSendIncomingRTNLMessage(shill::RTNLMessage::kModeDelete, addr, 0);
  }

  void CreateAndSendIncomingRTNLMessage(const shill::RTNLMessage::Mode mode,
                                        const std::string& address,
                                        uint16_t nud_state) {
    ASSERT_NE(registered_listener_, nullptr);

    shill::IPAddress addr(address);
    shill::RTNLMessage msg(shill::RTNLMessage::kTypeNeighbor, mode, 0, 0, 0,
                           kTestInterfaceIndex, addr.family());
    msg.SetAttribute(NDA_DST, addr.address());
    if (mode == shill::RTNLMessage::kModeAdd) {
      msg.set_neighbor_status(
          shill::RTNLMessage::NeighborStatus(nud_state, 0, 0));
      msg.SetAttribute(NDA_LLADDR, shill::ByteString(
                                       std::vector<uint8_t>{1, 2, 3, 4, 5, 6}));
    }

    registered_listener_->NotifyEvent(shill::RTNLHandler::kRequestNeighbor,
                                      msg);
  }

  // The internal implementation of Timer uses Now() so we need
  // MOCK_TIME_AND_NOW here.
  base::test::TaskEnvironment task_env_{
#if BASE_VER < 780000
    base::test::TaskEnvironment::TimeSource::MOCK_TIME_AND_NOW
  };
#else
    base::test::TaskEnvironment::TimeSource::MOCK_TIME
  };
#endif
  FakeNeighborConnectedStateChangedHandler fake_neighbor_event_handler_;
  NeighborLinkMonitor::ConnectedStateChangedHandler callback_;
  std::unique_ptr<shill::MockRTNLHandler> mock_rtnl_handler_;
  std::unique_ptr<NeighborLinkMonitor> link_monitor_;
  shill::RTNLListener* registered_listener_ = nullptr;
};

TEST_F(NeighborLinkMonitorTest, SendNeighborDumpMessageOnIPConfigChanged) {
  ShillClient::IPConfig ipconfig;
  ipconfig.ipv4_address = "1.2.3.4";
  ipconfig.ipv4_gateway = "1.2.3.5";
  ipconfig.ipv4_prefix_length = 24;
  ipconfig.ipv4_dns_addresses = {"1.2.3.6"};

  // On ipconfig changed, the link monitor should send only one dump request, to
  // fetch current NUD state of these new addresses.
  EXPECT_CALL(*mock_rtnl_handler_, DoSendMessage(IsNeighborDumpMessage(), _))
      .WillOnce(Return(true));

  link_monitor_->OnIPConfigChanged(ipconfig);
}

TEST_F(NeighborLinkMonitorTest, WatchLinkLocalIPv6DNSServerAddress) {
  ShillClient::IPConfig ipconfig;
  ipconfig.ipv6_address = "2401::1";
  ipconfig.ipv6_prefix_length = 64;
  ipconfig.ipv6_gateway = "fe80::1";
  ipconfig.ipv6_dns_addresses = {"fe80::2"};

  link_monitor_->OnIPConfigChanged(ipconfig);

  EXPECT_CALL(*mock_rtnl_handler_,
              DoSendMessage(IsNeighborProbeMessage("fe80::1"), _))
      .WillOnce(Return(true));
  EXPECT_CALL(*mock_rtnl_handler_,
              DoSendMessage(IsNeighborProbeMessage("fe80::2"), _))
      .WillOnce(Return(true));

  NotifyNUDStateChanged("fe80::1", NUD_REACHABLE);
  NotifyNUDStateChanged("fe80::2", NUD_REACHABLE);
}

TEST_F(NeighborLinkMonitorTest, SendNeighborProbeMessage) {
  // Only the gateway should be in the watching list.
  ShillClient::IPConfig ipconfig;
  ipconfig.ipv4_address = "1.2.3.4";
  ipconfig.ipv4_gateway = "1.2.3.5";
  ipconfig.ipv4_prefix_length = 24;
  link_monitor_->OnIPConfigChanged(ipconfig);

  // Creates a RTNL message about the NUD state of the gateway is NUD_REACHABLE
  // now. A probe message should be sent immediately after we know this address.
  EXPECT_CALL(*mock_rtnl_handler_,
              DoSendMessage(IsNeighborProbeMessage("1.2.3.5"), _))
      .WillOnce(Return(true));
  NotifyNUDStateChanged("1.2.3.5", NUD_REACHABLE);

  // Another probe message should be sent when the timer is triggered.
  EXPECT_CALL(*mock_rtnl_handler_,
              DoSendMessage(IsNeighborProbeMessage("1.2.3.5"), _))
      .WillOnce(Return(true));
  task_env_.FastForwardBy(NeighborLinkMonitor::kActiveProbeInterval);

  // If the state changed to NUD_PROBE, we should not probe this address again
  // when the timer is triggered.
  NotifyNUDStateChanged("1.2.3.5", NUD_PROBE);
  task_env_.FastForwardBy(NeighborLinkMonitor::kActiveProbeInterval);

  // The gateway is removed in the kernel. A dump request should be sent when
  // the timer is triggered.
  NotifyNeighborRemoved("1.2.3.5");
  EXPECT_CALL(*mock_rtnl_handler_, DoSendMessage(IsNeighborDumpMessage(), _))
      .WillOnce(Return(true));
  task_env_.FastForwardBy(NeighborLinkMonitor::kActiveProbeInterval);
}

TEST_F(NeighborLinkMonitorTest, UpdateWatchingEntries) {
  ShillClient::IPConfig ipconfig;
  ipconfig.ipv4_address = "1.2.3.4";
  ipconfig.ipv4_gateway = "1.2.3.5";
  ipconfig.ipv4_dns_addresses = {"1.2.3.6"};
  ipconfig.ipv4_prefix_length = 24;
  link_monitor_->OnIPConfigChanged(ipconfig);

  ipconfig.ipv4_dns_addresses = {"1.2.3.7"};
  // One dump request is expected since there is a new address.
  EXPECT_CALL(*mock_rtnl_handler_, DoSendMessage(IsNeighborDumpMessage(), _))
      .WillOnce(Return(true));
  link_monitor_->OnIPConfigChanged(ipconfig);

  // Updates both addresses to NUD_PROBE (to avoid the link monitor sending a
  // probe request), and then NUD_REACHABLE state.
  NotifyNUDStateChanged("1.2.3.5", NUD_PROBE);
  NotifyNUDStateChanged("1.2.3.5", NUD_REACHABLE);
  NotifyNUDStateChanged("1.2.3.7", NUD_PROBE);
  NotifyNUDStateChanged("1.2.3.7", NUD_REACHABLE);

  // This address is not been watching now. Nothing should happen when a message
  // about it comes.
  NotifyNUDStateChanged("1.2.3.6", NUD_REACHABLE);

  // Nothing should happen within one interval.
  task_env_.FastForwardBy(NeighborLinkMonitor::kActiveProbeInterval / 2);

  // Checks if probe requests sent for both addresses when the timer is
  // triggered.
  EXPECT_CALL(*mock_rtnl_handler_,
              DoSendMessage(IsNeighborProbeMessage("1.2.3.5"), _))
      .WillOnce(Return(true));
  EXPECT_CALL(*mock_rtnl_handler_,
              DoSendMessage(IsNeighborProbeMessage("1.2.3.7"), _))
      .WillOnce(Return(true));
  task_env_.FastForwardBy(NeighborLinkMonitor::kActiveProbeInterval);
}

TEST_F(NeighborLinkMonitorTest, UpdateWatchingEntriesWithSameAddress) {
  ShillClient::IPConfig ipconfig;
  ipconfig.ipv4_address = "1.2.3.4";
  ipconfig.ipv4_gateway = "1.2.3.5";
  ipconfig.ipv4_dns_addresses = {"1.2.3.6"};
  ipconfig.ipv4_prefix_length = 24;
  link_monitor_->OnIPConfigChanged(ipconfig);

  // No dump request is expected.
  EXPECT_CALL(*mock_rtnl_handler_, DoSendMessage(IsNeighborDumpMessage(), _))
      .Times(0);
  link_monitor_->OnIPConfigChanged(ipconfig);
}

TEST_F(NeighborLinkMonitorTest, NotifyNeighborStateChanged) {
  ShillClient::IPConfig ipconfig;
  ipconfig.ipv4_address = "1.2.3.4";
  ipconfig.ipv4_gateway = "1.2.3.5";
  ipconfig.ipv4_prefix_length = 24;

  fake_neighbor_event_handler_.Enable();

  SCOPED_TRACE("Nothing should happen if everything goes well.");
  link_monitor_->OnIPConfigChanged(ipconfig);
  NotifyNUDStateChanged("1.2.3.5", NUD_PROBE);
  NotifyNUDStateChanged("1.2.3.5", NUD_REACHABLE);
  task_env_.FastForwardBy(NeighborLinkMonitor::kBackToConnectedTimeout);

  SCOPED_TRACE(
      "Messages with NUD state not in NUD_VALID should trigger the callback "
      "once.");
  fake_neighbor_event_handler_.Expect(
      kTestInterfaceIndex, "1.2.3.5",
      NeighborLinkMonitor::NeighborRole::kGateway, false /* connected */);
  NotifyNUDStateChanged("1.2.3.5", NUD_FAILED);
  NotifyNUDStateChanged("1.2.3.5", NUD_FAILED);
  NotifyNeighborRemoved("1.2.3.5");

  SCOPED_TRACE("NUD_FAILED after NUD_VALID should cancel the timer.");
  NotifyNUDStateChanged("1.2.3.5", NUD_INCOMPLETE);
  NotifyNUDStateChanged("1.2.3.5", NUD_REACHABLE);
  NotifyNUDStateChanged("1.2.3.5", NUD_FAILED);
  task_env_.FastForwardBy(NeighborLinkMonitor::kBackToConnectedTimeout);

  SCOPED_TRACE(
      "Callback should be called at kBackToConnectedTimeout seconds after NUD "
      "state becomes NUD_VALID.");
  NotifyNUDStateChanged("1.2.3.5", NUD_REACHABLE);
  fake_neighbor_event_handler_.Expect(
      kTestInterfaceIndex, "1.2.3.5",
      NeighborLinkMonitor::NeighborRole::kGateway, true /* connected */);
  task_env_.FastForwardBy(NeighborLinkMonitor::kBackToConnectedTimeout);

  SCOPED_TRACE("No callback should come when the neighbor keeps in NUD_VALID.");
  NotifyNUDStateChanged("1.2.3.5", NUD_REACHABLE);
  task_env_.FastForwardBy(NeighborLinkMonitor::kBackToConnectedTimeout * 2);
}

TEST_F(NeighborLinkMonitorTest, NeighborRole) {
  ShillClient::IPConfig ipconfig;
  ipconfig.ipv4_address = "1.2.3.4";
  ipconfig.ipv4_prefix_length = 24;

  fake_neighbor_event_handler_.Enable();

  SCOPED_TRACE("On neighbor as gateway or DNS server failed.");
  ipconfig.ipv4_gateway = "1.2.3.5";
  ipconfig.ipv4_dns_addresses = {"1.2.3.6"};
  link_monitor_->OnIPConfigChanged(ipconfig);
  fake_neighbor_event_handler_.Expect(
      kTestInterfaceIndex, "1.2.3.5",
      NeighborLinkMonitor::NeighborRole::kGateway, false /* connected */);
  NotifyNUDStateChanged("1.2.3.5", NUD_FAILED);
  fake_neighbor_event_handler_.Expect(
      kTestInterfaceIndex, "1.2.3.6",
      NeighborLinkMonitor::NeighborRole::kDNSServer, false /* connected */);
  NotifyNUDStateChanged("1.2.3.6", NUD_FAILED);

  SCOPED_TRACE("Neighbors back to normal.");
  fake_neighbor_event_handler_.Disable();
  NotifyNUDStateChanged("1.2.3.5", NUD_REACHABLE);
  NotifyNUDStateChanged("1.2.3.6", NUD_REACHABLE);
  task_env_.FastForwardBy(NeighborLinkMonitor::kBackToConnectedTimeout);
  fake_neighbor_event_handler_.Enable();

  SCOPED_TRACE("On neighbor as gateway and DNS server failed");
  ipconfig.ipv4_gateway = "1.2.3.5";
  ipconfig.ipv4_dns_addresses = {"1.2.3.5"};
  link_monitor_->OnIPConfigChanged(ipconfig);
  fake_neighbor_event_handler_.Expect(
      kTestInterfaceIndex, "1.2.3.5",
      NeighborLinkMonitor::NeighborRole::kGatewayAndDNSServer,
      false /* connected */);
  NotifyNUDStateChanged("1.2.3.5", NUD_FAILED);

  SCOPED_TRACE("Neighbors back to normal.");
  fake_neighbor_event_handler_.Disable();
  NotifyNUDStateChanged("1.2.3.5", NUD_REACHABLE);
  task_env_.FastForwardBy(NeighborLinkMonitor::kBackToConnectedTimeout);
  fake_neighbor_event_handler_.Enable();

  SCOPED_TRACE("Swaps the roles.");
  ipconfig.ipv4_gateway = "1.2.3.6";
  ipconfig.ipv4_dns_addresses = {"1.2.3.5"};
  link_monitor_->OnIPConfigChanged(ipconfig);
  fake_neighbor_event_handler_.Expect(
      kTestInterfaceIndex, "1.2.3.5",
      NeighborLinkMonitor::NeighborRole::kDNSServer, false /* connected */);
  NotifyNUDStateChanged("1.2.3.5", NUD_FAILED);
  fake_neighbor_event_handler_.Expect(
      kTestInterfaceIndex, "1.2.3.6",
      NeighborLinkMonitor::NeighborRole::kGateway, false /* connected */);
  NotifyNUDStateChanged("1.2.3.6", NUD_FAILED);
}

class NetworkMonitorServiceTest : public testing::Test {
 protected:
  void SetUp() override {
    fake_shill_client_ = shill_helper_.FakeClient();
    monitor_svc_ = std::make_unique<NetworkMonitorService>(
        fake_shill_client_.get(),
        base::BindRepeating(&FakeNeighborConnectedStateChangedHandler::Run,
                            base::Unretained(&fake_neighbor_event_handler_)));
    mock_rtnl_handler_ = std::make_unique<shill::MockRTNLHandler>();
  }

  FakeShillClientHelper shill_helper_;
  FakeNeighborConnectedStateChangedHandler fake_neighbor_event_handler_;
  std::unique_ptr<FakeShillClient> fake_shill_client_;
  std::unique_ptr<shill::MockRTNLHandler> mock_rtnl_handler_;
  std::unique_ptr<NetworkMonitorService> monitor_svc_;
};

TEST_F(NetworkMonitorServiceTest, StartRTNLHanlderOnServiceStart) {
  monitor_svc_->rtnl_handler_ = mock_rtnl_handler_.get();
  EXPECT_CALL(*mock_rtnl_handler_, Start(RTMGRP_NEIGH));
  monitor_svc_->Start();
}

TEST_F(NetworkMonitorServiceTest, CallGetDevicePropertiesOnNewDevice) {
  monitor_svc_->rtnl_handler_ = mock_rtnl_handler_.get();
  // Device added before service starts.
  std::vector<dbus::ObjectPath> devices = {dbus::ObjectPath("/device/eth0")};
  fake_shill_client_->NotifyManagerPropertyChange(shill::kDevicesProperty,
                                                  brillo::Any(devices));
  monitor_svc_->Start();

  // Device added after service starts.
  devices.emplace_back(dbus::ObjectPath("/device/wlan0"));
  fake_shill_client_->NotifyManagerPropertyChange(shill::kDevicesProperty,
                                                  brillo::Any(devices));
  const std::set<std::string>& calls =
      fake_shill_client_->get_device_properties_calls();
  EXPECT_EQ(calls.size(), 2);
  EXPECT_NE(calls.find("eth0"), calls.end());
  EXPECT_NE(calls.find("wlan0"), calls.end());
}

}  // namespace patchpanel
