#!/usr/bin/env python
#  Copyright (c) 2012 The WebRTC project authors. All Rights Reserved.
#
#  Use of this source code is governed by a BSD-style license
#  that can be found in the LICENSE file in the root of the source
#  tree. An additional intellectual property rights grant can be found
#  in the file PATENTS.  All contributing project authors may
#  be found in the AUTHORS file in the root of the source tree.
"""Script for constraining traffic on the local machine."""

import ctypes
import logging
import os
import subprocess
import sys


class NetworkEmulatorError(BaseException):
    """Exception raised for errors in the network emulator.

  Attributes:
    fail_msg: User defined error message.
    cmd: Command for which the exception was raised.
    returncode: Return code of running the command.
    stdout: Output of running the command.
    stderr: Error output of running the command.
  """

    def __init__(self,
                 fail_msg,
                 cmd=None,
                 returncode=None,
                 output=None,
                 error=None):
        BaseException.__init__(self, fail_msg)
        self.fail_msg = fail_msg
        self.cmd = cmd
        self.returncode = returncode
        self.output = output
        self.error = error


class NetworkEmulator(object):
    """A network emulator that can constrain the network using Dummynet."""

    def __init__(self, connection_config, port_range):
        """Constructor.

    Args:
        connection_config: A config.ConnectionConfig object containing the
            characteristics for the connection to be emulation.
        port_range: Tuple containing two integers defining the port range.
    """
        self._pipe_counter = 0
        self._rule_counter = 0
        self._port_range = port_range
        self._connection_config = connection_config

    def Emulate(self, target_ip):
        """Starts a network emulation by setting up Dummynet rules.

    Args:
        target_ip: The IP address of the interface that shall be that have the
            network constraints applied to it.
    """
        receive_pipe_id = self._CreateDummynetPipe(
            self._connection_config.receive_bw_kbps,
            self._connection_config.delay_ms,
            self._connection_config.packet_loss_percent,
            self._connection_config.queue_slots)
        logging.debug('Created receive pipe: %s', receive_pipe_id)
        send_pipe_id = self._CreateDummynetPipe(
            self._connection_config.send_bw_kbps,
            self._connection_config.delay_ms,
            self._connection_config.packet_loss_percent,
            self._connection_config.queue_slots)
        logging.debug('Created send pipe: %s', send_pipe_id)

        # Adding the rules will start the emulation.
        incoming_rule_id = self._CreateDummynetRule(receive_pipe_id, 'any',
                                                    target_ip,
                                                    self._port_range)
        logging.debug('Created incoming rule: %s', incoming_rule_id)
        outgoing_rule_id = self._CreateDummynetRule(send_pipe_id, target_ip,
                                                    'any', self._port_range)
        logging.debug('Created outgoing rule: %s', outgoing_rule_id)

    @staticmethod
    def CheckPermissions():
        """Checks if permissions are available to run Dummynet commands.

    Raises:
      NetworkEmulatorError: If permissions to run Dummynet commands are not
      available.
    """
        try:
            if os.getuid() != 0:
                raise NetworkEmulatorError(
                    'You must run this script with sudo.')
        except AttributeError:

            # AttributeError will be raised on Windows.
            if ctypes.windll.shell32.IsUserAnAdmin() == 0:
                raise NetworkEmulatorError(
                    'You must run this script with administrator'
                    ' privileges.')

    def _CreateDummynetRule(self, pipe_id, from_address, to_address,
                            port_range):
        """Creates a network emulation rule and returns its ID.

    Args:
        pipe_id: integer ID of the pipe.
        from_address: The IP address to match source address. May be an IP or
          'any'.
        to_address: The IP address to match destination address. May be an IP or
          'any'.
        port_range: The range of ports the rule shall be applied on. Must be
          specified as a tuple of with two integers.
    Returns:
        The ID of the rule, starting at 100. The rule ID increments with 100 for
        each rule being added.
    """
        self._rule_counter += 100
        add_part = [
            'add', self._rule_counter, 'pipe', pipe_id, 'ip', 'from',
            from_address, 'to', to_address
        ]
        _RunIpfwCommand(add_part +
                        ['src-port', '%s-%s' % port_range],
                        'Failed to add Dummynet src-port rule.')
        _RunIpfwCommand(add_part +
                        ['dst-port', '%s-%s' % port_range],
                        'Failed to add Dummynet dst-port rule.')
        return self._rule_counter

    def _CreateDummynetPipe(self, bandwidth_kbps, delay_ms,
                            packet_loss_percent, queue_slots):
        """Creates a Dummynet pipe and return its ID.

    Args:
        bandwidth_kbps: Bandwidth.
        delay_ms: Delay for a one-way trip of a packet.
        packet_loss_percent: Float value of packet loss, in percent.
        queue_slots: Size of the queue.
    Returns:
        The ID of the pipe, starting at 1.
    """
        self._pipe_counter += 1
        cmd = [
            'pipe', self._pipe_counter, 'config', 'bw',
            str(bandwidth_kbps / 8) + 'KByte/s', 'delay',
            '%sms' % delay_ms, 'plr', (packet_loss_percent / 100.0), 'queue',
            queue_slots
        ]
        error_message = 'Failed to create Dummynet pipe. '
        if sys.platform.startswith('linux'):
            error_message += (
                'Make sure you have loaded the ipfw_mod.ko module to '
                'your kernel (sudo insmod /path/to/ipfw_mod.ko).')
        _RunIpfwCommand(cmd, error_message)
        return self._pipe_counter


def Cleanup():
    """Stops the network emulation by flushing all Dummynet rules.

  Notice that this will flush any rules that may have been created previously
  before starting the emulation.
  """
    _RunIpfwCommand(['-f', 'flush'], 'Failed to flush Dummynet rules!')
    _RunIpfwCommand(['-f', 'pipe', 'flush'], 'Failed to flush Dummynet pipes!')


def _RunIpfwCommand(command, fail_msg=None):
    """Executes a command and prefixes the appropriate command for
     Windows or Linux/UNIX.

  Args:
    command: Command list to execute.
    fail_msg: Message describing the error in case the command fails.

  Raises:
    NetworkEmulatorError: If command fails a message is set by the fail_msg
    parameter.
  """
    if sys.platform == 'win32':
        ipfw_command = ['ipfw.exe']
    else:
        ipfw_command = ['sudo', '-n', 'ipfw']

    cmd_list = ipfw_command[:] + [str(x) for x in command]
    cmd_string = ' '.join(cmd_list)
    logging.debug('Running command: %s', cmd_string)
    process = subprocess.Popen(cmd_list,
                               stdout=subprocess.PIPE,
                               stderr=subprocess.PIPE)
    output, error = process.communicate()
    if process.returncode != 0:
        raise NetworkEmulatorError(fail_msg, cmd_string, process.returncode,
                                   output, error)
    return output.strip()
