Пример #1
0
    def configure_EGP(cls, node):
        cfg = ''
        v6cfg = []
        # find any link on which two different netid's (i.e., AS numbers) are
        # present and configure a bgp-session between the two corresponding nodes.
        for localnetif in node.netifs():

            # do not include control interfaces
            if hasattr(localnetif, 'control') and localnetif.control == True:
                continue

            for idx, net_netif in list(localnetif.net._netif.items()):
                candidate_node = net_netif.node

                # skip our own interface
                if localnetif == net_netif.node:
                    continue

                # found two different ASes.
                if not node.netid == net_netif.node.netid and \
                        service_flags.EGP in net_netif.node.services:
                    for local_node_addr in localnetif.addrlist:

                        local_node_addr_str = str(local_node_addr.split('/')[0])
                        if not node.enable_ipv4 and \
                                isIPv4Address(local_node_addr):
                            continue
                        if not node.enable_ipv6 and \
                                isIPv6Address(local_node_addr):
                            continue

                        for remote_node_addr in net_netif.addrlist:
                            remote_node_addr_str = str(remote_node_addr.split('/')[0])
                            if not net_netif.node.enable_ipv4 and \
                                    isIPv4Address(remote_node_addr):
                                continue
                            if not net_netif.node.enable_ipv6 and \
                                    isIPv6Address(remote_node_addr):
                                continue

                            # for inter-AS links, use interface addresses
                            # instead of loopback addresses
                            if (isIPv4Address(local_node_addr) and \
                                    isIPv4Address(remote_node_addr)):
                                cfg += '  neighbor %s remote-as %s\n' % \
                                        (remote_node_addr_str, \
                                        str(net_netif.node.netid))

                            elif (isIPv6Address(local_node_addr) and \
                                    isIPv6Address(remote_node_addr)):
                                cfg += '  neighbor %s remote-as %s\n' % \
                                        (remote_node_addr_str, str(net_netif.node.netid))

                                v6cfg.append(('    neighbor %s activate\n' %
                                        remote_node_addr_str))
                                v6cfg.append(('    network %s\n' %
                                        str(local_node_addr)))

        return cfg, v6cfg
Пример #2
0
 def addaddr(self, ifindex, addr):
     if self.up:
         if self.enable_ipv4 and isIPv4Address(addr) or \
                 self.enable_ipv6 and isIPv6Address(addr):
             self.cmd([IP_BIN, "addr", "add", str(addr),
                 "dev", self.ifname(ifindex)])
     if self.enable_ipv4 and isIPv4Address(addr) or \
             self.enable_ipv6 and isIPv6Address(addr):
         self._netif[ifindex].addaddr(addr)
Пример #3
0
 def deladdr(self, ifindex, addr):
     try:
         if self.enable_ipv4 and isIPv4Address(addr) or \
                 self.enable_ipv6 and isIPv6Address(addr):
             self._netif[ifindex].deladdr(addr)
     except ValueError:
         self.warn("trying to delete unknown address: %s" % addr)
     if self.up:
         if self.enable_ipv4 and isIPv4Address(addr) or \
                 self.enable_ipv6 and isIPv6Address(addr):
             self.cmd([IP_BIN, "addr", "del", str(addr),
                   "dev", self.ifname(ifindex)])
Пример #4
0
    def compileZoneFile(cls, nameservers, hosts = None):
        # element in nameservers: tuple(server-name, server-ipaddr, zone that server handles)
        # element in hosts: tuple(server-name, server-ipaddr)

        if nameservers is None:
            nameservers = []

        if hosts is None:
            hosts = []

        nameserverlist = []
        tmpnameserverlist = []
        forwardhostlist = []
        reversehostlist = []

        seen_server_names = {}

        for server_name, server_addr, zone in nameservers:
            if isIPv4Address(server_addr):
                recordtype = 'A'
            elif isIPv6Address(server_addr):
                recordtype = 'AAAA'
            else:
                raise ValueError

            if not server_name in seen_server_names:
                seen_server_names[server_name] = {}
            if not zone in seen_server_names[server_name]:
                seen_server_names[server_name][zone]= 1

            tmpnameserverlist.extend([
                    server_name, ' ', recordtype, ' ', server_addr, '\n'
                    ])

        for servername, zones in seen_server_names.items():
            for zone in zones.keys():
                nameserverlist.extend([zone, ' IN NS ', servername, '\n'])

        nameserverlist.extend(tmpnameserverlist)

        for host_name, host_addr, zone in hosts:
            if isIPv4Address(host_addr):
                recordtype = 'A'
            elif isIPv6Address(host_addr):
                recordtype = 'AAAA'
            else:
                raise ValueError

            forwardhostlist.extend([host_name, ' IN ', recordtype, ' ', host_addr, '\n'])

        return (''.join(nameserverlist), ''.join(forwardhostlist), ''.join(reversehostlist))
