#!/usr/bin/python

from mininet.topo import Topo
from mininet.net import Mininet
from mininet.log import setLogLevel, output, info
from mininet.cli import CLI
from mininet.node import CPULimitedCCNHost, CCNHost
from mininet.link import TCLink
from mininet.conf_parser import parse_hosts,parse_routers, parse_links
import os.path, time
import optparse
import datetime

def parse_args():
    usage="""Usage: miniccnx [template_file] [ -t | --testbed ]
    If no template_file is given, will try to load template
    from file miniccnx.conf in the current directory.
    If --testbed is used, miniccnx will run the NDN Project Testbed.
    This assumes you are in the testbed directory in the miniccnx installation
    directory.
    """

    testbed = False
    parser = optparse.OptionParser(usage)

    parser.add_option("-t", "--testbed", action="store_true", dest="testbed",
    help="instantiates NDN Testbed")

    (options, arg) = parser.parse_args()

    testbed = options.testbed

    if len(arg) == 0 or len(arg) > 2:
        file = ''
    else:
        file = arg[0]

    return file, testbed


class CCNTopo(Topo):
    def __init__(self, conf_arq, **opts):
        Topo.__init__(self, **opts)

        hosts_conf = parse_hosts(conf_arq)
#       routers_conf = parse_routers(conf_arq)
        links_conf = parse_links(conf_arq)


        self.isTCLink = False
        self.isLimited = False

        for host in hosts_conf:
	    print host
            if host.cpu != None and self.isLimited != True:
                self.isLimited = True
            self.addHost(host.name, app=host.app, fib=host.uri_tuples,cpu=host.cpu,cores=host.cores,cache=host.cache)

#        for router in routers_conf:
#            if router.cpu != None and self.isLimited != True:
#                self.isLimited = True
#            self.addHost(router.name,fib=router.uri_tuples,cpu=router.cpu,cores=router.cores)

        for link in links_conf:
            if len(link.linkDict) == 0:
                self.addLink(link.h1, link.h2)
            else:
                self.addLink(link.h1, link.h2, **link.linkDict)
                self.isTCLink = True

        info('Parse of ' + conf_arq + ' done.\n')

def execute(template_file='miniccnx.conf', testbed=False):
    "Create a network based on template_file"

    if template_file == '':
        template_file='miniccnx.conf'

    if os.path.exists(template_file) == False:
        info('No template file given and default template file miniccnx.conf not found. Exiting...\n')
        quit()

    topo = CCNTopo(template_file)

    t = datetime.datetime.now()

    if topo.isTCLink == True and topo.isLimited == True:
        net = Mininet(topo,host=CPULimitedCCNHost,link=TCLink)
    elif topo.isTCLink == True and topo.isLimited == False:
        net = Mininet(topo,host=CCNHost,link=TCLink)
    elif topo.isTCLink == False and topo.isLimited == True:
        net = Mininet(topo,host=CPULimitedCCNHost)
    else:
        net = Mininet(topo,host=CCNHost)

    t2 = datetime.datetime.now()

    delta = t2 - t

    info('Setup time: ' + str(delta.seconds) + '\n')

    net.start()

    if testbed == True:
        info('Starting OSPFN ...\n')
        for host in net.hosts:
            host.cmd("cd {0}".format(host.name))
            host.cmd("./routing.sh {0}".format(host.name))

        time.sleep(60)

        for host in net.hosts:
            host.cmd("./ospfn-start.sh {0}".format(host.name))

        info('OSPFN configuration completed!\n')

    for host in net.hosts:
        if 'app' in host.params:
            if host.params['app'] != '_':
                host.cmd(host.params['app'])

    CLI(net)
    net.stop()

if __name__ == '__main__':

    template, testbed = parse_args()
    setLogLevel('info')
    execute(template, testbed)
