import json
import os
import platform
import sys
from copy import deepcopy
from multiprocessing.dummy import Pool
from subprocess import PIPE, Popen

_os = platform.system()
_packets = {}

_defaults = {
    "ip": None,
    "size": 0,
    "fragmentation": False,
    "count": 1,
    "exit_timeout": 1,
    "response_timeout": 1,
    "numeric": True
}

_help_message = \
    "Invalid parameters. Use: 'ping.py [PKT_SIZE] <IP>' or 'ping.py n.json'\n"

_template = {
    "returncode": -1,
    "stdout": "",
    "stderr": ""
}


def shell(command):
    _ps = Popen(
        " ".join(command),
        shell=True,
        stdout=PIPE,
        stderr=PIPE
    )
    _out = _ps.communicate()
    _err = _out[1]
    _out = _out[0]
    return _ps.returncode, _out, _err


def write_help():
    _t = deepcopy(_template)
    _t["returncode"] = 1
    _t["stderr"] = _help_message
    write_outcome(_t)


def write_outcome(_params):
    sys.stdout.write(json.dumps(_params))


def do_ping(_params):
    # Load params and defaults
    _d = deepcopy(_defaults)
    for key in _params:
        _d[key] = _params[key]

    # Build cmd
    _cmd = ["ping"]
    if _os == "Darwin":
        if not _d["fragmentation"]:
            _cmd.append("-D")
        if _d["exit_timeout"]:
            _cmd += ["-t", str(_d["exit_timeout"])]
    elif _os == "Linux":
        if not _d["fragmentation"]:
            _cmd += ["-M", "do"]
        if _d["exit_timeout"]:
            _cmd += ["-w", str(_d["exit_timeout"])]
    else:
        # Windows or other OS
        _t = deepcopy(_template)
        _t["returncode"] = 1
        _t["stderr"] = \
            "ping.py: '{}' support not implemented".format(_os)
        write_outcome(_t)
        sys.exit(1)

    if _d["size"]:
        _cmd += ["-s", str(_d["size"])]
    if _d["count"]:
        _cmd += ["-c", str(_d["count"])]
    if _d["numeric"]:
        _cmd.append("-n")
    if _d["response_timeout"]:
        _cmd += ["-W", str(_d["response_timeout"])]

    _cmd.append(_d["ip"])
    # sys.stdout.write("# {}\n".format(" ".join(_cmd)))
    _r, _out, _err = shell(_cmd)

    # TODO: parse results, latency, etc
    _t = deepcopy(_template)
    _t["returncode"] = _r
    _t["stdout"] = _out
    _t["stderr"] = _err
    _params.update(_t)
    return _params


def load_targets(filename):
    # load target ips from json
    with open(filename, "r") as f:
        j = json.load(f)

    return j


if len(sys.argv) < 2:
    # no params given
    write_help()
elif len(sys.argv) < 3:
    # one param: decide if it json file or IP
    _arg = sys.argv[1]
    if os.path.isfile(_arg):
        _packets = load_targets(_arg)
        # up to 15 packets at once
        pool = Pool(15)
        # prepare threaded map
        _param_map = []
        for _node, _data in _packets.iteritems():
            if isinstance(_data, list):
                for target in _data:
                    _param_map.append(target)
            elif isinstance(_data, dict):
                _param_map.append(_data)
            else:
                _t = deepcopy(_template)
                _t["returncode"] = 1
                _t["stderr"] = \
                    "TypeError: 'list' or 'dict' expected. " \
                    "Got '{}': '{}'".format(
                        type(_data).__name__,
                        _data
                )
                _packets[_node] = _t
        _threaded_out = pool.map(do_ping, _param_map)
        for _out in _threaded_out:
            if isinstance(_packets[_out["tgt_host"]], dict):
                _packets[_out["tgt_host"]] = _out
            elif isinstance(_packets[_out["tgt_host"]], list):
                _packets[_out["tgt_host"]][_out["ip_index"]] = _out
        sys.stdout.write(json.dumps(_packets))
    else:
        # IP given
        _ip = sys.argv[1]
        write_outcome(do_ping(_ip))
elif len(sys.argv) < 4:
    # two params: size and IP
    _s = sys.argv[1]
    _ip = sys.argv[2]
    write_outcome(do_ping(_ip, size=_s))
else:
    # too many params given
    write_help()