Пример #5
0
    def generateZebraConf(cls, node, services):
        ''' Returns configuration file text that defines which daemons to run.
        '''
        cfg = []

        cfg.append('log file /tmp/quagga-zebra-%s.log\n' % node.name)
        cfg.append('hostname %s\n' % node.name)
        cfg.append('agentx\n')
        cfg.append('interface lo\n')
        if node.enable_ipv4:
            cfg.append('  ip address %s/32\n' % node.getLoopbackIPv4())
        if node.enable_ipv6:
            cfg.append('  ipv6 address %s/128\n' % node.getLoopbackIPv6())

        for ifc in node.netifs():
            # do not ever include control interfaces in anything
            if hasattr(ifc, 'control') and ifc.control == True:
                continue

            cfg.append('interface %s\n' % ifc.name)
            for a in ifc.addrlist:
                if isIPv4Address(a):
                    cfg.append('  ip  address %s\n' % a)
                if isIPv6Address(a):
                    cfg.append('  ipv6  address %s\n' % a)
            cfg.append('!\n')

        if node.enable_ipv4:
            cfg.append('ip forwarding\n')
        if node.enable_ipv6:
            cfg.append('ipv6 forwarding\n')

        return ''.join(cfg)
 def add_virtual_host(self, parent, obj):
     assert isinstance(obj, nodes.PyCoreNode)
     el = self.add_host(parent, obj.name)
     device = self.find_device(self.root.baseEle, obj.name)
     if device is None:
         self.session.warn('corresponding XML device not found for %s' %
                           (obj.name))
         return
     self.add_mapping(device, 'testHost', el.getAttribute('id'))
     self.add_type(el, 'virtual')
     for netif in obj.netifs():
         for address in netif.addrlist:
             addr, slash, prefixlen= address.partition('/')
             if ipaddr.isIPv4Address(addr):
                 addr_type = 'IPv4'
             elif ipaddr.isIPv6Address(addr):
                 addr_type = 'IPv6'
             else:
                 raise NotImplementedError
             self.add_address(el, addr_type, address, netif.name)
         if isinstance(netif.net, nodes.EmaneNode):
             nem = self.add_emane_interface(parent, el, netif)
             interface = self.find_interface(device, netif.name)
             self.add_mapping(interface, 'nem', nem.getAttribute('id'))
     return el
Пример #7
0
    def generateconfig(cls, node, filename, services):
        cfg = "# auto-generated by StaticRouteToLoopback dummy service (utility.py)\n"
        for ifc in node.netifs():
            for idx, net_netif in list(ifc.net._netif.items()):
                # do not include control interfaces
                if hasattr(ifc, 'control') and ifc.control == True:
                    continue

                # skip all own interface(s)
                if ifc == net_netif:
                    continue

                # only core routers are candidate gateways
                if not service_flags.Router in net_netif.node.services:
                    continue

                for addr in ifc.addrlist:
                    if node.enable_ipv4 and isIPv4Address(addr):
                        route_target = node.getLoopbackIPv4()
                    elif node.enable_ipv6 and isIPv6Address(addr):
                        route_target = node.getLoopbackIPv6()
                    else:
                        continue

                    print(('[%s] ip r a %s via %s' % (str(cls),
                            str(route_target), str(addr.split('/')[0]))))
                    net_netif.node.cmd(['ip', 'route', 'add', str(route_target),
                            'via', addr.split('/')[0]])
                    cfg += ' '.join(['#ip', 'route', 'add', str(route_target),
                            'via', addr.split('/')[0], '\n'])
        return cfg
Пример #8
0
    def generatequaggaifcconfig(cls,  node,  ifc):
        if not node.enable_ipv4 and not node.enable_ipv6:
            return ''

        if hasattr(ifc, 'control') and ifc.control == True:
            return ''

        enable_ifc = False
        for a in ifc.addrlist:
            if node.enable_ipv4 and isIPv4Address(a):
                enable_ifc = True
            if node.enable_ipv6 and isIPv6Address(a):
                enable_ifc = True

        cfg = ''
        if enable_ifc:
            cfg += cls.mtucheck(ifc)
            for idx, net_netif in list(ifc.net._netif.items()):

                # skip our own interface
                if ifc == net_netif:
                    continue
                # skip control interface
                if hasattr(ifc, 'control') and ifc.control == True:
                    continue

                # found the same AS, enable IGP/OSPF
                if node.netid == net_netif.node.netid:
                    if not service_flags.Router in net_netif.node.services:
                        # other end of link is not router. don't send hellos
                        cfg += '  ipv6 ospf6 passive\n'
                        break
        return cfg
Пример #9
0
    def generatequaggaconfig(cls, node):
        if not node.enable_ipv4:
            return ''

        cfg = ''

        cfg += cls.generatequaggaloconfig(node)

        for ifc in node.netifs():
            # do not ever include control interfaces in anything
            if hasattr(ifc, 'control') and ifc.control == True:
                continue

            cfg += 'interface %s\n' % ifc.name
            cfg += cls.generatequaggaifcconfig(node, ifc)
            ipv4list = [x for x in ifc.addrlist if isIPv4Address(x)]
            cfg += '  '
            cfg += '\n  '.join(map(cls.addrstr, ipv4list))
            cfg += '\n'
            cfg += '!\n'

        cfg = '!\n! OSPFv2 (for IPv4) configuration\n!\n'
        cfg += 'log file /tmp/quagga-ospf-%s.log\n' % node.name
        cfg += 'router ospf\n'
        cfg += '  router-id %s\n' % cls.routerid(node)
        cfg += '  redistribute connected\n'
        cfg += '!\n'
        cfg += ''.join(set(cls.interface_iterator(node,
                cls.generate_network_statement)))
        cfg += '!\n'
        return cfg
