// Copyright (c) 2013 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.

#ifndef SHILL_TRAFFIC_MONITOR_H_
#define SHILL_TRAFFIC_MONITOR_H_

#include <base/callback.h>
#include <base/cancelable_callback.h>
#include <gtest/gtest_prod.h>  // for FRIEND_TEST

#include <map>

#include "shill/connection_info.h"
#include "shill/connection_info_reader.h"
#include "shill/refptr_types.h"
#include "shill/socket_info.h"

namespace shill {

class EventDispatcher;
class SocketInfoReader;

// TrafficMonitor detects certain abnormal scenarios on a network interface
// and notifies an observer of various scenarios via callbacks.
class TrafficMonitor {
 public:
  typedef base::Closure TcpOutTrafficNotRoutedCallback;

  TrafficMonitor(const DeviceRefPtr &device, EventDispatcher *dispatcher);
  virtual ~TrafficMonitor();

  // Starts traffic monitoring on the selected device.
  virtual void Start();

  // Stops traffic monitoring on the selected device.
  virtual void Stop();

  // Sets the callback to invoke, if the traffic monitor detects that too many
  // packets are failing to get transmitted over a TCP connection.
  void set_tcp_out_traffic_not_routed_callback(
      const TcpOutTrafficNotRoutedCallback &callback) {
    outgoing_tcp_packets_not_routed_callback_ = callback;
  }

 private:
  friend class TrafficMonitorTest;
  FRIEND_TEST(TrafficMonitorTest,
      BuildIPPortToTxQueueLengthInvalidConnectionState);
  FRIEND_TEST(TrafficMonitorTest, BuildIPPortToTxQueueLengthInvalidDevice);
  FRIEND_TEST(TrafficMonitorTest, BuildIPPortToTxQueueLengthInvalidTimerState);
  FRIEND_TEST(TrafficMonitorTest, BuildIPPortToTxQueueLengthMultipleEntries);
  FRIEND_TEST(TrafficMonitorTest, BuildIPPortToTxQueueLengthValid);
  FRIEND_TEST(TrafficMonitorTest, BuildIPPortToTxQueueLengthZero);
  FRIEND_TEST(TrafficMonitorTest, SampleTrafficDnsFailureThenSuccess);
  FRIEND_TEST(TrafficMonitorTest, SampleTrafficDnsOutstanding);
  FRIEND_TEST(TrafficMonitorTest, SampleTrafficDnsStatsReset);
  FRIEND_TEST(TrafficMonitorTest, SampleTrafficDnsSuccessful);
  FRIEND_TEST(TrafficMonitorTest, SampleTrafficDnsTimedOut);
  FRIEND_TEST(TrafficMonitorTest, SampleTrafficDnsTimedOutInvalidProtocol);
  FRIEND_TEST(TrafficMonitorTest, SampleTrafficDnsTimedOutInvalidSourceIp);
  FRIEND_TEST(TrafficMonitorTest, SampleTrafficDnsTimedOutOutsideTimeWindow);
  FRIEND_TEST(TrafficMonitorTest, SampleTrafficNonDnsTimedOut);
  FRIEND_TEST(TrafficMonitorTest,
      SampleTrafficStuckTxQueueIncreasingQueueLength);
  FRIEND_TEST(TrafficMonitorTest, SampleTrafficStuckTxQueueSameQueueLength);
  FRIEND_TEST(TrafficMonitorTest,
      SampleTrafficStuckTxQueueVariousQueueLengths);
  FRIEND_TEST(TrafficMonitorTest, SampleTrafficUnstuckTxQueueNoConnection);
  FRIEND_TEST(TrafficMonitorTest, SampleTrafficUnstuckTxQueueStateChanged);
  FRIEND_TEST(TrafficMonitorTest, SampleTrafficUnstuckTxQueueZeroQueueLength);
  FRIEND_TEST(TrafficMonitorTest, StartAndStop);

  typedef std::map<std::string, uint64> IPPortToTxQueueLengthMap;

  // The minimum number of samples that indicate an abnormal scenario
  // required to trigger the callback.
  static const int kMinimumFailedSamplesToTrigger;
  // The frequency at which to sample the TCP connections.
  static const int64 kSamplingIntervalMilliseconds;
  // DNS port.
  static const uint16 kDnsPort;
  // If a DNS "connection" time-to-expire falls below this threshold, then
  // it's considered a timed out DNS request.
  static const int64 kDnsTimedOutThresholdSeconds;

  // Resets congested tx-queues tracking statistics.
  void ResetCongestedTxQueuesStats();
  void ResetCongestedTxQueuesStatsWithLogging();

  // Builds map of IP address/port to tx queue lengths from socket info vector.
  // Skips sockets not on device, tx queue length is 0, connection state is not
  // established or does not have a pending retransmit timer.
  void BuildIPPortToTxQueueLength(
      const std::vector<SocketInfo> &socket_infos,
      IPPortToTxQueueLengthMap *tx_queue_length);

  // Checks for congested tx-queue via network statistics.
  // Returns |true| if tx-queue is congested.
  bool IsCongestedTxQueues();

  // Resets failing DNS queries tracking statistics.
  void ResetDnsFailingStats();
  void ResetDnsFailingStatsWithLogging();

  // Checks to see for failed DNS queries.
  bool IsDnsFailing();

  // Samples traffic (e.g. receive and transmit byte counts) on the
  // selected device and invokes appropriate callbacks when certain
  // abnormal scenarios are detected.
  void SampleTraffic();

  // The device on which to perform traffic monitoring.
  DeviceRefPtr device_;

  // Dispatcher on which to create delayed tasks.
  EventDispatcher *dispatcher_;

  // Callback to invoke when TrafficMonitor needs to sample traffic
  // of the network interface.
  base::CancelableClosure sample_traffic_callback_;

  // Callback to invoke when we detect that the send queue has been increasing
  // on an ESTABLISHED TCP connection through the network interface.
  TcpOutTrafficNotRoutedCallback outgoing_tcp_packets_not_routed_callback_;

  // Reads and parses socket information from the system.
  scoped_ptr<SocketInfoReader> socket_info_reader_;

  // Number of consecutive congested tx-queue cases sampled.
  int accummulated_congested_tx_queues_samples_;

  // Map of tx queue lengths from previous sampling pass.
  IPPortToTxQueueLengthMap old_tx_queue_lengths_;

  // Reads and parses connection information from the system.
  scoped_ptr<ConnectionInfoReader> connection_info_reader_;

  // Number of consecutive sample intervals that contains failed DNS requests.
  int accummulated_dns_failures_samples_;

  DISALLOW_COPY_AND_ASSIGN(TrafficMonitor);
};

}  // namespace shill

#endif  // SHILL_TRAFFIC_MONITOR_H_
