#!/usr/bin/python2.7

"""report: make a table summarizing output from one or more runs of `sample`."""

import collections
import csv
import datetime
import os
import re
import sys

import ifstats
import iperf
import isostream
import options
import wifipacket

optspec = """
report [options...] <journal>
--
r,report_dir=  path to a single report directory to be parsed
"""

NFILE = 'n-datarates.tsv'
nrates = {}

CHANNELFILE = 'channels.tsv'
channels = {}


def _Resource(name):
  return os.path.join(os.path.dirname(os.path.abspath(__file__)), name)


def LoadNRates():
  """Loads 802.11n coding and data rates into a global variable."""
  if nrates: return

  raw = []

  with open(_Resource(NFILE), 'rb') as csvfile:
    reader = csv.reader(csvfile, delimiter='\t')
    next(reader)  # skip header row when reading by machine
    for mcs, width, gi, rate in reader:
      raw.append([int(mcs), int(width), int(gi), float(rate)])

  # Load global table, computing MCS 8-31 statistics from MCS 0-7.
  for mcs, width, gi, rate in raw:
    for i in range(4):
      nrates[(8*i + mcs, width, gi)] = rate * (i + 1)


def LoadChannels():
  """Load 802.11n channels and frequencies into a global variable."""
  if channels: return

  with open(_Resource(CHANNELFILE), 'rb') as csvfile:
    reader = csv.reader(csvfile, delimiter='\t')
    next(reader)

    for channel, freq in reader:
      channels[int(channel)] = int(freq)


def ParseMCSFile(outfile, width=20):
  """Extract MCS and PHY rate statistics from an MCS report file."""
  LoadNRates()

  # assume long guard interval
  guard = 800

  counter = collections.Counter()
  for line in outfile:
    for tok in line.split():
      if tok == '.': continue

      mcs = int(tok)
      counter[mcs] += 1

  phy = 0.0
  alltimes = 0
  for mcs, times in counter.iteritems():
    phy += nrates[(mcs, width, guard)] * times
    alltimes += times

  return counter.most_common()[0][0], phy / alltimes


def Channel(text_channel):
  """Given a text channel spec like 149,+1 return the central freq and width."""
  LoadChannels()

  if ',' in text_channel:
    base, offset = text_channel.split(',')
    freq = channels[int(base)]
    offset = int(offset)
    return (2 * freq + offset * 20) / 2, 40
  else:
    return channels[int(text_channel)], 20


def Overlap(c1, w1, c2, w2):
  """Return True if two WiFi channels overlap, or False otherwise."""
  # TODO(willangley): replace with code from Waveguide
  b1 = c1 - w1 / 2
  t1 = c1 + w1 / 2
  b2 = c2 - w2 / 2
  t2 = c2 + w2 / 2

  return ((b1 <= b2 <= t1) or (b2 <= b1 <= t2)
          or (b1 <= t2 <= t1) or (b2 <= t1 <= t2))