Пример #10
0
    def generatequaggaconfig(cls, node):
        cfg = ''

        cfg += cls.generatequaggaloconfig(node)

        for ifc in node.netifs():
            # do not ever include control interfaces in anything
            if hasattr(ifc, 'control') and ifc.control == True:
                continue

            tmpcfg = 'interface %s\n' % ifc.name

            cfgv4 = ''
            cfgv6 = ''
            cfgvall = ''
            want_ipv4 = False
            want_ipv6 = False

            ifccfg = cls.generatequaggaifcconfig(node, ifc)
            if cls._ipv4_routing and node.enable_ipv4:
                want_ipv4 = True
            if cls._ipv6_routing and node.enable_ipv6:
                want_ipv6 = True

            if want_ipv4 and not want_ipv6:
                cfgv4 += ifccfg
            elif not want_ipv4 and want_ipv6:
                cfgv6 += ifccfg
            elif want_ipv4 and want_ipv6:
                cfgvall += ifccfg

            if want_ipv4 and not want_ipv6:
                ipv4list = [x for x in ifc.addrlist if isIPv4Address(x)]
                tmpcfg += cfgv4

            elif not want_ipv4 and want_ipv6:
                ipv6list = [x for x in ifc.addrlist if isIPv6Address(x)]
                tmpcfg += cfgv6

            elif want_ipv4 and want_ipv6:
                tmpcfg += cfgv4
                tmpcfg += cfgv6
                tmpcfg += cfgvall

            tmpcfg += '!\n'

            if want_ipv4 or want_ipv6:
                cfg += tmpcfg

        cfg += '! ISIS configuration\n'

        if node.enable_ipv4 or node.enable_ipv6:
            cfg += 'log file /tmp/quagga-isis-%s.log\n' % node.name
            cfg += 'router isis 1\n'
            cfg += '  net %s\n' % cls.get_ISIS_ID(cls.routerid(node), str(node.netid))
            cfg += '  metric-style wide\n'
            cfg += '!\n'

        return cfg
Пример #11
0
 def addrstr(x):
     ''' helper for mapping IP addresses to zebra config statements
     '''
     if isIPv4Address(x):
         return 'ip address %s' % x
     elif isIPv6Address(x):
         return 'ipv6 address %s' % x
     else:
         raise Value('invalid address: %s').with_traceback(x)
Пример #12
0
    def generateQuaggaConf(cls, node, services):
        ''' Returns configuration file text. Other services that depend on zebra
           will have generatequaggaifcconfig() and generatequaggaconfig()
           hooks that are invoked here.
        '''
        # we could verify here that filename == Quagga.conf
        cfg = ""
        for ifc in node.netifs():
            cfg += "interface %s\n" % ifc.name
            # include control interfaces in addressing but not routing daemons
            if hasattr(ifc, 'control') and ifc.control == True:
                cfg += "  "
                cfg += "\n  ".join(map(cls.addrstr, ifc.addrlist))
                cfg += "\n"
                continue
            cfgv4 = ""
            cfgv6 = ""
            want_ipv4 = False
            want_ipv6 = False
            for s in services:
                if cls._name not in s._depends:
                    continue
                ifccfg = s.generatequaggaifcconfig(node, ifc)
                if s._ipv4_routing:
                    want_ipv4 = True
                if s._ipv6_routing:
                    want_ipv6 = True
                    cfgv6 += ifccfg
                else:
                    cfgv4 += ifccfg

            if want_ipv4:
                ipv4list = filter(lambda x: isIPv4Address(x.split('/')[0]),
                                  ifc.addrlist)
                cfg += "  "
                cfg += "\n  ".join(map(cls.addrstr, ipv4list))
                cfg += "\n"
                cfg += cfgv4
            if want_ipv6:
                ipv6list = filter(lambda x: isIPv6Address(x.split('/')[0]),
                                  ifc.addrlist)
                cfg += "  "
                cfg += "\n  ".join(map(cls.addrstr, ipv6list))
                cfg += "\n"
                cfg += cfgv6
            cfg += "!\n"

        for s in services:
            if cls._name not in s._depends:
                continue
            cfg += s.generatequaggaconfig(node)
        return cfg
Пример #13
0
    def generateQuaggaConf(cls, node, services):
        ''' Returns configuration file text. Other services that depend on zebra
           will have generatequaggaifcconfig() and generatequaggaconfig()
           hooks that are invoked here.
        '''
        # we could verify here that filename == Quagga.conf
        cfg = ""
        for ifc in node.netifs():
            cfg += "interface %s\n" % ifc.name
            # include control interfaces in addressing but not routing daemons
            if hasattr(ifc, 'control') and ifc.control == True:
                cfg += "  "
                cfg += "\n  ".join(map(cls.addrstr, ifc.addrlist))
                cfg += "\n"
                continue
            cfgv4 = ""
            cfgv6 = ""
            want_ipv4 = False
            want_ipv6 = False
            for s in services:
                if cls._name not in s._depends:
                    continue
                ifccfg = s.generatequaggaifcconfig(node, ifc)
                if s._ipv4_routing:
                    want_ipv4 = True
                if s._ipv6_routing:
                    want_ipv6 = True
                    cfgv6 += ifccfg
                else:
                    cfgv4 += ifccfg

            if want_ipv4:
                ipv4list = filter(lambda x: isIPv4Address(x.split('/')[0]),
                                  ifc.addrlist)
                cfg += "  "
                cfg += "\n  ".join(map(cls.addrstr, ipv4list))
                cfg += "\n"
                cfg += cfgv4
            if want_ipv6:
                ipv6list = filter(lambda x: isIPv6Address(x.split('/')[0]),
                                  ifc.addrlist)
                cfg += "  "
                cfg += "\n  ".join(map(cls.addrstr, ipv6list))
                cfg += "\n"
                cfg += cfgv6
            cfg += "!\n"

        for s in services:
            if cls._name not in s._depends:
                continue
            cfg += s.generatequaggaconfig(node)
        return cfg
