def start(self): if ip.valid_ipv6(self._address): server = hub.listen((self._address, self._port), family=socket.AF_INET6) else: server = hub.listen((self._address, self._port)) key = self.CONF.ovsdb.mngr_privkey or self.CONF.ctl_privkey cert = self.CONF.ovsdb.mngr_cert or self.CONF.ctl_cert if key is not None and cert is not None: ssl_kwargs = dict(keyfile=key, certfile=cert, server_side=True) if self.CONF.ca_certs is not None: ssl_kwargs['cert_reqs'] = ssl.CERT_REQUIRED ssl_kwargs['ca_certs'] = self.CONF.ca_certs server = ssl.wrap_socket(server, **ssl_kwargs) self._server = server if ip.valid_ipv6(self._address): self.logger.info('Listening on [%s]:%s for clients', self._address, self._port) else: self.logger.info('Listening on %s:%s for clients', self._address, self._port) t = hub.spawn(self._accept, self._server) super(OVSDB, self).start() return t
def _split_addr(addr): """ Splits a str of IP address and port pair into (host, port). Example:: >>> _split_addr('127.0.0.1:6653') ('127.0.0.1', 6653) >>> _split_addr('[::1]:6653') ('::1', 6653) Raises ValueError if invalid format. :param addr: A pair of IP address and port. :return: IP address and port """ e = ValueError('Invalid IP address and port pair: "%s"' % addr) pair = addr.rsplit(':', 1) if len(pair) != 2: raise e addr, port = pair if addr.startswith('[') and addr.endswith(']'): addr = addr.lstrip('[').rstrip(']') if not ip.valid_ipv6(addr): raise e elif not ip.valid_ipv4(addr): raise e return addr, int(port, 0)
def ip_address_add(session, ifname, ifaddr): """ Adds an IP address to interface record identified with the given "ifname". The arguments are similar to "ip address add" command of iproute2. :param session: Session instance connecting to database. :param ifname: Name of interface. :param ifaddr: IPv4 or IPv6 address. :return: Instance of record or "None" if failed. """ def _append_inet_addr(intf_inet, addr): addr_list = intf_inet.split(',') if addr in addr_list: LOG.debug('Interface "%s" has already "ifaddr": %s', intf.ifname, addr) return intf_inet else: addr_list.append(addr) return ','.join(addr_list) intf = ip_link_show(session, ifname=ifname) if not intf: LOG.debug('Interface "%s" does not exist', ifname) return None if ip.valid_ipv4(ifaddr): intf.inet = _append_inet_addr(intf.inet, ifaddr) elif ip.valid_ipv6(ifaddr): intf.inet6 = _append_inet_addr(intf.inet6, ifaddr) else: LOG.debug('Invalid IP address for "ifaddr": %s', ifaddr) return None return intf
def __init__(self, listen_info, handle=None, backlog=None, spawn='default', **ssl_args): assert backlog is None assert spawn == 'default' if ip.valid_ipv6(listen_info[0]): self.server = eventlet.listen(listen_info, family=socket.AF_INET6) elif os.path.isdir(os.path.dirname(listen_info[0])): # Case for Unix domain socket self.server = eventlet.listen(listen_info[0], family=socket.AF_UNIX) else: self.server = eventlet.listen(listen_info) if ssl_args: def wrap_and_handle(sock, addr): ssl_args.setdefault('server_side', True) handle(ssl.wrap_socket(sock, **ssl_args), addr) self.handle = wrap_and_handle else: self.handle = handle
def validate_bgp_server_hosts(hosts): for host in hosts: if not ip.valid_ipv4(host) and not ip.valid_ipv6(host): raise ConfigTypeError(desc=('Invalid bgp sever hosts ' 'configuration value %s' % hosts)) return hosts
def create_connection(address): """ Wrapper for socket.create_connection() function. If *address* (a 2-tuple ``(host, port)``) contains a valid IPv4/v6 address, passes *address* to socket.create_connection(). If *host* is valid path to Unix Domain socket, tries to connect to the server listening on the given socket. :param address: IP address or path to Unix Domain socket. :return: Socket instance. """ host, _port = address if ip.valid_ipv4(host) or ip.valid_ipv6(host): return socket.create_connection(address) elif os.path.exists(host): sock = None try: sock = socket.socket(socket.AF_UNIX, socket.SOCK_STREAM) sock.connect(host) except socket.error as e: if sock is not None: sock.close() raise e return sock else: raise ValueError('Invalid IP address or Unix Socket: %s' % host)
def register_switch_address(addr, interval=None): """ Registers a new address to initiate connection to switch. Registers a new IP address and port pair of switch to let os_ken.controller.controller.OpenFlowController to try to initiate connection to switch. :param addr: A tuple of (host, port) pair of switch. :param interval: Interval in seconds to try to connect to switch """ assert len(addr) == 2 assert ip.valid_ipv4(addr[0]) or ip.valid_ipv6(addr[0]) ofp_handler = app_manager.lookup_service_brick(ofp_event.NAME) _TMP_ADDRESSES[addr] = interval def _retry_loop(): # Delays registration if ofp_handler is not started yet while True: if ofp_handler.controller is not None: for a, i in _TMP_ADDRESSES.items(): ofp_handler.controller.spawn_client_loop(a, i) hub.sleep(1) break hub.sleep(1) hub.spawn(_retry_loop)
def _send_ip_route_impl(self, prefix, nexthops=None, safi=packet_safi.UNICAST, flags=zebra.ZEBRA_FLAG_INTERNAL, distance=None, metric=None, mtu=None, tag=None, is_withdraw=False): if ip.valid_ipv4(prefix): if is_withdraw: msg_cls = zebra.ZebraIPv4RouteDelete else: msg_cls = zebra.ZebraIPv4RouteAdd elif ip.valid_ipv6(prefix): if is_withdraw: msg_cls = zebra.ZebraIPv6RouteDelete else: msg_cls = zebra.ZebraIPv6RouteAdd else: raise ValueError('Invalid prefix: %s' % prefix) nexthop_list = [] for nexthop in nexthops: if ip.valid_ipv4(nexthop): nexthop_list.append(zebra.NextHopIPv4(addr=nexthop)) elif ip.valid_ipv6(nexthop): nexthop_list.append(zebra.NextHopIPv6(addr=nexthop)) else: raise ValueError('Invalid nexthop: %s' % nexthop) msg = zebra.ZebraMessage(version=self.zserv_ver, body=msg_cls(route_type=self.route_type, flags=flags, message=0, safi=safi, prefix=prefix, nexthops=nexthop_list, distance=distance, metric=metric, mtu=mtu, tag=tag, instance=0)) self.send_msg(msg) return msg
def detect_address_family(host): if ip.valid_ipv4(host): return socket.AF_INET elif ip.valid_ipv6(host): return socket.AF_INET6 elif os.path.isdir(os.path.dirname(host)): return socket.AF_UNIX else: return None
def serialize(self): # fixup if ip.valid_ipv4(self.peer_ip) and ip.valid_ipv4(self.local_ip): self.afi = self.AFI_IPv4 elif ip.valid_ipv6(self.peer_ip) and ip.valid_ipv6(self.local_ip): self.afi = self.AFI_IPv6 else: raise ValueError( 'peer_ip and local_ip must be the same address family: ' 'peer_ip=%s, local_ip=%s' % (self.peer_ip, self.local_ip)) buf = struct.pack(self._HEADER_FMT, self.peer_as, self.local_as, self.if_index, self.afi) buf += ip.text_to_bin(self.peer_ip) buf += ip.text_to_bin(self.local_ip) buf += self.bgp_message.serialize() return buf
def serialize(self): if ip.valid_ipv6(self.ip_addr): # Sets Peer IP Address family bit to IPv6 self.type |= self.IP_ADDR_FAMILY_BIT ip_addr = ip.text_to_bin(self.ip_addr) if self.type & self.AS_NUMBER_SIZE_BIT or self.as_num > 0xffff: # Four octet AS number self.type |= self.AS_NUMBER_SIZE_BIT as_num = struct.pack('!I', self.as_num) else: # Two octet AS number as_num = struct.pack('!H', self.as_num) buf = struct.pack(self._HEADER_FMT, self.type, addrconv.ipv4.text_to_bin(self.bgp_id)) return buf + ip_addr + as_num
def __init__(self, listen_info, handle=None, backlog=None, spawn='default', **ssl_args): assert backlog is None assert spawn == 'default' if ip.valid_ipv6(listen_info[0]): self.server = eventlet.listen(listen_info, family=socket.AF_INET6) elif os.path.isdir(os.path.dirname(listen_info[0])): # Case for Unix domain socket self.server = eventlet.listen(listen_info[0], family=socket.AF_UNIX) else: self.server = eventlet.listen(listen_info) if ssl_args: ssl_args.setdefault('server_side', True) if 'ssl_ctx' in ssl_args: ctx = ssl_args.pop('ssl_ctx') ctx.load_cert_chain(ssl_args.pop('certfile'), ssl_args.pop('keyfile')) if 'cert_reqs' in ssl_args: ctx.verify_mode = ssl_args.pop('cert_reqs') if 'ca_certs' in ssl_args: ctx.load_verify_locations(ssl_args.pop('ca_certs')) def wrap_and_handle_ctx(sock, addr): handle(ctx.wrap_socket(sock, **ssl_args), addr) self.handle = wrap_and_handle_ctx else: def wrap_and_handle_ssl(sock, addr): handle(ssl.wrap_socket(sock, **ssl_args), addr) self.handle = wrap_and_handle_ssl else: self.handle = handle
def _accept(self, server): if self.CONF.ovsdb.whitelist: def check(address): if address in self.CONF.ovsdb.whitelist: return True self.logger.debug('Connection from non-whitelist client ' '(%s:%s)' % address) return False else: def check(address): return True while self.is_active: try: # TODO(jkoelker) SSL Certificate Fingerprint check sock, client_address = server.accept() except: if self.is_active: self.logger.exception('Error accepting connection') continue if not check(client_address[0]): sock.shutdown(socket.SHUT_RDWR) sock.close() continue if ip.valid_ipv6(client_address[0]): self.logger.debug('New connection from [%s]:%s' % client_address[:2]) else: self.logger.debug('New connection from %s:%s' % client_address[:2]) t = hub.spawn(self._start_remote, sock, client_address) self.threads.append(t)
def ip_route_add(session, destination, device=None, gateway='', source='', ifindex=0, route_type=zebra.ZEBRA_ROUTE_KERNEL, is_selected=True): """ Adds a route record into Zebra protocol service database. The arguments are similar to "ip route add" command of iproute2. If "is_selected=True", disables the existing selected route for the given destination. :param session: Session instance connecting to database. :param destination: Destination prefix. :param device: Source device. :param gateway: Gateway IP address. :param source: Source IP address. :param ifindex: Index of source device. :param route_type: Route type of daemon (or kernel). :param is_selected: If select the given route as "in use" or not. :return: Instance of record or "None" if failed. """ if device: intf = interface.ip_link_show(session, ifname=device) if not intf: LOG.debug('Interface "%s" does not exist', device) return None ifindex = ifindex or intf.ifindex route = ip_route_show(session, destination=destination, device=device) if route: LOG.debug( 'Route to "%s" already exists on "%s" device', destination, device) return route dest_addr, dest_prefix_num = destination.split('/') dest_prefix_num = int(dest_prefix_num) if ip.valid_ipv4(dest_addr) and 0 <= dest_prefix_num <= 32: family = socket.AF_INET elif ip.valid_ipv6(dest_addr) and 0 <= dest_prefix_num <= 128: family = socket.AF_INET6 else: LOG.debug('Invalid IP address for "prefix": %s', destination) return None safi = packet_safi.UNICAST if is_selected: old_routes = ip_route_show_all( session, destination=destination, is_selected=True) for old_route in old_routes: if old_route: LOG.debug('Set existing route to unselected: %s', old_route) old_route.is_selected = False new_route = Route( family=family, safi=safi, destination=destination, gateway=gateway, ifindex=ifindex, source=source, route_type=route_type, is_selected=is_selected) session.add(new_route) return new_route
def valid_ip_address(addr): if not ip.valid_ipv4(addr) and not ip.valid_ipv6(addr): return False return True
def is_valid_ipv6(ipv6): """Returns True if given `ipv6` is a valid IPv6 address """ return ip.valid_ipv6(ipv6)
def __init__(self, addr, timeout=None, **ssl_args): assert ip.valid_ipv4(addr[0]) or ip.valid_ipv6(addr[0]) self.addr = addr self.timeout = timeout self.ssl_args = ssl_args self._is_active = True