def ReportLine(report_dir, series=None):
  """Condense the output of a sample.py run into a one-line summary report."""
  line = collections.OrderedDict()
  if series:
    line['Series'] = series

  _, stamp, steps = os.path.basename(report_dir).split('-')
  line['Time'] = datetime.datetime.fromtimestamp(float(stamp))
  line['Steps'] = int(steps)

  system, cache = ifstats.Restore(report_dir)
  result = ifstats.Parse(system, cache)

  if not result.get('link'):
    pass
  elif system == 'Darwin':
    airport = result.get('link')
    channel, width = Channel(airport['channel'])
    shared = 0
    overlap = 0

    scan = result.get('scan')
    if len(scan) > 1:
      for row in scan[1:]:
        oc, ow = Channel(row[3])
        if channel == oc and width == ow:
          shared += 1
        if Overlap(channel, width, oc, ow):
          overlap += 1

    line.update({
        'Channel': channel,
        'Width': width,
        'RSSI': airport['agrCtlRSSI'],
        'Noise': airport['agrCtlNoise'],
        'Shared': shared,
        'Interfering': overlap - shared
    })
  elif system == 'Linux':
    iwlink = result.get('link')
    signal = int(iwlink.get('signal', '0 dBm').split()[0])
    channel = int(iwlink.get('freq', '0'))
    width = 20
    m = re.search(r'(\d+)MHz', iwlink.get('tx bitrate', ''), flags=re.I)
    if m:
      width = int(m.group(1))

    # Noise and contention not yet gathered in samples run on Linux systems.
    line.update({
        'Channel': channel,
        'Width': width,
        'RSSI': signal,
    })

  try:
    ppath = os.path.join(report_dir, 'testnetwork.pcap')
    with open(ppath) as stream:
      rates = [float(opt.rate) for opt, _ in wifipacket.Packetize(stream)]

      # TODO(willangley): come up with a meaningful modal MCS for mixed
      #   802.11n/802.11ac captures like we have here.
      line['PHY'] = sum(rates)/max(len(rates), 1)
  except IOError:
    try:
      mpath = os.path.join(report_dir, 'mcs')
      with open(mpath) as mf:
        mcs, phy = ParseMCSFile(mf, width)
        line['MCS'] = mcs
        line['PHY'] = phy
    except IOError:
      pass

  # If the initial ping test fails, we won't collect performance information.
  # deal with this gracefully.
  ips = iperf.Restore(report_dir)
  if 'iperf' in ips:
    # pylint:disable=line-too-long
    for key, perf in [('TCP BW up', iperf.ParseIperfTCP(ips.get('iperf', ''))),
                      ('UDP BW up', iperf.ParseIperfUDP(ips.get('iperfu', '')))]:
      line[key] = perf.get('bandwidth')
      line['{} units'.format(key)] = perf.get('bandwidth_unit')
  elif 'iperf3' in ips:
    for name in (key for key in ips
                 if key.startswith('iperf3')):
      perf = iperf.ParseIperf3(ips[name])
      if not perf or 'error' in perf:
        continue

      test_start = perf['start']['test_start']
      protocol = test_start['protocol']
      direction = 'down' if test_start['reverse'] else 'up'
      key = '{protocol} BW {direction}'.format(protocol=protocol,
                                               direction=direction)

      if protocol == 'TCP':
        line[key] = perf['end']['sum_received']['bits_per_second']
      elif protocol == 'UDP':
        line[key] = perf['end']['sum']['bits_per_second']
      else:
        continue

      line['{} units'.format(key)] = 'bit/s'

  try:
    with open(os.path.join(report_dir, 'isostream')) as istm:
      text = istm.read()
      line['isostream'] = isostream.ParseIsostream(text)
  except IOError:
    pass

  return line


def ReadJournal(jname):
  """Read a journal, returning a series name and its data folders."""
  jname = os.path.realpath(jname)
  series = os.path.basename(jname)
  if series == 'journal':
    series = os.path.basename(os.path.dirname(jname))

  folders = []
  with open(jname) as journal:
    for line in journal:
      line = line.strip()
      if line.startswith('#'):
        continue
      folders.append(os.path.join(os.path.dirname(jname), line))

  return series, folders


def Report(journals):
  """Given the name of a journal file, return a list of ReportLines."""
  report = []
  bad = []

  for jname in journals:
    series, folders = ReadJournal(jname)
    for folder in folders:
      try:
        report += [ReportLine(folder, series=series)]
      except (TypeError, IOError) as e:
        bad += [collections.OrderedDict(folder=folder, error=repr(e))]

  return report, bad


def WriteReport(lines):
  """Write a network testing report in .tsv format to stdout."""
  # include every field we can write in the header row
  header = ['Series', 'Time', 'Steps', 'Channel', 'Width', 'RSSI', 'Noise',
            'Shared', 'Interfering', 'MCS', 'PHY', 'TCP BW up',
            'TCP BW up units', 'UDP BW up', 'UDP BW up units', 'TCP BW down',
            'TCP BW down units', 'UDP BW down', 'UDP BW down units',
            'isostream']

  writer = csv.DictWriter(sys.stdout, header, dialect=csv.excel_tab)
  writer.writeheader()
  writer.writerows(lines)


def main():
  o = options.Options(optspec)
  (opt, _, extra) = o.parse(sys.argv[1:])

  if opt.report_dir:
    report = [ReportLine(opt.report_dir)]
  elif extra:
    report, bad = Report(extra)
    if bad:
      writer = csv.DictWriter(sys.stdout, bad[0].keys(), dialect=csv.excel_tab)
      writer.writeheader()
      writer.writerows(bad)
      print

  if len(report) < 1:
    o.fatal("Didn't find any samples. Did you supply at least one report dir"
            ' or journal?')

  WriteReport(report)


if __name__ == '__main__':
  main()