Пример #14
0
    def nodewalker_asroot_dns_find_hosts_in_as_callback(startnode, currentnode):
        """ add any host from the AS of startnode to hostlist and return it """
        hosts = []
        # element in hosts: tuple(server-fqdn, server-ipaddr, zone that host lives in)

        if hasattr(currentnode, 'netid') and not currentnode.netid is None:
            netid = currentnode.netid
        else:
            # TODO: netid 0 is invalid
            netid = 0
        zone = "AS%s.virtual." % str(netid)

        # ignore AS authoritative servers as they are already included
        #if not service_flags.DNSASRootServer in currentnode.services and \
        if currentnode.netid == startnode.netid:

            # add plain hostname
            server_name = currentnode.name
            for ipversion in currentnode.getIPversions():
                if ipversion in startnode.getIPversions():
                    server_addr = currentnode.getLoopback(ipversion)
                    server_addr = str(server_addr).partition('/')[0]
                    hosts.append((server_name, server_addr, zone))

            # add all interface names
            for intf in list(currentnode._netif.values()):
                server_name = '%s.%s' % (intf.name, currentnode.name)
                # use first v4 and first v6 address of this interface
                v4addr = None
                v6addr = None
                for addr in intf.addrlist:
                    addr = addr.partition('/')[0]
                    if not v4addr is None and not v6addr is None:
                        break
                    if v4addr is None and isIPv4Address(addr):
                        v4addr = addr
                    if v6addr is None and isIPv6Address(addr):
                        v6addr = addr

                if not v4addr is None and 4 in currentnode.getIPversions() and \
                        4 in startnode.getIPversions():
                    hosts.append((server_name, v4addr, zone))
                if not v6addr is None and 6 in currentnode.getIPversions() and \
                        6 in startnode.getIPversions():
                    hosts.append((server_name, v6addr, zone))

        return hosts
Пример #15
0
 def nodewalker_if_verbose_callback(startnode, currentnode):
     result = []
     #if currentnode.enable_ipv6 and startnode.enable_ipv6:
     #    result.append(str(currentnode.getLoopbackIPv6()))
     if currentnode.enable_ipv4 and startnode.enable_ipv4:
         for intf in currentnode._netif.values():
             for addr in intf.addrlist:
                 if isIPv4Address(addr):
                     result.extend([addr.partition('/')[0],
                     ' ', currentnode.name, '\n'])
     if currentnode.enable_ipv6 and startnode.enable_ipv6:
         for intf in currentnode._netif.values():
             for addr in intf.addrlist:
                 if isIPv6Address(addr):
                     result.extend([addr.partition('/')[0],
                     ' ', currentnode.name, '\n'])
     return result
Пример #16
0
    def nodewalker_callback(startnode, currentnode):
        result = []

        hostname = '%s.AS%s.virtual' % (currentnode.name,
                str(currentnode.netid))

        if currentnode.enable_ipv6 and startnode.enable_ipv6:
            result.extend([hostname, ' AAAA ',
                    str(currentnode.getLoopbackIPv6()), '\n'])
            # TODO: in order to check PTR records, convert IP addr to PTR-style
            #result.extend([str(currentnode.getLoopbackIPv6()), ' PTR ',
            #        hostname, '\n'])

        if currentnode.enable_ipv4 and startnode.enable_ipv4:
            result.extend([hostname, ' A ',
                    str(currentnode.getLoopbackIPv4()), '\n'])
            # TODO: in order to check PTR records, convert IP addr to PTR-style
            #result.extend([str(currentnode.getLoopbackIPv4()), ' PTR ',
            #        hostname, '\n'])

        if currentnode.enable_ipv4 and startnode.enable_ipv4:
            for intf in currentnode._netif.values():
                if hasattr(intf, 'control') and intf.control == True:
                    continue
                for addr in intf.addrlist:
                    if isIPv4Address(addr):
                        result.extend(['%s.%s' % (intf.name, hostname), ' A ',
                                addr.partition('/')[0], '\n'])
                        # TODO: in order to check PTR records, convert IP addr to PTR-style
                        #result.extend([addr.partition('/')[0], ' PTR ',
                        #        '%s.%s' % (intf.name, hostname), '\n'])

        if currentnode.enable_ipv6 and startnode.enable_ipv6:
            for intf in currentnode._netif.values():
                if hasattr(intf, 'control') and intf.control == True:
                    continue
                for addr in intf.addrlist:
                    if isIPv6Address(addr):
                        result.extend(['%s.%s' % (intf.name, hostname),
                                ' AAAA ', addr.partition('/')[0], '\n'])
                        # TODO: in order to check PTR records, convert IP addr to PTR-style
                        #result.extend([addr.partition('/')[0], ' PTR ',
                        #        '%s.%s' % (intf.name, hostname), '\n'])

        return result
Пример #17
0
 def nodewalker_if_callback(startnode, currentnode):
     result = []
     #if currentnode.enable_ipv6 and startnode.enable_ipv6:
     #    result.append(str(currentnode.getLoopbackIPv6()))
     if currentnode.enable_ipv4 and startnode.enable_ipv4:
         for intf in currentnode._netif.values():
             if hasattr(intf, 'control') and intf.control == True:
                 continue
             for addr in intf.addrlist:
                 if isIPv4Address(addr):
                     result.extend([addr.partition('/')[0], '\n'])
     if currentnode.enable_ipv6 and startnode.enable_ipv6:
         for intf in currentnode._netif.values():
             if hasattr(intf, 'control') and intf.control == True:
                 continue
             for addr in intf.addrlist:
                 if isIPv6Address(addr):
                     result.extend([addr.partition('/')[0], '\n'])
     return result
