def __init__(self, domain, ip_type, ip_val, port): ''' Constructor: This routine assumes that the IP address of the DPS Client uniquely identifies the DPS Client. @param domain: The Domain object @type domain: Domain @param ip_type: socket.AF_INET6 or socket.AF_INET @type ip_type: Integer @param ip_val: The Value of the IP Address @type ip_val: String (IPv6) or Integer @param port: The DPS Client Port (for UDP communication) @type port: Integer ''' self.domain = domain #DPS Client Location i.e. the UDP Port and Location self.location = IPAddressLocation(ip_type, ip_val, port) #List of Tunnel Endpoints #This is to store the Tunnel Endpoint IP Address self.Tunnel_Endpoints_Hash_IPv4 = {} self.Tunnel_Endpoints_Hash_IPv6 = {} ##Failure count self.failure_count = self.failure_count_max self.version = 0 self.valid = True #Add to Domain collection Domain.dps_client_add(self.domain, self)
def delete(self): ''' Destructor: ''' if not self.valid: return self.valid = False #Remove from GlobalCollection DPSClientHost.Host_Delete_All(self.domain, self.location.ip_value) #Remove self from VNID_Broadcast_Updates_To for key in DpsCollection.VNID_Broadcast_Updates_To.keys(): try: tuple_value = DpsCollection.VNID_Broadcast_Updates_To[key] dps_client = tuple_value[1] if dps_client == self: del DpsCollection.VNID_Broadcast_Updates_To[key] except Exception: pass #Remove self from DPS Client Updates for key in DpsCollection.Policy_Updates_To.keys(): try: tuple_value = DpsCollection.Policy_Updates_To[key] dps_client = tuple_value[1] if dps_client == self: del DpsCollection.Policy_Updates_To[key] except Exception: pass #Remove from Gateway_Updates_To for key in DpsCollection.Gateway_Updates_To.keys(): try: tuple_value = DpsCollection.Gateway_Updates_To[key] dps_client = tuple_value[1] if dps_client == self: del DpsCollection.Gateway_Updates_To[key] except Exception: pass #Remove from VNID_Multicast_Updates_To for key in DpsCollection.VNID_Multicast_Updates_To.keys(): try: tuple_value = DpsCollection.VNID_Multicast_Updates_To[key] dps_client = tuple_value[1] if dps_client == self: del DpsCollection.VNID_Multicast_Updates_To[key] except Exception: pass #Remove from Address_Resolution_Requests_To for key in DpsCollection.Address_Resolution_Requests_To.keys(): try: tuple_value = DpsCollection.Address_Resolution_Requests_To[key] dps_client = tuple_value[1] if dps_client == self: del DpsCollection.Address_Resolution_Requests_To[key] except Exception: continue for tunnel in self.Tunnel_Endpoints_Hash_IPv4.values(): tunnel.delete() for tunnel in self.Tunnel_Endpoints_Hash_IPv6.values(): tunnel.delete() Domain.dps_client_delete(self.domain, self)
def ip_clear(self, inet_type, ip_value): ''' This deletes a tunnel IP address from this Tunnel and all DVGS and types @param dvg: The DVG on which this registration occurred @type dvg: DVG @param client_type: The Type of Client: should be in DpsClientType.types @type client_type: Integer @param inet_type: AF_INET or AF_INET6 @type inet_type: Integer @param ip_value: The IP address value @type ip_value: Integer or String ''' while True: for client_type in DpsClientType.types.keys(): #Delete IP from all matching VNIDs and Client Type for vnid in self.DVG_Hash[client_type].keys(): fRemoveVNID = False try: vnid_hash_ip = self.VNID_Hash_IP[client_type][vnid] del vnid_hash_ip[ip_value] if len(vnid_hash_ip) == 0: del self.VNID_Hash_IP[client_type][vnid] fRemoveVNID = True except Exception: pass #Remove the IP from the DVG try: dvg = self.DVG_Hash[client_type][vnid] DVG.tunnel_endpoint_delete_IP(dvg, client_type, inet_type, ip_value) if fRemoveVNID: del self.DVG_Hash[client_type][vnid] if len(self.DVG_Hash[client_type]) == 0: #print 'Delete all Endpoints with client_type %s\r'%client_type self.delete_client_type(client_type) except Exception: pass #Delete IP completly from Tunnel try: ip_hash_vnid = self.IP_Hash_VNID[client_type][ip_value] ip_hash_vnid.clear() del self.IP_Hash_VNID[client_type][ip_value] except Exception: pass #Delete the IP from Domain and DPS Clients since no DVGs have it if inet_type == socket.AF_INET: self.ip_listv4.remove(inet_type, ip_value) elif inet_type == socket.AF_INET6: self.ip_listv6.remove(inet_type, ip_value) #Remove IP to DPS Client DPSClient.tunnel_endpoint_delete_IP(self.dps_client, inet_type, ip_value) #Remove IP from Domain Domain.tunnel_endpoint_delete_IP(self.domain, inet_type, ip_value) #Delete Self if not IP Addresses are present if self.ip_listv4.count() == 0 and self.ip_listv6.count() == 0: self.delete() break return
def ip_add(self, dvg, fregister, client_type, inet_type, ip_value, transaction_type): ''' This adds a tunnel IP address @param dvg: The DVG on which this registration occurred @type dvg: DVG @param fregister: Whether this is an explicit tunnel register @param fregister: Boolean @param client_type: The Type of Client: should be in DpsClientType.types @type client_type: Integer @param inet_type: AF_INET or AF_INET6 @type inet_type: Integer @param ip_value: The IP address value @type ip_value: Integer or String @param transaction_type: The Type of Transaction: should be in DpsTransactionType @type transaction_type: Integer ''' while True: try: client_type_value = DpsClientType.types[client_type] except Exception: break self.DVG_Hash[client_type][dvg.unique_id] = dvg #Add to Tunnels List even though it may have come through other DVGs as well if inet_type == socket.AF_INET: if not self.ip_listv4.search(ip_value): self.ip_listv4.add(inet_type, ip_value) elif inet_type == socket.AF_INET6: if not self.ip_listv4.search(ip_value): self.ip_listv6.add(inet_type, ip_value) #log.info('ip_add: Adding to DPS Client %s', ip_value) #Add DVG to self. #Add IP to DPS Client DPSClient.tunnel_endpoint_add_IP(self.dps_client, self, inet_type, ip_value) #Add IP to this DVGs DVG.tunnel_endpoint_add_IP(dvg, fregister, self, client_type, inet_type, ip_value, transaction_type) try: vnid_hash_ip = self.VNID_Hash_IP[client_type][dvg.unique_id] except Exception: self.VNID_Hash_IP[client_type][dvg.unique_id] = {} vnid_hash_ip = self.VNID_Hash_IP[client_type][dvg.unique_id] vnid_hash_ip[ip_value] = True #Add DVGs to IP hash try: ip_hash_vnid = self.IP_Hash_VNID[client_type][ip_value] except Exception: self.IP_Hash_VNID[client_type][ip_value] = {} ip_hash_vnid = self.IP_Hash_VNID[client_type][ip_value] ip_hash_vnid[dvg.unique_id] = True #Add IP to Domain #log.info('ip_add: Adding to domain %s', self.domain.unique_id) Domain.tunnel_endpoint_add_IP(self.domain, self, inet_type, ip_value) break return
def __init__(self, domain, dvg, vnid, client_type, transaction_type, tunnel_endpoint, vMac, vIP, version): ''' Constructor: @param domain: The Domain Object @type domain: Domain @param dvg: The DVG Object @type dvg: DVG @param vnid: The VNID (Maybe different from dvg.unique_id for Domain/DVG 0) @type vnid: Integer @param client_type: The Type of Client: should be in DpsClientType.types @type client_type: Integer @param transaction_type: The Type of Transaction: should be in DpsTransactionType @type transaction_type: Integer @param tunnel_endpoint: The DOVE Switch on which the Endpoint is hosted Maybe(None) - Then dove_gateway must be valid @type tunnel_endpoint: The Tunnel Endpoint @param vMAC: The Virtual MAC Address @type vMAC: ByteArray/String @param vIP: The IP Address of the Endpoint @type vIP: IPAddressLocation @param version: The version to start with @type version: integer ''' if DpsCollection.Endpoints_Count >= DpsCollection.Endpoints_Count_Max: raise MemoryError('Out of Memory') self.domain = domain self.dvg = dvg self.vnid = vnid self.client_type = client_type self.vMac = vMac self.tunnel_endpoint = tunnel_endpoint self.vIP_set = {} self.vIP_set_show = {} if vIP is not None: self.vIP_set[vIP.ip_value] = vIP self.vIP_set_show[vIP.ip_value] = vIP #self.version = self.version_start self.version = version self.valid = True self.in_migration = False ############################################################# #TODO:To be finished #Add to the appropriate DPS Client List #log.info('__init__: Adding to TunnelEndpoint\r') TunnelEndpoint.endpoint_add(tunnel_endpoint, self, transaction_type) #log.info('__init__: Added to TunnelEndpoint\r') #Add to the appropriate Domain Lists Domain.endpoint_add(domain, self) #log.info('__init__: Added to Domain\r') #Add to the appropriate DVG/VNID Lists DVG.endpoint_add(dvg, self) #log.info('__init__: Added to DVG\r') #self.show(None) DpsCollection.Endpoints_Count += 1
def vIP_add(self, vIP): ''' Add a virtual IP address @param vIP: The IP Address of the Endpoint @type vIP: IPAddressLocation ''' if vIP is not None: self.vIP_set[vIP.ip_value] = vIP Domain.endpoint_vIP_add(self.domain, self, vIP) DVG.endpoint_vIP_add(self.dvg, self, vIP) if len(self.vIP_set) < DpsCollection.Endpoints_vIP_Max: self.vIP_set_show[vIP.ip_value] = vIP
def vIP_del(self, vIP): ''' Delete a virtual IP address @param vIP: The IP Address of the Endpoint @type vIP: IPAddressLocation ''' if vIP is not None: try: del self.vIP_set[vIP.ip_value] Domain.endpoint_vIP_del(self.domain, vIP) DVG.endpoint_vIP_del(self.dvg, vIP) del self.vIP_set_show[vIP.ip_value] except Exception: pass
def __init__(self, domain, traffic_type, policy_type, src_dvg, dst_dvg, ttl, action): ''' Constructor: @param domain: The Domain Object @type domain: Domain @param traffic_type: The Traffic Type (0: Unicast, 1:Multicast) @type traffic_type: Integer @param policy_type: The Policy Type @type policy_type: Integer @param src_dvg: The Source DVG Object @type src_dvg: DVG @param dst_dvg: The Destination DVG Object @type dst_dvg: DVG @param ttl: Time-To-Live cached in DPS client @type ttl: Integer @param action: Action taken to traffic from Source DVG to destination DVG @type action: IPAddressList or Integer depends on action_type @raise DOVE_STATUS_INVALID_POLICY: Bad policy type ''' #Based on Object Model Chapter 5: Policy Object if policy_type <= 0 or policy_type >= self.type_bad: raise DOVEStatus.DOVE_STATUS_INVALID_POLICY if policy_type == self.type_ip_list: raise DOVEStatus.DOVE_STATUS_NOT_SUPPORTED self.domain = domain self.traffic_type = traffic_type self.type = policy_type self.src_dvg = src_dvg self.dst_dvg = dst_dvg self.ttl = ttl self.action = action action_struct = struct.unpack(self.fmt_action_struct_hdr, self.action[:self.fmt_action_struct_hdr_size]) self.action_connectivity = self.action_drop if self.type == self.type_connectivity: self.action_connectivity = action_struct[2] #3rd parameter self.version = action_struct[0] self.key = self.key_fmt%(src_dvg.unique_id, dst_dvg.unique_id) #TODO: Store the Policy result in a packed data format that # can be sent to the C Code when needed. # ############################################################# dcs_object.__init__(self, self.key) ############################################################# #Add the policy into a Policy_Hash table in a domain, #source DVG and destination DVG ############################################################# Domain.policy_add(self.domain, self) DVG.policy_add_src(src_dvg, dst_dvg.unique_id, self) DVG.policy_add_dst(dst_dvg, src_dvg.unique_id, self)
def __init__(self, domain, traffic_type, policy_type, src_dvg, dst_dvg, ttl, action): """ Constructor: @param domain: The Domain Object @type domain: Domain @param traffic_type: The Traffic Type (0: Unicast, 1:Multicast) @type traffic_type: Integer @param policy_type: The Policy Type @type policy_type: Integer @param src_dvg: The Source DVG Object @type src_dvg: DVG @param dst_dvg: The Destination DVG Object @type dst_dvg: DVG @param ttl: Time-To-Live cached in DPS client @type ttl: Integer @param action: Action taken to traffic from Source DVG to destination DVG @type action: IPAddressList or Integer depends on action_type @raise DOVE_STATUS_INVALID_POLICY: Bad policy type """ # Based on Object Model Chapter 5: Policy Object if policy_type <= 0 or policy_type >= self.type_bad: raise DOVEStatus.DOVE_STATUS_INVALID_POLICY if policy_type == self.type_ip_list: raise DOVEStatus.DOVE_STATUS_NOT_SUPPORTED self.domain = domain self.traffic_type = traffic_type self.type = policy_type self.src_dvg = src_dvg self.dst_dvg = dst_dvg self.ttl = ttl self.action = action action_struct = struct.unpack(self.fmt_action_struct_hdr, self.action[: self.fmt_action_struct_hdr_size]) self.action_connectivity = self.action_drop if self.type == self.type_connectivity: self.action_connectivity = action_struct[2] # 3rd parameter self.version = action_struct[0] self.key = self.key_fmt % (src_dvg.unique_id, dst_dvg.unique_id) # TODO: Store the Policy result in a packed data format that # can be sent to the C Code when needed. # ############################################################# dcs_object.__init__(self, self.key) ############################################################# # Add the policy into a Policy_Hash table in a domain, # source DVG and destination DVG ############################################################# Domain.policy_add(self.domain, self) DVG.policy_add_src(src_dvg, dst_dvg.unique_id, self) DVG.policy_add_dst(dst_dvg, src_dvg.unique_id, self)
def delete(self): """ Destructor: Remove itself from collection """ if not self.valid: return self.valid = False if self.src_dvg == self.dst_dvg: # Restore to default allow policy and send update to VNID self.update(0, 67108864, struct.pack(Policy.fmt_action_struct_hdr, 0, 0, Policy.action_forward)) if self.domain.active: DpsCollection.policy_update_queue.put((self.src_dvg, self.traffic_type)) else: # Remove self from Domain, SRC and DST VNID/DVG DVG.policy_del_dst(self.dst_dvg, self.src_dvg.unique_id, self.traffic_type) DVG.policy_del_src(self.src_dvg, self.dst_dvg.unique_id, self.traffic_type) Domain.policy_del(self.domain, self)
def delete(self): ''' Destructor: Remove itself from collection ''' if not self.valid: return self.valid = False if self.src_dvg == self.dst_dvg: #Restore to default allow policy and send update to VNID self.update(0, 67108864, struct.pack(Policy.fmt_action_struct_hdr, 0, 0, Policy.action_forward)) if self.domain.active: DpsCollection.policy_update_queue.put((self.src_dvg, self.traffic_type)) else: #Remove self from Domain, SRC and DST VNID/DVG DVG.policy_del_dst(self.dst_dvg, self.src_dvg.unique_id, self.traffic_type) DVG.policy_del_src(self.src_dvg, self.dst_dvg.unique_id, self.traffic_type) Domain.policy_del(self.domain, self)
def delete(self): ''' Destructor: ''' if not self.valid: return self.valid = False #Remove from Conflict Detection List self.domain.ConflictDetection.endpoint_delete(self) #Remove from DPS Client List TunnelEndpoint.endpoint_del(self.tunnel_endpoint, self) #Remove from Domain Collection Domain.endpoint_del(self.domain, self) #Remove from VNID/DVG collection DVG.endpoint_del(self.dvg, self) #Remove vIPs self.vIP_set.clear() self.vIP_set_show.clear() DpsCollection.Endpoints_Count -= 1 return
def tunnel_endpoint_delete_IP(self, inet_type, ip_value): ''' Deletes a Tunnel Endpoint Physical IP Address to the Domain Collection @param tunnel_endpoint: The Tunnel Endpoint @type tunnel_endpoint: TunnelEndpoint Object @param inet_type: AF_INET or AF_INET6 @type inet_type: Integer @param ip_value: The IP address value @type ip_value: Integer or String ''' if inet_type == socket.AF_INET: ip_hash = self.Tunnel_Endpoints_Hash_IPv4 else: ip_hash = self.Tunnel_Endpoints_Hash_IPv6 try: del ip_hash[ip_value] except Exception: pass if ((len(self.Tunnel_Endpoints_Hash_IPv4) == 0) and (len(self.Tunnel_Endpoints_Hash_IPv6) == 0)): #log.info('DPSClient.tunnel_endpoint_delete: No tunnel endpoints') #No other tunnels attached Domain.dps_client_delete(self.domain, self) return
def tunnel_endpoint_delete(self, tunnel_endpoint): ''' Removes a Tunnel Endpoint from the collection @param tunnel_endpoint: The Tunnel Endpoint @type tunnel_endpoint: TunnelEndpoint Object ''' #log.info('DPSClient.tunnel_endpoint_delete %s', tunnel_endpoint.primary_ip().show()) ip_list = tunnel_endpoint.ip_listv4.ip_list for ip_value in ip_list: try: del self.Tunnel_Endpoints_Hash_IPv4[ip_value] except Exception: pass ip_list = tunnel_endpoint.ip_listv6.ip_list for ip_value in ip_list: try: del self.Tunnel_Endpoints_Hash_IPv6[ip_value] except Exception: pass if ((len(self.Tunnel_Endpoints_Hash_IPv4) == 0) and (len(self.Tunnel_Endpoints_Hash_IPv6) == 0)): #log.info('DPSClient.tunnel_endpoint_delete: No tunnel endpoints') #No other tunnels attached Domain.dps_client_delete(self.domain, self)
def delete_if_empty(self): ''' This routine checks if a DPS Client no longer hosts any Endpoint. If it doesn't, it unlinks itself from all the domain ''' if len(self.Endpoint_Hash_MAC) != 0: return if not self.valid: return self.valid = False #Remove self from all DVGs for client_type in DpsClientType.types.keys(): for dvg in self.DVG_Hash[client_type].values(): DVG.tunnel_endpoint_delete(dvg, self, client_type) #Clear the VNID/DVG Hash self.DVG_Hash.clear() #Remove from DPS Client Collection DPSClient.tunnel_endpoint_delete(self.dps_client, self) #Remove from Domain Collection Domain.tunnel_endpoint_delete(self.domain, self) #Clear IPs self.ip_listv4.clear() self.ip_listv6.clear() return
def ip_delete(self, dvg, client_type, inet_type, ip_value): ''' This deletes a tunnel IP address from a DVG and client type @param dvg: The DVG on which this registration occurred @type dvg: DVG @param client_type: The Type of Client: should be in DpsClientType.types @type client_type: Integer @param inet_type: AF_INET or AF_INET6 @type inet_type: Integer @param ip_value: The IP address value @type ip_value: Integer or String ''' fdeleteVNID = False fdeleteIP = False while True: try: client_type_value = DpsClientType.types[client_type] except Exception: break try: vnid_hash_ip = self.VNID_Hash_IP[client_type][dvg.unique_id] del vnid_hash_ip[ip_value] if len(vnid_hash_ip) == 0: del self.VNID_Hash_IP[client_type][dvg.unique_id] fdeleteVNID = True except Exception: pass try: ip_hash_vnid = self.IP_Hash_VNID[client_type][ip_value] del ip_hash_vnid[dvg.unique_id] if len(ip_hash_vnid) == 0: del self.IP_Hash_VNID[client_type][ip_value] fdeleteIP = True except Exception: pass if fdeleteVNID: #Remove Tunnel from DVG DVG.tunnel_endpoint_delete(dvg, self, client_type) try: del self.DVG_Hash[client_type][dvg.unique_id] if len(self.DVG_Hash[client_type]) == 0: #print 'Delete all Endpoints with client_type %s\r'%client_type_value self.delete_client_type(client_type) except Exception: pass if not fdeleteIP: break if fdeleteIP: #Remove only the IP from the DVG DVG.tunnel_endpoint_delete_IP(dvg, client_type, inet_type, ip_value) #Check if IP is present in any client type ip_present = False for ctype in self.IP_Hash_VNID.keys(): try: ip_hash_vnid = self.IP_Hash_VNID[ctype][ip_value] ip_present = True break except Exception: continue if ip_present: break #Actually delete the IP from Domain and DPS Clients since no DVGs have it if inet_type == socket.AF_INET: self.ip_listv4.remove(inet_type, ip_value) elif inet_type == socket.AF_INET6: self.ip_listv6.remove(inet_type, ip_value) #Remove IP to DPS Client DPSClient.tunnel_endpoint_delete_IP(self.dps_client, inet_type, ip_value) #Remove IP from Domain Domain.tunnel_endpoint_delete_IP(self.domain, inet_type, ip_value) #Delete Self if not IP Addresses are present if self.ip_listv4.count() == 0 and self.ip_listv6.count() == 0: self.delete() break return