Пример #18
0
    def generateDelegationRecord(cls, delegation_servers, zone):
        delegationitems = []
        delegationitems.append('$ORIGIN %s\n' % zone)
        tmp_servers = [server for server, server_addr in delegation_servers]
        # add each server once but only once (that's why the set is there)
        for server in set(tmp_servers):
            delegationitems.append('@ IN NS %s\n' % (server))

        for server, server_addr in delegation_servers:
            recordtype = ''
            if isIPv4Address(server_addr):
                recordtype = 'A'
            elif isIPv6Address(server_addr):
                recordtype = 'AAAA'
            else:
                raise ValueError
            delegationitems.append('%s %s %s\n' % (server, recordtype, server_addr))

        return ''.join(delegationitems)
Пример #19
0
    def generateconfig(cls, node, filename, services):
        cfg = "#!/bin/sh\n"
        cfg += "# auto-generated by DefaultRoute service (utility.py)\n"
        for ifc in node.netifs():
            for idx, net_netif in list(ifc.net._netif.items()):
                # do not include control interfaces
                if hasattr(ifc, 'control') and ifc.control == True:
                    continue

                # skip our own interface
                if ifc == net_netif:
                    continue

                for addr in net_netif.addrlist:
                    # only core routers are candidate gateways
                    if not service_flags.Router in net_netif.node.services:
                        continue
                    if node.enable_ipv4 and isIPv4Address(addr):
                        cfg += cls.addrstr(addr)
                    if node.enable_ipv6 and isIPv6Address(addr):
                        cfg += cls.addrstr(addr)
        return cfg
Пример #20
0
    def generate_network_statement(cls, node, ifc):
        cfg = []
        # find any link on which two equal netid's (i.e., AS numbers) are
        # present and configure an ospf-session on this interface
        # on all other interfaces, disable ospf
        for idx, net_netif in list(ifc.net._netif.items()):

            # skip our own interface
            if ifc == net_netif:
                continue
            # skip control interface
            if hasattr(ifc, 'control') and ifc.control == True:
                continue

            # found the same AS, enable IGP/OSPF
            if node.netid == net_netif.node.netid:
                if not service_flags.Router in net_netif.node.services:
                    cfg.append('  passive-interface %s\n' % ifc.name)
                for a in ifc.addrlist:
                    if not isIPv4Address(a):
                        continue
                    cfg.append('  network %s area 0.0.0.0\n' % a)
        return cfg
Пример #21
0
 def get_ipv4_addresses(self):
     return [addr for addr in self.__addresses__ if isIPv4Address(addr)]
Пример #22
0
    def getAndGeneratePTRZonesASAuthServer(cls, node):
        """ returns a list of all reverse zones a root dns server serves """
        # find dns as authoritative servers
        # (server_name, server_addr, zone)
        as_auth_servers = []
        service_helpers.nodewalker(node, node, as_auth_servers,
                cls.nodewalker_root_dns_find_all_auth_servers_callback)
        as_auth_servers = [('%s.%s' % (server_name, zone), server_addr, zone) \
                for server_name, server_addr, zone in as_auth_servers]
        # zone = "AS%s.virtual." % str(netid)

        zonenames = []

        if hasattr(node, 'netid') and not node.netid is None:
            netid = node.netid
        else:
            # TODO: netid 0 is invalid
            netid = 0
        asn = netid

        for ipversion in node.getIPversions():
            # collect loopback address space
            loopback_net = Loopback.getLoopbackNet_per_net(\
                    node.session.sessionid, netid, ipversion)
            print(('[DEBUG] loopback_net IPv%d: %s' % (ipversion, loopback_net)))

            # collect interface address space
            interface_net = Interface.getInterfaceNet_per_net(\
                    node.session.sessionid, netid, ipversion)
            print(('[DEBUG] interface_net IPv%d: %s' % (ipversion, interface_net)))

            if ipversion == 4:
                auth_servers = [(server_name, server_addr) \
                        for server_name, server_addr, zone in as_auth_servers \
                        if zone == "AS%s.virtual." % str(netid) and \
                        isIPv4Address(server_addr)]
            elif ipversion == 6:
                auth_servers = [(server_name, server_addr) \
                        for server_name, server_addr, zone in as_auth_servers \
                        if zone == "AS%s.virtual." % str(netid) and \
                        isIPv6Address(server_addr)]
            else:
                raise ValueError

            for asn_net in loopback_net, interface_net:
                zonename = cls.getPTRZoneNameFromPrefix(cls, asn_net)
                print(('[DEBUG] zonename: %s' % zonename))

                ORIGINHeader = '$ORIGIN %s\n' % zonename
                print(('[DEBUG] ORIGINHeader: %s' % ORIGINHeader))

                SOAHeader = cls.generateSOAHeader(cls, auth_servers, zonename)
                print(('[DEBUG] SOAHeader:\n%s' % SOAHeader))

                zoneentries = []

                # get host list of this AS
                # TODO: iterating over all nodes for interface and
                # loopback address space is expensive. and we are only talking
                # about IPv4 or IPv6 at the moment.
                # is there a better way of doing this?
                hosts = []
                service_helpers.nodewalker(node, node, hosts,
                        cls.nodewalker_asroot_dns_find_hosts_in_as_callback)
                for hostname, asn_addr, zone in hosts:
                    if ipversion == 4 and not isIPv4Address(asn_addr):
                        continue
                    if ipversion == 6 and not isIPv6Address(asn_addr):
                        continue

                    if ipversion == 4:
                        asn_addr = IPv4Addr(asn_addr)
                    elif ipversion == 6:
                        asn_addr = IPv6Addr(asn_addr)
                    else:
                        raise ValueError

                    if asn_addr < asn_net.minaddr() or \
                            asn_addr > asn_net.maxaddr():
                        continue

                    # set prefix length. just to be sure
                    asn_addr.set_prefixlen(asn_net.prefixlen)
                    asn_ptr_name = cls.getPTR_CNAME_FromAddr(cls, asn_addr)

                    print(('[DEBUG] ASN PTR addr (IPv%d): %s' %
                            (ipversion, str(asn_addr))))

                    print(('[DEBUG] adding: "%s IN PTR %s.AS%s.virtual.' %
                            (asn_ptr_name, hostname, str(netid))))
                    zoneentries.append(('%s IN PTR %s.AS%s.virtual.' %
                            (asn_ptr_name, hostname, str(netid))))

                print(('[DEBUG] PTR records: %s' % (zoneentries)))

                zonecontents = '%s\n%s\n%s\n' % (ORIGINHeader, SOAHeader,
                        '\n'.join(zoneentries))
                cls.writeZoneFile(cls, node, zonename, zonecontents)
                print(('[DEBUG] adding ptrzone: %s' % zonename))
                zonenames.append(zonename)

        return zonenames
Пример #23
0
    def getAndGeneratePTRZonesRootServer(cls, node):
        """ returns a list of all reverse zones a root dns server serves """

        # find dns root servers
        # (server_name, server_addr)
        rootservers = []
        service_helpers.nodewalker(node, node, rootservers,
                cls.nodewalker_find_root_dns_callback)
        rootservers = [('%s.' % server_name, server_addr) \
                for server_name, server_addr in rootservers]
        # find dns as authoritative servers
        # (server_name, server_addr, zone)
        as_auth_servers = []
        service_helpers.nodewalker(node, node, as_auth_servers,
                cls.nodewalker_root_dns_find_all_auth_servers_callback)
        as_auth_servers = [('%s.%s' % (server_name, zone), server_addr, zone) \
                for server_name, server_addr, zone in as_auth_servers]

        zonenames = []

        SOAHeader = cls.generateSOAHeader(cls, rootservers, '.')
        print(('[DEBUG] SOAHeader:\n%s' % SOAHeader))

        for ipversion in node.getIPversions():
            # collect loopback address space
            loopback_net = Loopback.getLoopbackNet(ipversion)
            print(('[DEBUG] loopback_net IPv%d: %s' % (ipversion, loopback_net)))

            # collect interface address space
            interface_net = Interface.getInterfaceNet(ipversion)
            print(('[DEBUG] interface_net IPv%d: %s' % (ipversion, interface_net)))

            # get all deployed ASN's
            asns = list(NetIDNodeMap.mapping[node.session.sessionid].keys())
            print(('[DEBUG] deployed ASN\'s: %s' % asns))
            for net in loopback_net, interface_net:
                zonename = cls.getPTRZoneNameFromPrefix(cls, net)
                net_prefixlen = net.prefixlen
                print(('[DEBUG] zonename: %s' % zonename))

                ORIGINHeader = '$ORIGIN %s\n' % zonename
                print(('[DEBUG] ORIGINHeader: %s' % ORIGINHeader))

                zoneentries = []
                for asn in asns:
                    # get AS address space
                    if net == loopback_net:
                        asn_net = Loopback.getLoopbackNet_per_net(\
                                node.session.sessionid, asn, ipversion)
                    elif net == interface_net:
                        asn_net = Interface.getInterfaceNet_per_net(\
                                node.session.sessionid, asn, ipversion)

                    # find authoritative AS dns servers
                    # zone == "AS%s.virtual." % str(netid)
                    for server_name, server_addr, zone in as_auth_servers:
                        server_asn = zone.lstrip('AS')
                        server_asn = int(server_asn[:server_asn.find('.')])

                        # not the correct asn
                        if not asn == server_asn:
                            continue

                        # not our IP version
                        if ipversion == 4 and not isIPv4Address(server_addr):
                            continue
                        if ipversion == 6 and not isIPv6Address(server_addr):
                            continue

                        print(('[DEBUG] server_name: %s, server_addr: %s, zone: %s' %
                                (server_name, server_addr, zone)))

                        if ipversion == 4:
                            # get host list of this AS
                            # TODO: iterating over all nodes for each AS for interface and
                            # loopback address space is expensive. and we are only talking
                            # about IPv4 at the moment. is there a better way of doing this?
                            hosts = []
                            # TODO: tmp. setting another netid of a node is a dirty hack
                            tmpnetid = node.netid
                            node.netid = server_asn
                            service_helpers.nodewalker(node, node, hosts,
                                    cls.nodewalker_asroot_dns_find_hosts_in_as_callback)
                            node.netid = tmpnetid
                            for hostname, asn_addr, zone in hosts:
                                if not isIPv4Address(asn_addr):
                                    continue

                                asn_addr = IPv4Addr(asn_addr)

                                print(('[DEBUG] asn_addr(%s) in asn_net(%s)' %
                                        (str(asn_addr), str(asn_net))))

                                if asn_addr < asn_net.minaddr() or \
                                        asn_addr > asn_net.maxaddr():
                                    continue

                                # set prefix length of the supernet
                                asn_addr.set_prefixlen(net_prefixlen)
                                asn_ptr_name = cls.getPTR_CNAME_FromAddr(cls, asn_addr)

                                #print(('[DEBUG] deployed ASN network (IPv%d): %s' %
                                #        (ipversion, str(asn_net))))
                                print(('[DEBUG] ASN PTR addr (IPv%d): %s' %
                                        (ipversion, str(asn_addr))))

                                print(('[DEBUG] adding: "%s IN NS %s"' %
                                        (asn_ptr_name, server_name)))
                                zoneentries.append(('%s IN NS %s' %
                                        (asn_ptr_name, server_name)))
                        elif ipversion == 6:
                            asn_ptr_name = cls.getPTRZoneNameFromPrefix(cls, asn_net)
                            print(('[DEBUG] adding: "%s IN NS %s"' %
                                    (asn_ptr_name, server_name)))
                            zoneentries.append(('%s IN NS %s' %
                                    (asn_ptr_name, server_name)))

                print(('[DEBUG] subnet name servers: %s' % (zoneentries)))

                zonecontents = '%s\n%s\n%s\n' % (ORIGINHeader, SOAHeader,
                        '\n'.join(zoneentries))
                cls.writeZoneFile(cls, node, zonename, zonecontents)
                print(('[DEBUG] adding ptrzone to zonenames: %s' % zonename))
                zonenames.append(zonename)

        return zonenames
Пример #24
0
    def add_link(self, link):
        def is_ptp(link):
            return (not link.get_src_node().get_type() == 'lanswitch' and \
                    not link.get_dst_node().get_type() == 'lanswitch')

        # TODO: refactor me

        #print('[TRACE] add_link(link=%s)' % str(link))
        # TODO: raise if link_cnt > 255 / if addr > ipv4_interface_net/'ipv4_interface_net_per_netid'

        asn = link.get_src_node().get_asn()
        #print('[DEBUG] ASN of src_node: %d' % asn)
        ptp = is_ptp(link)
        #print('[DEBUG] is PTP: %s' % ptp)

        # generate which interfaces
        generate_src_if = False
        src_interface = link.get_src_interface()
        generate_dst_if = False
        dst_interface = link.get_dst_interface()
        src_if_ipv4_addr = None
        dst_if_ipv4_addr = None
        src_if_ipv6_addr = None
        dst_if_ipv6_addr = None

        # case: both interfaces of this link have no addresses set
        if link.get_src_interface() is None or link.get_dst_interface() is None:
            if ptp:
                link_ipv4_prefix = self.__as_get_next_link_ipv4_prefix__(asn, ptp=ptp)
                #print('[DEBUG] ipv4 link_prefix: %s' % str(link_ipv4_prefix))
                src_if_ipv4_addr = link_ipv4_prefix.minaddr()
                src_if_ipv4_addr.set_prefixlen(link_ipv4_prefix.prefixlen)
                dst_if_ipv4_addr = link_ipv4_prefix.maxaddr()
                dst_if_ipv4_addr.set_prefixlen(link_ipv4_prefix.prefixlen)

                link_ipv6_prefix = self.__as_get_next_link_ipv6_prefix__(asn)
                #print('[DEBUG] ipv6 link_prefix: %s' % str(link_ipv6_prefix))
                src_if_ipv6_addr = link_ipv6_prefix.minaddr()
                src_if_ipv6_addr.set_prefixlen(link_ipv6_prefix.prefixlen)

                # when using >=/64 for ptp-links, use next line
                if link_ipv6_prefix.prefixlen >= 64:
                    #dst_if_ipv6_addr = link_ipv6_prefix.maxaddr()
                    dst_if_ipv6_addr = src_if_ipv6_addr + 1
                    dst_if_ipv6_addr.set_prefixlen(link_ipv6_prefix.prefixlen)
                else:
                    # when using </64 (63,62,..) for ptp-links, use next line
                    dst_prefix = IPv6Prefix('%s/%s' % (str(src_if_ipv6_addr),
                            str(link_ipv6_prefix.prefixlen + 1)))
                    # intentionally overflow to next prefix
                    # (skip brdcst, network, select first addr of following prefix)
                    dst_if_ipv6_addr = dst_prefix.maxaddr() + 3
                    dst_if_ipv6_addr.set_prefixlen(link_ipv6_prefix.prefixlen)

                if link.get_src_interface() is None:
                    generate_src_if = True
                if link.get_dst_interface() is None:
                    generate_dst_if = True
            else:
                # not point-to-point-link
                # this means, that there is a switch between src and dst
                # find igp_node (router) behind the switch and use it's subnet
                # as address space for connected nodes
                switch = None
                if link.get_src_node().get_type() == 'lanswitch':
                    switch = link.get_src_node()
                    generate_dst_if = True
                elif link.get_dst_node().get_type() == 'lanswitch':
                    switch = link.get_dst_node()
                    generate_src_if = True

                # give me all links that this switch currently has
                for node_link in self.get_links_of_node(switch):
                    for node, interface in node_link.nodes:
                        if node is switch:
                            continue
                        # found the igp_node (router) behind the switch
                        if node.get_tag() == 'igp':
                            if len(interface.get_addresses()) == 1 and \
                                    interface.get_addresses()[0] is None:
                                #print('[DEBUG] igp_node does not yet have an addr on its interface')
                                pass
                            else:
                                # TODO: this is kinda wrong. what happens when there are more than
                                # one addresses assigned?
                                for base_addr in interface.get_addresses():
                                    ifc_key = interface.get_key()
                                    #print('[DEBUG] base addr of igp_node (if idx: %s) behind switch: %s'
                                    #        % (ifc_key, base_addr))
                                    if isIPv4Address(base_addr):
                                        # set src and dst to the same addr (we only assign one of them. see below)
                                        if not node in self.__bookkeeping__['ipv4_brdcst_max_addr']:
                                            self.__bookkeeping__['ipv4_brdcst_max_addr'][node] = {}
                                        if not ifc_key in self.__bookkeeping__['ipv4_brdcst_max_addr'][node]:
                                            self.__bookkeeping__['ipv4_brdcst_max_addr'][node][ifc_key] = base_addr

                                        self.__bookkeeping__['ipv4_brdcst_max_addr'][node][ifc_key] += 1
                                        src_if_ipv4_addr = self.__bookkeeping__['ipv4_brdcst_max_addr'][node][ifc_key]
                                        src_if_ipv4_addr.set_prefixlen(base_addr.prefixlen)
                                        dst_if_ipv4_addr = src_if_ipv4_addr
                                    elif isIPv6Address(base_addr):
                                        # set src and dst to the same addr (we only assign one of them. see below)
                                        if not node in self.__bookkeeping__['ipv6_brdcst_max_addr']:
                                            self.__bookkeeping__['ipv6_brdcst_max_addr'][node] = {}
                                        if not ifc_key in self.__bookkeeping__['ipv6_brdcst_max_addr'][node]:
                                            self.__bookkeeping__['ipv6_brdcst_max_addr'][node][ifc_key] = base_addr
                                        self.__bookkeeping__['ipv6_brdcst_max_addr'][node][ifc_key] += 1
                                        src_if_ipv6_addr = self.__bookkeeping__['ipv6_brdcst_max_addr'][node][ifc_key]
                                        src_if_ipv6_addr.set_prefixlen(base_addr.prefixlen)
                                        dst_if_ipv6_addr = src_if_ipv6_addr

                if len(self.get_links_of_node(switch)) == 0:
                    #print('[DEBUG] switch does not yet have any registered links')
                    link_ipv4_prefix = self.__as_get_next_link_ipv4_prefix__(asn, ptp=ptp)
                    #print('[DEBUG] ipv4 link_prefix: %s' % str(link_ipv4_prefix))

                    # set src and dst to the same addr (we only assign one of them. see below)
                    src_if_ipv4_addr = link_ipv4_prefix.minaddr()
                    src_if_ipv4_addr.set_prefixlen(link_ipv4_prefix.prefixlen)
                    dst_if_ipv4_addr = src_if_ipv4_addr

                    link_ipv6_prefix = self.__as_get_next_link_ipv6_prefix__(asn, ptp=ptp)
                    #print('[DEBUG] ipv6 link_prefix: %s' % str(link_ipv6_prefix))
                    src_if_ipv6_addr = link_ipv6_prefix.minaddr()
                    src_if_ipv6_addr.set_prefixlen(link_ipv6_prefix.prefixlen)
                    dst_if_ipv6_addr = src_if_ipv6_addr

        if generate_src_if:
            #print('[DEBUG] link: src ipv4 address: %s/%s' % (src_if_ipv4_addr,
            #        str(src_if_ipv4_addr.get_prefixlen())))
            #print('[DEBUG] link: src ipv6 address: %s/%s' % (src_if_ipv6_addr,
            #        str(src_if_ipv6_addr.get_prefixlen())))

            # don't assign an IP address to a switch interface
            if link.get_src_node().get_type() == 'lanswitch':
                #print('[DEBUG] node type is lanswitch')
                src_interface = link.get_src_node().create_interface([])
            else:
                src_interface = link.get_src_node().create_interface([
                    src_if_ipv4_addr, src_if_ipv6_addr])
            #print('[DEBUG] adding link_src: (%s, %s)' % (link.get_src_node().get_name(), src_interface))
            link.set_src(link.get_src_node(), src_interface)

        if src_interface is None:
            #print('[DEBUG] src_interface is None: %s' % str(src_interface))
            src_interface = link.get_src_node().create_interface([])
            link.set_src(link.get_src_node(), src_interface)

        if generate_dst_if:
            #print('[DEBUG] link: dst ipv4 address: %s/%s' % (dst_if_ipv4_addr,
            #        str(dst_if_ipv4_addr.get_prefixlen())))
            #print('[DEBUG] link: dst ipv6 address: %s/%s' % (dst_if_ipv6_addr,
            #        str(dst_if_ipv6_addr.get_prefixlen())))

            # don't assign an IP address to a switch interface
            if link.get_dst_node().get_type() == 'lanswitch':
                #print('[DEBUG] node type is lanswitch')
                dst_interface = link.get_dst_node().create_interface([])
            else:
                dst_interface = link.get_dst_node().create_interface([
                    dst_if_ipv4_addr, dst_if_ipv6_addr])
            #print('[DEBUG] adding link_dst: (%s, %s)' % (link.get_dst_node().get_name(), dst_interface))
            link.set_dst(link.get_dst_node(), dst_interface)

        if dst_interface is None:
            dst_interface = link.get_dst_node().create_interface([])
            link.set_dst(link.get_dst_node(), dst_interface)

        self.__links__.append(link)
Пример #25
-1
 def newnetif(self, net = None, addrlist = [], hwaddr = None,
              ifindex = None, ifname = None):
     self.lock.acquire()
     try:
         if isinstance(net, EmaneNode):
             ifindex = self.newtuntap(ifindex = ifindex, ifname = ifname,
                                      net = net)
             # TUN/TAP is not ready for addressing yet; the device may
             #   take some time to appear, and installing it into a
             #   namespace after it has been bound removes addressing;
             #   save addresses with the interface now
             self.attachnet(ifindex, net)
             netif = self.netif(ifindex)
             netif.sethwaddr(hwaddr)
             for addr in maketuple(addrlist):
                 if self.enable_ipv4 and isIPv4Address(addr) or \
                         self.enable_ipv6 and isIPv6Address(addr):
                     netif.addaddr(addr)
             return ifindex
         else:
             ifindex = self.newveth(ifindex = ifindex, ifname = ifname,
                                    net = net)
         if net is not None:
             self.attachnet(ifindex, net)
         if hwaddr:
             self.sethwaddr(ifindex, hwaddr)
         for addr in maketuple(addrlist):
             if self.enable_ipv4 and isIPv4Address(addr) or \
                     self.enable_ipv6 and isIPv6Address(addr):
                 self.addaddr(ifindex, addr)
         self.ifup(ifindex)
         return ifindex
     finally:
         self.lock.release()