From: HemaTG Date: Mon, 2 May 2016 09:27:40 +0000 (+0530) Subject: Vxlan/Gre co-existence,Alarms,tunnelstate,TR fixes X-Git-Url: https://git.opendaylight.org/gerrit/gitweb?p=vpnservice.git;a=commitdiff_plain;h=refs%2Fchanges%2F56%2F38256%2F1 Vxlan/Gre co-existence,Alarms,tunnelstate,TR fixes Change-Id: Ia253c413dc198dce371b6f87c2c67af2bdb324b5 Signed-off-by: HemaTG --- diff --git a/itm/itm-api/src/main/java/org/opendaylight/vpnservice/itm/api/IITMProvider.java b/itm/itm-api/src/main/java/org/opendaylight/vpnservice/itm/api/IITMProvider.java index c45b982d..3ec13113 100644 --- a/itm/itm-api/src/main/java/org/opendaylight/vpnservice/itm/api/IITMProvider.java +++ b/itm/itm-api/src/main/java/org/opendaylight/vpnservice/itm/api/IITMProvider.java @@ -16,7 +16,7 @@ import org.opendaylight.vpnservice.mdsalutil.MatchInfo; import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.inet.types.rev100924.IpAddress; //import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.itm.config.rev151102.vtep.config.schemas.VtepConfigSchema; import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.config.rev151102.vtep.config.schemas.VtepConfigSchema; -//import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.itm.op.rev150701.TunnelsState; +import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.op.rev150701.TunnelList ; public interface IITMProvider { // APIs used by i @@ -27,6 +27,7 @@ public interface IITMProvider { public DataBroker getDataBroker(); public void showTeps(); + public void showState(TunnelList tunnels); public void deleteVtep(BigInteger dpnId, String portName, Integer vlanId, String ipAddress, String subnetMask, String gatewayIp, String transportZone); diff --git a/itm/itm-api/src/main/java/org/opendaylight/vpnservice/itm/globals/ITMConstants.java b/itm/itm-api/src/main/java/org/opendaylight/vpnservice/itm/globals/ITMConstants.java index b6f6673b..eaba9f31 100644 --- a/itm/itm-api/src/main/java/org/opendaylight/vpnservice/itm/globals/ITMConstants.java +++ b/itm/itm-api/src/main/java/org/opendaylight/vpnservice/itm/globals/ITMConstants.java @@ -20,8 +20,11 @@ public class ITMConstants{ //Tunnel Monitoring public static final boolean DEFAULT_MONITOR_ENABLED = true; public static final int DEFAULT_MONITOR_INTERVAL = 10; + public static final int BFD_DEFAULT_MONITOR_INTERVAL = 100; public static final String DUMMY_IP_ADDRESS = "0.0.0.0"; public static final String TUNNEL_TYPE_VXLAN = "VXLAN"; public static final String TUNNEL_TYPE_GRE = "GRE"; + public static final String TUNNEL_TYPE_MPLS_OVER_GRE = "MPLS_OVER_GRE"; + public static final String TUNNEL_TYPE_INVALID = "Invalid"; } diff --git a/itm/itm-api/src/main/yang/itm-rpc.yang b/itm/itm-api/src/main/yang/itm-rpc.yang index 866c6e63..0ca995bf 100644 --- a/itm/itm-api/src/main/yang/itm-rpc.yang +++ b/itm/itm-api/src/main/yang/itm-rpc.yang @@ -39,6 +39,11 @@ module itm-rpc { leaf destination-dpid { type uint64; } + leaf tunnel-type { + type identityref { + base odlif:tunnel-type-base; + } + } } output { leaf interface-name { @@ -56,6 +61,11 @@ module itm-rpc { leaf destination-ip { type inet:ip-address; } + leaf tunnel-type { + type identityref { + base odlif:tunnel-type-base; + } + } } output { leaf interface-name { @@ -73,6 +83,11 @@ module itm-rpc { leaf destination-node { type string; } + leaf tunnel-type { + type identityref { + base odlif:tunnel-type-base; + } + } } output { leaf interface-name { @@ -182,6 +197,20 @@ module itm-rpc { } } + rpc add-l2-gw-mlag-device { + description "used for building tunnels between teps on all Dpns and hwVtep"; + input { + leaf topology-id { + type string; + } + leaf-list node-id { + type string; + } + leaf ip-address { + type inet:ip-address; + } + } + } rpc delete-l2-gw-device { description "used for deleting tunnels between teps on all Dpns and hwVtep"; input { @@ -197,4 +226,18 @@ module itm-rpc { } } + rpc delete-l2-gw-mlag-device { + description "used for deleting tunnels between teps on all Dpns and hwVtep"; + input { + leaf topology-id { + type string; + } + leaf-list node-id { + type string; + } + leaf ip-address { + type inet:ip-address; + } + } + } } \ No newline at end of file diff --git a/itm/itm-api/src/main/yang/itm-state.yang b/itm/itm-api/src/main/yang/itm-state.yang index aa302691..c76ce52e 100644 --- a/itm/itm-api/src/main/yang/itm-state.yang +++ b/itm/itm-api/src/main/yang/itm-state.yang @@ -27,6 +27,27 @@ module itm-state { /* Operational state */ + identity tep-type-base { + description "Base TEP device type"; + } + identity tep-type-internal { + base tep-type-base; + description "TEP type internal e.g. Compute OVS"; + } + identity tep-type-external { + base tep-type-base; + description "TEP type external e.g. DC Gateway"; + } + identity tep-type-hwvtep { + base tep-type-base; + description "TEP type Hwvtep e.g. TOR devices"; + } + typedef tep-type { + type identityref { + base tep-type-base; + } + description "This type is used to refer to an TEP Device Type."; + } container dpn-endpoints { list DPN-TEPs-info { @@ -43,8 +64,8 @@ module itm-state { /* Minimum 1 port. We may for now support only two ports */ list tunnel-end-points { - - key "portname VLAN-ID ip-address"; /* Multiple tunnels on the same physical port but on different VLAN can be supported */ + ordered-by user; + key "portname VLAN-ID ip-address tunnel-type"; /* Multiple tunnels on the same physical port but on different VLAN can be supported */ leaf portname { type string; @@ -81,7 +102,7 @@ module itm-state { container tunnel-list { list internal-tunnel { - key "source-DPN destination-DPN"; + key "source-DPN destination-DPN transport-type"; leaf source-DPN { type uint64; @@ -90,6 +111,11 @@ module itm-state { leaf destination-DPN { type uint64; } + leaf transport-type { + type identityref { + base odlif:tunnel-type-base; + } + } /* logical-group interface id */ @@ -102,7 +128,7 @@ module itm-state { container external-tunnel-list { list external-tunnel { - key "source-device destination-device"; + key "source-device destination-device transport-type"; leaf source-device { type string; //dpnid or node-id @@ -112,6 +138,11 @@ module itm-state { type string; //dpn-id or node-id or ip } + leaf transport-type { + type identityref { + base odlif:tunnel-type-base; + } + } /* logical-group interface id */ leaf tunnel-interface-name { @@ -121,7 +152,43 @@ module itm-state { } } - + grouping tep-info-attributes { + leaf tep-device-type { + type identityref { + base tep-type-base; + } + } + leaf tep-device-id { + type string; //dpnid or node-id + } + leaf tep-ip { + type inet:ip-address; //dpnid or node-id + } + } + + container tunnels_state { + list state-tunnel-list { + key "tunnel-interface-name"; + leaf tunnel-interface-name { + type string; + } + leaf tunnel-state { + type boolean; + config false; + } + container src-info { + uses tep-info-attributes; + } + container dst-info { + uses tep-info-attributes; + } + leaf transport-type { + type identityref { + base odlif:tunnel-type-base; + } + } + } + } notification itm-tunnel-build-complete{ } diff --git a/itm/itm-api/src/main/yang/itm.yang b/itm/itm-api/src/main/yang/itm.yang index 3d3ccbe5..ddef8f07 100644 --- a/itm/itm-api/src/main/yang/itm.yang +++ b/itm/itm-api/src/main/yang/itm.yang @@ -29,6 +29,7 @@ module itm { container transport-zones { list transport-zone { + ordered-by user; key zone-name; leaf zone-name { type string; diff --git a/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/cli/TepCommandHelper.java b/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/cli/TepCommandHelper.java index 7f417d3b..f7741591 100644 --- a/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/cli/TepCommandHelper.java +++ b/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/cli/TepCommandHelper.java @@ -22,16 +22,24 @@ import org.opendaylight.vpnservice.interfacemgr.exceptions.InterfaceNotFoundExce import org.opendaylight.vpnservice.interfacemgr.interfaces.IInterfaceManager; //import org.opendaylight.vpnservice.interfacemgr.util.OperationalIfmUtil; import org.opendaylight.vpnservice.itm.globals.ITMConstants; +import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.interfacemgr.rev150331.IfL2vlan; import org.opendaylight.vpnservice.itm.impl.ItmUtils; import org.opendaylight.vpnservice.mdsalutil.MDSALDataStoreUtils; import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.inet.types.rev100924.IpAddress; import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.inet.types.rev100924.IpPrefix; +import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.interfaces.rev140508.interfaces.Interface; +import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.interfaces.rev140508.interfaces.state.Interface.AdminStatus; +import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.interfaces.rev140508.interfaces.state.Interface.OperStatus; import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.config.rev151102.TunnelMonitorEnabled; import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.config.rev151102.TunnelMonitorEnabledBuilder; import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.config.rev151102.TunnelMonitorInterval; import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.config.rev151102.TunnelMonitorIntervalBuilder; +import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.op.rev150701.TunnelList ; +import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.op.rev150701.tunnel.list.InternalTunnel; +import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.op.rev150701.tunnel.list.InternalTunnelKey; import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.interfacemgr.rev150331.TunnelTypeBase; import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.interfacemgr.rev150331.TunnelTypeGre; +import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.interfacemgr.rev150331.IfTunnel; import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.interfacemgr.rev150331.TunnelTypeVxlan; import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.rev150701.TransportZones; import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.rev150701.TransportZonesBuilder; @@ -44,6 +52,7 @@ import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.rev150701.tr import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.rev150701.transport.zones.transport.zone.subnets.Vteps; import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.rev150701.transport.zones.transport.zone.subnets.VtepsBuilder; import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.rev150701.transport.zones.transport.zone.subnets.VtepsKey; +import org.opendaylight.yang.gen.v1.urn.opendaylight.l2.types.rev130827.VlanId; import org.opendaylight.yangtools.yang.binding.DataObject; import org.opendaylight.yangtools.yang.binding.InstanceIdentifier; import org.slf4j.Logger; @@ -436,9 +445,9 @@ public class TepCommandHelper { result.add(String.format("Tunnel Monitoring (for VXLAN tunnels): %s", (monitorEnabled ? "On" : "Off"))); result.add(String.format("Tunnel Monitoring Interval (for VXLAN tunnels): %d", monitorInterval)); result.add(System.lineSeparator()); - result.add(String.format("%-16s %-16s %-16s %-12s %-12s %-12s %-12s %-12s", "TransportZone", "TunnelType", "SubnetMask", + result.add(String.format("%-16s %-16s %-16s %-12s %-12s %-12s %-16s %-12s", "TransportZone", "TunnelType", "SubnetMask", "GatewayIP", "VlanID", "DpnID", "IPAddress", "PortName")); - result.add("--------------------------------------------------------------------------------------------------------------"); + result.add("------------------------------------------------------------------------------------------------------------------------------"); for (TransportZone tZ : tZones.getTransportZone()) { if (tZ.getSubnets() == null || tZ.getSubnets().isEmpty()) { LOG.error("Transport Zone " + tZ.getZoneName() + "has no subnets"); @@ -456,7 +465,7 @@ public class TepCommandHelper { strTunnelType = ITMConstants.TUNNEL_TYPE_GRE ; else strTunnelType = ITMConstants.TUNNEL_TYPE_VXLAN ; - result.add(String.format("%-16s %-16s %-16s %-12s %-12s %-12s %-12s %-12s", tZ.getZoneName(), strTunnelType, sub + result.add(String.format("%-16s %-16s %-16s %-12s %-12s %-12s %-16s %-12s", tZ.getZoneName(), strTunnelType, sub .getPrefix().getIpv4Prefix().getValue(), sub.getGatewayIp().getIpv4Address() .getValue(), sub.getVlanId().toString(), vtep.getDpnId().toString(), vtep .getIpAddress().getIpv4Address().getValue(), vtep.getPortname().toString())); @@ -628,46 +637,60 @@ public class TepCommandHelper { e.printStackTrace(); } } -/* - public void showState(TunnelsState tunnelsState, boolean tunnelMonitorEnabled) { - List tunnelLists = tunnelsState.getStateTunnelList(); + + public void showState(TunnelList tunnels, boolean tunnelMonitorEnabled) { + IfTunnel tunnelInterface = null; + IfL2vlan l2Vlan = null; + List tunnelLists = tunnels.getInternalTunnel(); if (tunnelLists == null || tunnelLists.isEmpty()) { - System.out.println("No Logical Tunnels Exist"); + System.out.println("No Internal Tunnels Exist"); return; } if (!tunnelMonitorEnabled) { System.out.println("Tunnel Monitoring is Off"); } - System.out.println(String.format("%-16s %-16s %-16s %-10s %-16s %-8s %-10s %-10s", "Source-DPN", - "Destination-DPN", "SourcePortName", "Source-IP", "Destination-IP", "VLan-ID", "Trunk-State", - "Logical-Tunnel-State")); - System.out.println("----------------------------------------------------------------------------------------------------------------------"); - - for (StateTunnelList tunnel : tunnelLists) { - String logicaltunnelState = (tunnel.isLogicalTunnelState()) ? "UP" : "DOWN"; - try { - List trunks = - interfaceManager.getTunnelInterfacesOfLogicalGroup(tunnel.getLogicalTunnelGroupName()); - if (trunks != null && !trunks.isEmpty()) { - for (String trunk : trunks) { - List params = Arrays.asList(trunk.split(":")); - LOG.trace("trunk {} for LogicalIf {} ", trunk, tunnel.getLogicalTunnelGroupName()); - String trunkState = (OperationalIfmUtil.isInterfaceUp(dataBroker, trunk)) ? "UP" : "DOWN"; - System.out.println(String.format("%-16s %-16s %-16s %-10s %-16s %-8s %-10s %-10s", tunnel - .getSourceDPN().toString(), tunnel.getDestinationDPN().toString(), params - .get(1), params.get(3), params.get(4), params.get(2), trunkState, - logicaltunnelState)); - } - } else { - LOG.error("No trunks for " + tunnel.getLogicalTunnelGroupName()); + String displayFormat = "%-16s %-16s %-16s %-16s %-16s %-8s %-10s %-10s"; + System.out.println(String.format(displayFormat, "Tunnel Name", "Source-DPN", + "Destination-DPN", "Source-IP", "Destination-IP", "Vlan Id", "Trunk-State", "Transport Type")); + System.out.println("-------------------------------------------------------------------------------------------------------------------------------------"); + + for (InternalTunnel tunnel : tunnelLists) { + String tunnelInterfaceName = tunnel.getTunnelInterfaceName(); + LOG.trace("tunnelInterfaceName::: {}", tunnelInterfaceName); + + InstanceIdentifier ifStateId = + ItmUtils.buildStateInterfaceId(tunnelInterfaceName); + Optional ifStateOptional = + ItmUtils.read(LogicalDatastoreType.OPERATIONAL, ifStateId, dataBroker); + String tunnelState = "DOWN" ; + if (ifStateOptional.isPresent()) { + org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.interfaces.rev140508.interfaces.state.Interface iface = ifStateOptional.get() ; + if(iface.getAdminStatus() == AdminStatus.Up && iface.getOperStatus() == OperStatus.Up) + tunnelState = "UP" ; + } + InstanceIdentifier trunkIdentifier = ItmUtils.buildId(tunnelInterfaceName); + Optional ifaceObj = ItmUtils.read(LogicalDatastoreType.CONFIGURATION, trunkIdentifier, dataBroker) ; + if (ifaceObj.isPresent()) { + l2Vlan = (IfL2vlan) ifaceObj.get().getAugmentation(IfL2vlan.class); + tunnelInterface = (IfTunnel) ifaceObj.get().getAugmentation(IfTunnel.class); } - } catch (InterfaceNotFoundException e) { - LOG.error("if not found " + tunnel.getLogicalTunnelGroupName()); - } - } + Class tunType = tunnelInterface.getTunnelInterfaceType(); + String tunnelType = ITMConstants.TUNNEL_TYPE_VXLAN; + if( tunType.equals(TunnelTypeVxlan.class)) + tunnelType = ITMConstants.TUNNEL_TYPE_VXLAN ; + else if( tunType.equals(TunnelTypeGre.class) ) + tunnelType = ITMConstants.TUNNEL_TYPE_GRE ; + int vlanId = 0; + if( l2Vlan != null ) { + vlanId = l2Vlan.getVlanId().getValue() ; + } + System.out.println(String.format(displayFormat, tunnel.getTunnelInterfaceName(), tunnel + .getSourceDPN().toString(), tunnel.getDestinationDPN().toString(), tunnelInterface.getTunnelSource().getIpv4Address().getValue(), tunnelInterface.getTunnelDestination().getIpv4Address().getValue(),vlanId, tunnelState , + tunnelType)); + } } -*/ + // deletes from ADD-cache if it exists. public boolean isInCache(BigInteger dpnId, String portName, Integer vlanId, String ipAddress, String subnetMask, String gatewayIp, String transportZone) { diff --git a/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/cli/TepShowState.java b/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/cli/TepShowState.java index a2a254de..7e64282f 100644 --- a/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/cli/TepShowState.java +++ b/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/cli/TepShowState.java @@ -15,7 +15,7 @@ import org.opendaylight.controller.md.sal.binding.api.DataBroker; import org.opendaylight.controller.md.sal.common.api.data.LogicalDatastoreType; import org.opendaylight.vpnservice.itm.api.IITMProvider; import org.opendaylight.vpnservice.itm.impl.ItmUtils; -//import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.itm.op.rev150701.TunnelsState; +import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.op.rev150701.TunnelList ; import org.opendaylight.yangtools.yang.binding.InstanceIdentifier; import java.util.ArrayList; @@ -33,18 +33,16 @@ import java.util.List; @Override protected Object doExecute() throws Exception { - /* + DataBroker broker = itmProvider.getDataBroker(); List result = new ArrayList(); - InstanceIdentifier path = InstanceIdentifier.builder(TunnelsState.class).build(); - Optional tunnels = ItmUtils.read(LogicalDatastoreType.OPERATIONAL, path, broker); + InstanceIdentifier path = InstanceIdentifier.builder(TunnelList.class).build(); + Optional tunnels = ItmUtils.read(LogicalDatastoreType.CONFIGURATION, path, broker); if (tunnels.isPresent()) { itmProvider.showState(tunnels.get()); } else - System.out.println("No Logical Tunnels Exist"); - */ - System.out.println( "Logical Tunnels state is not currently supported"); + System.out.println("No Internal Tunnels Exist"); return null; } } diff --git a/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/confighelpers/ItmExternalTunnelAddWorker.java b/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/confighelpers/ItmExternalTunnelAddWorker.java index 6a0ed5be..caae0cbb 100644 --- a/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/confighelpers/ItmExternalTunnelAddWorker.java +++ b/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/confighelpers/ItmExternalTunnelAddWorker.java @@ -15,6 +15,7 @@ import com.google.common.base.Optional; import org.opendaylight.controller.md.sal.binding.api.DataBroker; import org.opendaylight.controller.md.sal.binding.api.WriteTransaction; import org.opendaylight.controller.md.sal.common.api.data.LogicalDatastoreType; +import org.opendaylight.vpnservice.itm.globals.ITMConstants; import org.opendaylight.vpnservice.itm.impl.ItmUtils; import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.inet.types.rev100924.IpAddress; import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.inet.types.rev100924.IpPrefix; @@ -75,15 +76,16 @@ public class ItmExternalTunnelAddWorker { // CHECK -- Assumption -- Only one End Point / Dpn for GRE/Vxlan Tunnels TunnelEndPoints firstEndPt = teps.getTunnelEndPoints().get(0); String interfaceName = firstEndPt.getInterfaceName(); - String trunkInterfaceName = ItmUtils.getTrunkInterfaceName(idManagerService, interfaceName, firstEndPt.getIpAddress().getIpv4Address().getValue(), extIp.getIpv4Address().getValue()); + String tunTypeStr = tunType.getName(); + String trunkInterfaceName = ItmUtils.getTrunkInterfaceName(idManagerService, interfaceName, firstEndPt.getIpAddress().getIpv4Address().getValue(), extIp.getIpv4Address().getValue(), tunTypeStr); char[] subnetMaskArray = firstEndPt.getSubnetMask().getValue(); String subnetMaskStr = String.valueOf(subnetMaskArray); SubnetUtils utils = new SubnetUtils(subnetMaskStr); String dcGwyIpStr = String.valueOf(extIp.getValue()); - IpAddress gwyIpAddress = (utils.getInfo().isInRange(dcGwyIpStr)) ? null : firstEndPt.getGwIpAddress(); - String ifDescription = tunType.getName(); + IpAddress gatewayIpObj = new IpAddress("0.0.0.0".toCharArray()); + IpAddress gwyIpAddress = (utils.getInfo().isInRange(dcGwyIpStr)) ? gatewayIpObj : firstEndPt.getGwIpAddress(); logger.debug(" Creating Trunk Interface with parameters trunk I/f Name - {}, parent I/f name - {}, source IP - {}, DC Gateway IP - {} gateway IP - {}", trunkInterfaceName, interfaceName, firstEndPt.getIpAddress(), extIp, gwyIpAddress); - Interface iface = ItmUtils.buildTunnelInterface(teps.getDPNID(), trunkInterfaceName, String.format("%s %s", ifDescription, "Trunk Interface"), true, tunType, firstEndPt.getIpAddress(), extIp, gwyIpAddress, firstEndPt.getVLANID(), false,false,null); + Interface iface = ItmUtils.buildTunnelInterface(teps.getDPNID(), trunkInterfaceName, String.format("%s %s", ItmUtils.convertTunnelTypetoString(tunType), "Trunk Interface"), true, tunType, firstEndPt.getIpAddress(), extIp, gwyIpAddress, firstEndPt.getVLANID(), false,false,null); logger.debug(" Trunk Interface builder - {} ", iface); InstanceIdentifier trunkIdentifier = ItmUtils.buildId(trunkInterfaceName); logger.debug(" Trunk Interface Identifier - {} ", trunkIdentifier); @@ -92,8 +94,9 @@ public class ItmExternalTunnelAddWorker { // update external_tunnel_list ds InstanceIdentifier path = InstanceIdentifier.create( ExternalTunnelList.class) - .child(ExternalTunnel.class, new ExternalTunnelKey(extIp.toString(), teps.getDPNID().toString())); - ExternalTunnel tnl = ItmUtils.buildExternalTunnel(teps.getDPNID().toString(), extIp.toString(), trunkInterfaceName); + .child(ExternalTunnel.class, new ExternalTunnelKey(extIp.toString(), teps.getDPNID().toString(), tunType)); + ExternalTunnel tnl = ItmUtils.buildExternalTunnel( teps.getDPNID().toString(), extIp.toString(), + tunType, trunkInterfaceName); t.merge(LogicalDatastoreType.CONFIGURATION, path, tnl, true); } futures.add(t.submit()); @@ -144,14 +147,16 @@ public class ItmExternalTunnelAddWorker { String cssID = dpn.getDPNID().toString(); String nodeId = hwVtepDS.getNodeId(); //CSS-TOR + Boolean monitorEnabled = ItmUtils.readMonitoringStateFromDS(dataBroker); + Integer monitorInterval = ItmUtils.readMonitorIntervalfromDS(dataBroker); logger.trace("wire up {} and {}",tep, hwVtepDS); if (!wireUp(dpn.getDPNID(), tep.getPortname(), sub.getVlanId(), tep.getIpAddress(), nodeId, hwVtepDS.getIpAddress(), tep.getSubnetMask(), - sub.getGatewayIp(), sub.getPrefix(), tZone.getTunnelType(), idManagerService, dataBroker, futures, t)) + sub.getGatewayIp(), sub.getPrefix(), tZone.getTunnelType(),monitorEnabled,ITMConstants.BFD_DEFAULT_MONITOR_INTERVAL, idManagerService, dataBroker, futures, t)) logger.error("Unable to build tunnel {} -- {}", tep.getIpAddress(), hwVtepDS.getIpAddress()); //TOR-CSS logger.trace("wire up {} and {}", hwVtepDS,tep); if (!wireUp(hwVtepDS.getTopologyId(), hwVtepDS.getNodeId(), hwVtepDS.getIpAddress(), cssID, tep.getIpAddress(), sub.getPrefix(), - sub.getGatewayIp(), tep.getSubnetMask(), tZone.getTunnelType(), idManagerService, dataBroker, futures, t)) + sub.getGatewayIp(), tep.getSubnetMask(), tZone.getTunnelType(), monitorEnabled,ITMConstants.BFD_DEFAULT_MONITOR_INTERVAL, idManagerService, dataBroker, futures, t)) logger.error("Unable to build tunnel {} -- {}", hwVtepDS.getIpAddress(), tep.getIpAddress()); } @@ -167,6 +172,7 @@ public class ItmExternalTunnelAddWorker { for (HwVtep hwTep : cfgdHwVteps) { InstanceIdentifier tzonePath = InstanceIdentifier.builder(TransportZones.class).child(TransportZone.class, new TransportZoneKey((hwTep.getTransportZone()))).build(); Optional tZoneOptional = ItmUtils.read(LogicalDatastoreType.CONFIGURATION, tzonePath, dataBroker); + Class tunType = TunnelTypeVxlan.class; if (tZoneOptional.isPresent()) { TransportZone tZone = tZoneOptional.get(); //do we need to check tunnel type? @@ -177,14 +183,17 @@ public class ItmExternalTunnelAddWorker { if (hwVtepDS.getIpAddress().equals(hwTep.getHwIp())) continue;//dont mesh with self //TOR1-TOR2 + Boolean monitorEnabled = ItmUtils.readMonitoringStateFromDS(dataBroker); + Integer monitorInterval = ItmUtils.readMonitorIntervalfromDS(dataBroker); logger.trace("wire up {} and {}",hwTep, hwVtepDS); if (!wireUp(hwTep.getTopo_id(), hwTep.getNode_id(), hwTep.getHwIp(), hwVtepDS.getNodeId(), hwVtepDS.getIpAddress(), - hwTep.getIpPrefix(), hwTep.getGatewayIP(), sub.getPrefix(), tZone.getTunnelType(), idManagerService, dataBroker, futures, t)) + hwTep.getIpPrefix(), hwTep.getGatewayIP(), sub.getPrefix(), tunType,monitorEnabled, + ITMConstants.BFD_DEFAULT_MONITOR_INTERVAL, idManagerService, dataBroker, futures, t)) logger.error("Unable to build tunnel {} -- {}", hwTep.getHwIp(), hwVtepDS.getIpAddress()); //TOR2-TOR1 logger.trace("wire up {} and {}", hwVtepDS,hwTep); if (!wireUp(hwTep.getTopo_id(), hwVtepDS.getNodeId(), hwVtepDS.getIpAddress(), hwTep.getNode_id(), hwTep.getHwIp(), - sub.getPrefix(), sub.getGatewayIp(), hwTep.getIpPrefix(), tZone.getTunnelType(), idManagerService, dataBroker, futures, t)) + sub.getPrefix(), sub.getGatewayIp(), hwTep.getIpPrefix(), tunType, monitorEnabled,ITMConstants.BFD_DEFAULT_MONITOR_INTERVAL, idManagerService, dataBroker, futures, t)) logger.error("Unable to build tunnel {} -- {}", hwVtepDS.getIpAddress(), hwTep.getHwIp()); } } @@ -192,14 +201,17 @@ public class ItmExternalTunnelAddWorker { for (Vteps vtep : sub.getVteps()) { //TOR-CSS String cssID = vtep.getDpnId().toString(); + Boolean monitorEnabled = ItmUtils.readMonitoringStateFromDS(dataBroker); + Integer monitorInterval = ItmUtils.readMonitorIntervalfromDS(dataBroker); logger.trace("wire up {} and {}",hwTep, vtep); if(!wireUp(hwTep.getTopo_id(), hwTep.getNode_id(), hwTep.getHwIp(), cssID, vtep.getIpAddress(), hwTep.getIpPrefix(), - hwTep.getGatewayIP(), sub.getPrefix(), tZone.getTunnelType(),idManagerService, dataBroker, futures, t )) + hwTep.getGatewayIP(), sub.getPrefix(), tunType,monitorEnabled, ITMConstants.BFD_DEFAULT_MONITOR_INTERVAL, idManagerService, dataBroker, futures, t )) logger.error("Unable to build tunnel {} -- {}", hwTep.getHwIp(), vtep.getIpAddress()); //CSS-TOR logger.trace("wire up {} and {}", vtep,hwTep); if(!wireUp(vtep.getDpnId(), vtep.getPortname(), sub.getVlanId(), vtep.getIpAddress(), - hwTep.getNode_id(),hwTep.getHwIp(),sub.getPrefix(), sub.getGatewayIp(),hwTep.getIpPrefix(),tZone.getTunnelType(),idManagerService, dataBroker, futures, t )); + hwTep.getNode_id(),hwTep.getHwIp(),sub.getPrefix(), sub.getGatewayIp(),hwTep.getIpPrefix(), + tunType,monitorEnabled,ITMConstants.BFD_DEFAULT_MONITOR_INTERVAL,idManagerService, dataBroker, futures, t )); } @@ -212,41 +224,57 @@ public class ItmExternalTunnelAddWorker { //for tunnels from TOR device private static boolean wireUp(String topo_id, String srcNodeid, IpAddress srcIp, String dstNodeId, IpAddress dstIp, IpPrefix srcSubnet, - IpAddress gWIp, IpPrefix dstSubnet, Class tunType, IdManagerService idManagerService, DataBroker dataBroker, List> futures, WriteTransaction t) { - IpAddress gwyIpAddress = (srcSubnet.equals(dstSubnet)) ? null : gWIp; + IpAddress gWIp, IpPrefix dstSubnet, Class tunType,Boolean monitorEnabled, + Integer monitorInterval,IdManagerService idManagerService, DataBroker dataBroker, List> futures, WriteTransaction t) { + IpAddress gatewayIpObj = new IpAddress("0.0.0.0".toCharArray()); + IpAddress gwyIpAddress = (srcSubnet.equals(dstSubnet)) ? gatewayIpObj : gWIp; String parentIf = ItmUtils.getHwParentIf(topo_id, srcNodeid); - String tunnelIfName = ItmUtils.getTrunkInterfaceName(idManagerService, parentIf, srcIp.getIpv4Address().getValue(), dstIp.getIpv4Address().getValue()); + String tunTypeStr = tunType.getName(); + String tunnelIfName = ItmUtils.getTrunkInterfaceName(idManagerService, parentIf, + srcIp.getIpv4Address().getValue(), dstIp.getIpv4Address().getValue(), tunTypeStr); logger.debug(" Creating ExternalTrunk Interface with parameters Name - {}, parent I/f name - {}, source IP - {}, destination IP - {} gateway IP - {}", tunnelIfName, parentIf, srcIp, dstIp, gwyIpAddress); Interface hwTunnelIf = ItmUtils.buildHwTunnelInterface(tunnelIfName, String.format("%s %s", tunType.getName(), "Trunk Interface"), - true, topo_id, srcNodeid, tunType, srcIp, dstIp, gwyIpAddress, true); + true, topo_id, srcNodeid, tunType, srcIp, dstIp, gwyIpAddress, monitorEnabled, monitorInterval); InstanceIdentifier ifIID = InstanceIdentifier.builder(Interfaces.class).child(Interface.class, new InterfaceKey(tunnelIfName)).build(); logger.trace(" Writing Trunk Interface to Config DS {}, {} ", ifIID, hwTunnelIf); + ItmUtils.itmCache.addInterface(hwTunnelIf); t.merge(LogicalDatastoreType.CONFIGURATION, ifIID, hwTunnelIf, true); // also update itm-state ds? InstanceIdentifier path = InstanceIdentifier.create( ExternalTunnelList.class) - .child(ExternalTunnel.class, new ExternalTunnelKey(getExternalTunnelKey(dstNodeId), getExternalTunnelKey(srcNodeid))); - ExternalTunnel tnl = ItmUtils.buildExternalTunnel(getExternalTunnelKey(srcNodeid), getExternalTunnelKey(dstNodeId), tunnelIfName); + .child(ExternalTunnel.class, new ExternalTunnelKey( getExternalTunnelKey(dstNodeId), getExternalTunnelKey(srcNodeid), tunType)); + ExternalTunnel tnl = ItmUtils.buildExternalTunnel( getExternalTunnelKey(srcNodeid), + getExternalTunnelKey(dstNodeId), + tunType, tunnelIfName); t.merge(LogicalDatastoreType.CONFIGURATION, path, tnl, true); + ItmUtils.itmCache.addExternalTunnel(tnl); return true; } //for tunnels from CSS private static boolean wireUp(BigInteger dpnId,String portname, Integer vlanId, IpAddress srcIp, String dstNodeId, IpAddress dstIp, IpPrefix srcSubnet, - IpAddress gWIp, IpPrefix dstSubnet, Class tunType, IdManagerService idManagerService, DataBroker dataBroker, List> futures, WriteTransaction t) { - IpAddress gwyIpAddress = (srcSubnet.equals(dstSubnet)) ? null : gWIp; + IpAddress gWIp, IpPrefix dstSubnet, Class tunType,Boolean monitorEnabled, Integer monitorInterval, + IdManagerService idManagerService, DataBroker dataBroker, List> futures, WriteTransaction t) { + IpAddress gatewayIpObj = new IpAddress("0.0.0.0".toCharArray()); + IpAddress gwyIpAddress = (srcSubnet.equals(dstSubnet)) ? gatewayIpObj : gWIp; String parentIf = ItmUtils.getInterfaceName(dpnId, portname, vlanId); - String tunnelIfName = ItmUtils.getTrunkInterfaceName(idManagerService, parentIf, srcIp.getIpv4Address().getValue(), dstIp.getIpv4Address().getValue()); + String tunTypeStr = tunType.getName(); + String tunnelIfName = ItmUtils.getTrunkInterfaceName(idManagerService, parentIf, + srcIp.getIpv4Address().getValue(), dstIp.getIpv4Address().getValue(), tunTypeStr); logger.debug(" Creating ExternalTrunk Interface with parameters Name - {}, parent I/f name - {}, source IP - {}, destination IP - {} gateway IP - {}", tunnelIfName, parentIf, srcIp, dstIp, gwyIpAddress); - Interface extTunnelIf = ItmUtils.buildTunnelInterface(dpnId, tunnelIfName, String.format("%s %s", tunType.getName(), "Trunk Interface"), true, tunType, srcIp, dstIp, gwyIpAddress, vlanId, false, true, 5L); + Interface extTunnelIf = ItmUtils.buildTunnelInterface(dpnId, tunnelIfName, String.format("%s %s", tunType.getName(), "Trunk Interface"), true, tunType, srcIp, dstIp, gwyIpAddress, vlanId, false,monitorEnabled, monitorInterval); InstanceIdentifier ifIID = InstanceIdentifier.builder(Interfaces.class).child(Interface.class, new InterfaceKey(tunnelIfName)).build(); logger.trace(" Writing Trunk Interface to Config DS {}, {} ", ifIID, extTunnelIf); t.merge(LogicalDatastoreType.CONFIGURATION, ifIID, extTunnelIf, true); + ItmUtils.itmCache.addInterface(extTunnelIf); InstanceIdentifier path = InstanceIdentifier.create( ExternalTunnelList.class) - .child(ExternalTunnel.class, new ExternalTunnelKey(getExternalTunnelKey(dstNodeId), dpnId.toString())); - ExternalTunnel tnl = ItmUtils.buildExternalTunnel(dpnId.toString(), getExternalTunnelKey(dstNodeId), tunnelIfName); + .child(ExternalTunnel.class, new ExternalTunnelKey(getExternalTunnelKey(dstNodeId), dpnId.toString(), tunType)); + ExternalTunnel tnl = ItmUtils.buildExternalTunnel( dpnId.toString(), + getExternalTunnelKey(dstNodeId), + tunType, tunnelIfName); t.merge(LogicalDatastoreType.CONFIGURATION, path, tnl, true); + ItmUtils.itmCache.addExternalTunnel(tnl); return true; } diff --git a/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/confighelpers/ItmExternalTunnelDeleteWorker.java b/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/confighelpers/ItmExternalTunnelDeleteWorker.java index c1d8f863..16e629a1 100644 --- a/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/confighelpers/ItmExternalTunnelDeleteWorker.java +++ b/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/confighelpers/ItmExternalTunnelDeleteWorker.java @@ -16,10 +16,13 @@ import com.google.common.base.Optional; import org.opendaylight.controller.md.sal.binding.api.DataBroker; import org.opendaylight.controller.md.sal.binding.api.WriteTransaction; import org.opendaylight.controller.md.sal.common.api.data.LogicalDatastoreType; +import org.opendaylight.vpnservice.itm.globals.ITMConstants; import org.opendaylight.vpnservice.itm.impl.ItmUtils; import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.inet.types.rev100924.IpAddress; import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.interfaces.rev140508.interfaces.Interface; import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.interfacemgr.rev150331.TunnelTypeBase; +import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.interfacemgr.rev150331.TunnelTypeGre; +import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.interfacemgr.rev150331.TunnelTypeVxlan; import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.op.rev150701.ExternalTunnelList; import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.op.rev150701.dpn.endpoints.DPNTEPsInfo; import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.op.rev150701.dpn.endpoints.dpn.teps.info.TunnelEndPoints; @@ -52,20 +55,26 @@ public class ItmExternalTunnelDeleteWorker { } for( DPNTEPsInfo teps : dpnTepsList) { TunnelEndPoints firstEndPt = teps.getTunnelEndPoints().get(0) ; - if( firstEndPt.getTunnelType().equals(tunType)) { String interfaceName = firstEndPt.getInterfaceName() ; - String trunkInterfaceName = ItmUtils.getTrunkInterfaceName(idManagerService, interfaceName,firstEndPt.getIpAddress().getIpv4Address().getValue(), extIp.getIpv4Address().getValue()) ; + String trunkInterfaceName = ItmUtils.getTrunkInterfaceName( idManagerService, interfaceName, + firstEndPt.getIpAddress().getIpv4Address().getValue(), + extIp.getIpv4Address().getValue(), + tunType.getName()); InstanceIdentifier trunkIdentifier = ItmUtils.buildId(trunkInterfaceName); t.delete(LogicalDatastoreType.CONFIGURATION, trunkIdentifier); + ItmUtils.itmCache.removeInterface(trunkInterfaceName); InstanceIdentifier path = InstanceIdentifier.create( ExternalTunnelList.class) - .child(ExternalTunnel.class, getExternalTunnelKey(extIp.toString(), teps.getDPNID().toString())); + .child(ExternalTunnel.class, ItmUtils.getExternalTunnelKey(extIp.toString(), + teps.getDPNID().toString(), + tunType)); t.delete(LogicalDatastoreType.CONFIGURATION, path); + logger.debug( "Deleting tunnel towards DC gateway, Tunnel interface name {} ",trunkInterfaceName ); + ItmUtils.itmCache.removeExternalTunnel(trunkInterfaceName); // Release the Ids for the trunk interface Name - ItmUtils.releaseIdForTrunkInterfaceName(idManagerService,interfaceName,firstEndPt.getIpAddress().getIpv4Address().getValue(), extIp.getIpv4Address().getValue() ); + ItmUtils.releaseIdForTrunkInterfaceName(idManagerService,interfaceName,firstEndPt.getIpAddress().getIpv4Address().getValue(), extIp.getIpv4Address().getValue(),tunType.getName()); } - } futures.add(t.submit()) ; return futures ; } @@ -73,23 +82,21 @@ public class ItmExternalTunnelDeleteWorker { public static List> deleteHwVtepsTunnels(DataBroker dataBroker, IdManagerService idManagerService, List delDpnList ,List cfgdHwVteps) { List> futures = new ArrayList<>(); WriteTransaction t = dataBroker.newWriteOnlyTransaction(); - if (null != delDpnList) { - tunnelsFromCSS(delDpnList, idManagerService , futures, t , dataBroker); - } - if (null != cfgdHwVteps) { - tunnelsFromhWVtep(cfgdHwVteps, idManagerService, futures, t, dataBroker); - } if (delDpnList != null || cfgdHwVteps != null) + tunnelsDeletion(delDpnList, cfgdHwVteps, idManagerService, futures, t, dataBroker); futures.add(t.submit()); return futures; } - private static void tunnelsFromCSS(List cfgdDpnList, IdManagerService idManagerService, List> futures, WriteTransaction t, DataBroker dataBroker) { + private static void tunnelsDeletion(List cfgdDpnList, List cfgdhwVteps, IdManagerService idManagerService, List> futures, WriteTransaction t, DataBroker dataBroker) { + if (cfgdDpnList != null && !cfgdDpnList.isEmpty()) { for (DPNTEPsInfo dpn : cfgdDpnList) { if (dpn.getTunnelEndPoints() != null && !dpn.getTunnelEndPoints().isEmpty()) for (TunnelEndPoints srcTep : dpn.getTunnelEndPoints()) { - InstanceIdentifier tzonePath = InstanceIdentifier.builder(TransportZones.class).child(TransportZone.class, new TransportZoneKey((srcTep.getTransportZone()))).build(); + InstanceIdentifier tzonePath = InstanceIdentifier.builder(TransportZones.class) + .child(TransportZone.class, new TransportZoneKey((srcTep.getTransportZone()))) + .build(); Optional tZoneOptional = ItmUtils.read(LogicalDatastoreType.CONFIGURATION, tzonePath, dataBroker); if (tZoneOptional.isPresent()) { TransportZone tZone = tZoneOptional.get(); @@ -100,13 +107,64 @@ public class ItmExternalTunnelDeleteWorker { for (DeviceVteps hwVtepDS : sub.getDeviceVteps()) { String cssID = dpn.getDPNID().toString(); //CSS-TOR-CSS - deleteTrunksCSSTOR(dataBroker, idManagerService, dpn.getDPNID(), - srcTep.getInterfaceName(), srcTep.getIpAddress(), - hwVtepDS.getTopologyId(), hwVtepDS.getNodeId(), - hwVtepDS.getIpAddress(), t, futures); + deleteTrunksCSSTOR(dataBroker, idManagerService, dpn.getDPNID(), srcTep.getInterfaceName(), srcTep.getIpAddress(), + hwVtepDS.getTopologyId(), hwVtepDS.getNodeId(), hwVtepDS.getIpAddress(), tZone.getTunnelType(), + t, futures); + } + } + } + } + if (cfgdhwVteps != null && !cfgdhwVteps.isEmpty()) { + for (HwVtep hwVtep : cfgdhwVteps) { + deleteTrunksCSSTOR(dataBroker, idManagerService, dpn.getDPNID(), srcTep.getInterfaceName(), srcTep.getIpAddress(), + hwVtep.getTopo_id(), hwVtep.getNode_id(), hwVtep.getHwIp(), + TunnelTypeVxlan.class, t, futures); + } + } + } + } + } + } + if (cfgdhwVteps != null && !cfgdhwVteps.isEmpty()) { + for (HwVtep hwTep : cfgdhwVteps) { + logger.trace("processing hwTep from list {}", hwTep); + for (HwVtep hwTepRemote : cfgdhwVteps) { + if (!hwTep.getHwIp().equals(hwTepRemote.getHwIp())) { + deleteTrunksTORTOR(dataBroker, idManagerService, hwTep.getTopo_id(), hwTep.getNode_id(), + hwTep.getHwIp(), hwTepRemote.getTopo_id(), hwTepRemote.getNode_id(), + hwTepRemote.getHwIp(), TunnelTypeVxlan.class, t, futures); + } + } + InstanceIdentifier tzonePath = InstanceIdentifier.builder(TransportZones.class) + .child(TransportZone.class, new TransportZoneKey((hwTep.getTransportZone()))).build(); + Optional tZoneOptional = ItmUtils.read(LogicalDatastoreType.CONFIGURATION, tzonePath, dataBroker); + if (tZoneOptional.isPresent()) { + TransportZone tZone = tZoneOptional.get(); + logger.trace("subnets under tz {} are {}", tZone.getZoneName(), tZone.getSubnets()); + if (tZone.getSubnets() != null && !tZone.getSubnets().isEmpty()) { + for (Subnets sub : tZone.getSubnets()) { + if (sub.getDeviceVteps() != null && !sub.getDeviceVteps().isEmpty()) { + for (DeviceVteps hwVtepDS : sub.getDeviceVteps()) { + logger.trace("hwtepDS exists {}", hwVtepDS); + if (hwVtepDS.getIpAddress().equals(hwTep.getHwIp())) + continue;//dont delete tunnels with self + logger.trace("deleting tor-tor {} and {}", hwTep, hwVtepDS); + deleteTrunksTORTOR(dataBroker, idManagerService, hwTep.getTopo_id(), hwTep.getNode_id(), + hwTep.getHwIp(), hwVtepDS.getTopologyId(), hwVtepDS.getNodeId(), + hwVtepDS.getIpAddress(), tZone.getTunnelType(), + t, futures); } } + if (sub.getVteps() != null && !sub.getVteps().isEmpty()) { + for (Vteps vtep : sub.getVteps()) { + logger.trace("deleting tor-css-tor {} and {}", hwTep, vtep); + String parentIf = ItmUtils.getInterfaceName(vtep.getDpnId(), vtep.getPortname(), sub.getVlanId()); + deleteTrunksCSSTOR(dataBroker, idManagerService, vtep.getDpnId(), parentIf, vtep.getIpAddress(), + hwTep.getTopo_id(), hwTep.getNode_id(), hwTep.getHwIp(), + tZone.getTunnelType(), t, futures); + } + } } } } @@ -118,83 +176,50 @@ public class ItmExternalTunnelDeleteWorker { - private static void tunnelsFromhWVtep(List cfgdHwVteps, IdManagerService idManagerService, List> futures, WriteTransaction t, DataBroker dataBroker) { - for (HwVtep hwTep : cfgdHwVteps) { - logger.trace("processing hwTep from list {}",hwTep); - InstanceIdentifier tzonePath = InstanceIdentifier.builder(TransportZones.class).child(TransportZone.class, new TransportZoneKey((hwTep.getTransportZone()))).build(); - Optional tZoneOptional = ItmUtils.read(LogicalDatastoreType.CONFIGURATION, tzonePath, dataBroker); - if (tZoneOptional.isPresent()) { - TransportZone tZone = tZoneOptional.get(); //do we need to check tunnel type? - logger.trace("subnets under tz {} are {}",tZone.getZoneName(),tZone.getSubnets()); - if (tZone.getSubnets() != null && !tZone.getSubnets().isEmpty()) { - for (Subnets sub : tZone.getSubnets()) { - if (sub.getDeviceVteps() != null && !sub.getDeviceVteps().isEmpty()) { - for (DeviceVteps hwVtepDS : sub.getDeviceVteps()) { - logger.trace("hwtepDS exists {}",hwVtepDS); //do i need to check node-id? //for mlag case and non-m-lag case, isnt it enough to just check ipaddress? - if (hwVtepDS.getIpAddress().equals(hwTep.getHwIp())) - continue;//dont delete tunnels with self //TOR-TOR - logger.trace("deleting tor-tor {} and {}",hwTep,hwVtepDS); - deleteTrunksTORTOR(dataBroker, idManagerService, hwTep.getTopo_id(), hwTep.getNode_id(), - hwTep.getHwIp(), hwVtepDS.getTopologyId(), hwVtepDS.getNodeId(), - hwVtepDS.getIpAddress(), t, futures); - } - } - if (sub.getVteps() != null && !sub.getVteps().isEmpty()) { - for (Vteps vtep : sub.getVteps()) { //TOR-CSS - logger.trace("deleting tor-css-tor {} and {}",hwTep,vtep); - String parentIf = ItmUtils.getInterfaceName(vtep.getDpnId(),vtep.getPortname(),sub.getVlanId()); - deleteTrunksCSSTOR(dataBroker,idManagerService,vtep.getDpnId(),parentIf,vtep.getIpAddress(), - hwTep.getTopo_id(),hwTep.getNode_id(),hwTep.getHwIp(),t,futures ); - } - } - } - } - } - } - } private static void deleteTrunksCSSTOR(DataBroker dataBroker, IdManagerService idManagerService, BigInteger dpnid, String interfaceName, IpAddress cssIpAddress, String topologyId, String nodeId, IpAddress hWIpAddress, - WriteTransaction t, List> futures) { + Class tunType, WriteTransaction t, + List> futures) { //CSS-TOR - if (trunkExists(dpnid.toString(), nodeId,dataBroker)) { + if (trunkExists(dpnid.toString(), nodeId, tunType, dataBroker)) { logger.trace("deleting tunnel from {} to {} ", dpnid.toString(), nodeId); String parentIf = interfaceName; String fwdTrunkIf = ItmUtils.getTrunkInterfaceName(idManagerService,parentIf,cssIpAddress.getIpv4Address().getValue(), - hWIpAddress.getIpv4Address().getValue()); + hWIpAddress.getIpv4Address().getValue(), tunType.getName()); InstanceIdentifier trunkIdentifier = ItmUtils.buildId(fwdTrunkIf); t.delete(LogicalDatastoreType.CONFIGURATION, trunkIdentifier); InstanceIdentifier path = InstanceIdentifier.create( ExternalTunnelList.class) - .child(ExternalTunnel.class, getExternalTunnelKey(nodeId, dpnid.toString())); + .child(ExternalTunnel.class, ItmUtils.getExternalTunnelKey(nodeId, dpnid.toString(), tunType)); t.delete(LogicalDatastoreType.CONFIGURATION, path); } else { logger.trace(" trunk from {} to {} already deleted",dpnid.toString(), nodeId); } //TOR-CSS - if (trunkExists( nodeId, dpnid.toString(),dataBroker)) { + if (trunkExists( nodeId, dpnid.toString(), tunType, dataBroker)) { logger.trace("deleting tunnel from {} to {} ",nodeId, dpnid.toString()); String parentIf = ItmUtils.getHwParentIf(topologyId,nodeId); String revTrunkIf = ItmUtils.getTrunkInterfaceName(idManagerService,parentIf, hWIpAddress.getIpv4Address().getValue(), - cssIpAddress.getIpv4Address().getValue()); + cssIpAddress.getIpv4Address().getValue(), tunType.getName()); InstanceIdentifier trunkIdentifier = ItmUtils.buildId(revTrunkIf); t.delete(LogicalDatastoreType.CONFIGURATION, trunkIdentifier); InstanceIdentifier path = InstanceIdentifier.create( ExternalTunnelList.class) - .child(ExternalTunnel.class, getExternalTunnelKey( dpnid.toString(),nodeId)); + .child(ExternalTunnel.class, ItmUtils.getExternalTunnelKey(dpnid.toString(),nodeId, tunType)); t.delete(LogicalDatastoreType.CONFIGURATION, path); } else { @@ -204,37 +229,39 @@ public class ItmExternalTunnelDeleteWorker { private static void deleteTrunksTORTOR(DataBroker dataBroker, IdManagerService idManagerService, String topologyId1, String nodeId1, IpAddress hWIpAddress1, String topologyId2, String nodeId2, IpAddress hWIpAddress2, - WriteTransaction t, List> futures) { + Class tunType, WriteTransaction t, List> futures) { //TOR1-TOR2 - if (trunkExists(nodeId1, nodeId2,dataBroker)) { + if (trunkExists(nodeId1, nodeId2, tunType, dataBroker)) { logger.trace("deleting tunnel from {} to {} ", nodeId1, nodeId2); String parentIf = ItmUtils.getHwParentIf(topologyId1,nodeId1); String fwdTrunkIf = ItmUtils.getTrunkInterfaceName(idManagerService, parentIf, - hWIpAddress1.getIpv4Address().getValue(), hWIpAddress2.getIpv4Address().getValue()); + hWIpAddress1.getIpv4Address().getValue(), + hWIpAddress2.getIpv4Address().getValue(), + tunType.getName()); InstanceIdentifier trunkIdentifier = ItmUtils.buildId(fwdTrunkIf); t.delete(LogicalDatastoreType.CONFIGURATION, trunkIdentifier); InstanceIdentifier path = InstanceIdentifier.create( ExternalTunnelList.class) - .child(ExternalTunnel.class, getExternalTunnelKey(nodeId2, nodeId1)); + .child(ExternalTunnel.class, ItmUtils.getExternalTunnelKey(nodeId2, nodeId1, tunType)); t.delete(LogicalDatastoreType.CONFIGURATION, path); } else { logger.trace(" trunk from {} to {} already deleted",nodeId1, nodeId2); } //TOR2-TOR1 - if (trunkExists( nodeId2, nodeId1,dataBroker)) { + if (trunkExists( nodeId2, nodeId1, tunType, dataBroker)) { logger.trace("deleting tunnel from {} to {} ",nodeId2, nodeId1); String parentIf = ItmUtils.getHwParentIf(topologyId2,nodeId2); String revTrunkIf = ItmUtils.getTrunkInterfaceName(idManagerService,parentIf, hWIpAddress2.getIpv4Address().getValue(), - hWIpAddress1.getIpv4Address().getValue()); + hWIpAddress1.getIpv4Address().getValue(), tunType.getName()); InstanceIdentifier trunkIdentifier = ItmUtils.buildId(revTrunkIf); t.delete(LogicalDatastoreType.CONFIGURATION, trunkIdentifier); InstanceIdentifier path = InstanceIdentifier.create( ExternalTunnelList.class) - .child(ExternalTunnel.class, getExternalTunnelKey( nodeId1,nodeId2)); + .child(ExternalTunnel.class, ItmUtils.getExternalTunnelKey(nodeId1,nodeId2, tunType)); t.delete(LogicalDatastoreType.CONFIGURATION, path); } else { @@ -242,25 +269,17 @@ public class ItmExternalTunnelDeleteWorker { } } - private static boolean trunkExists( String srcDpnOrNode, String dstDpnOrNode, DataBroker dataBroker) { + private static boolean trunkExists( String srcDpnOrNode, String dstDpnOrNode, + Class tunType,DataBroker dataBroker) { boolean existsFlag = false ; InstanceIdentifier path = InstanceIdentifier.create( ExternalTunnelList.class) - .child(ExternalTunnel.class, getExternalTunnelKey(dstDpnOrNode, srcDpnOrNode)); + .child(ExternalTunnel.class, ItmUtils.getExternalTunnelKey(dstDpnOrNode, srcDpnOrNode, tunType)); Optional exTunnels = ItmUtils.read(LogicalDatastoreType.CONFIGURATION,path, dataBroker) ; - if( exTunnels.isPresent()) + if( exTunnels.isPresent()) { existsFlag = true ; - return existsFlag ; } - - static ExternalTunnelKey getExternalTunnelKey(String dst , String src) { - if (src.indexOf("physicalswitch") > 0) { - src = src.substring(0, src.indexOf("physicalswitch") - 1); - } - if (dst.indexOf("physicalswitch") > 0) { - dst = dst.substring(0, dst.indexOf("physicalswitch") - 1); - } - return new ExternalTunnelKey(dst, src); + return existsFlag ; } diff --git a/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/confighelpers/ItmInternalTunnelAddWorker.java b/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/confighelpers/ItmInternalTunnelAddWorker.java index c1850200..9f219643 100644 --- a/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/confighelpers/ItmInternalTunnelAddWorker.java +++ b/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/confighelpers/ItmInternalTunnelAddWorker.java @@ -147,26 +147,34 @@ public class ItmInternalTunnelAddWorker { logger.trace( "Wiring between source tunnel end points {}, destination tunnel end points {} " , srcte, dstte ); String interfaceName = srcte.getInterfaceName() ; Class tunType = srcte.getTunnelType(); - String ifDescription = srcte.getTunnelType().getName(); + String tunTypeStr = srcte.getTunnelType().getName(); // Form the trunk Interface Name - String trunkInterfaceName = ItmUtils.getTrunkInterfaceName(idManagerService, interfaceName,srcte.getIpAddress().getIpv4Address().getValue(), dstte.getIpAddress().getIpv4Address().getValue()) ; - IpAddress gwyIpAddress = ( srcte.getSubnetMask().equals(dstte.getSubnetMask()) ) ? null : srcte.getGwIpAddress() ; + String trunkInterfaceName = ItmUtils.getTrunkInterfaceName( idManagerService, interfaceName, + srcte.getIpAddress().getIpv4Address().getValue(), + dstte.getIpAddress().getIpv4Address().getValue(), + tunTypeStr) ; + IpAddress gatewayIpObj = new IpAddress("0.0.0.0".toCharArray()); + IpAddress gwyIpAddress = ( srcte.getSubnetMask().equals(dstte.getSubnetMask()) ) ? gatewayIpObj : srcte.getGwIpAddress() ; logger.debug( " Creating Trunk Interface with parameters trunk I/f Name - {}, parent I/f name - {}, source IP - {}, destination IP - {} gateway IP - {}",trunkInterfaceName, interfaceName, srcte.getIpAddress(), dstte.getIpAddress(), gwyIpAddress ) ; - Interface iface = ItmUtils.buildTunnelInterface(srcDpnId, trunkInterfaceName, - String.format("%s %s", ifDescription, "Trunk Interface"), true, tunType, srcte.getIpAddress(), - dstte.getIpAddress(), gwyIpAddress, srcte.getVLANID(), true, false, null); + Boolean monitorEnabled = ItmUtils.readMonitoringStateFromDS(dataBroker); + Integer monitorInterval = ItmUtils.readMonitorIntervalfromDS(dataBroker); + if(monitorInterval == null) + monitorInterval = ITMConstants.DEFAULT_MONITOR_INTERVAL; + Interface iface = ItmUtils.buildTunnelInterface(srcDpnId, trunkInterfaceName, String.format( "%s %s",ItmUtils.convertTunnelTypetoString(srcte.getTunnelType()), "Trunk Interface"), true, tunType, srcte.getIpAddress(), dstte.getIpAddress(), gwyIpAddress, srcte.getVLANID(), true, monitorEnabled, monitorInterval*1000); logger.debug( " Trunk Interface builder - {} ", iface ) ; InstanceIdentifier trunkIdentifier = ItmUtils.buildId(trunkInterfaceName); logger.debug( " Trunk Interface Identifier - {} ", trunkIdentifier ) ; logger.trace( " Writing Trunk Interface to Config DS {}, {} ", trunkIdentifier, iface ) ; t.merge(LogicalDatastoreType.CONFIGURATION, trunkIdentifier, iface, true); + ItmUtils.itmCache.addInterface(iface); // also update itm-state ds? InstanceIdentifier path = InstanceIdentifier.create( TunnelList.class) - .child(InternalTunnel.class, new InternalTunnelKey( dstDpnId,srcDpnId )); - InternalTunnel tnl = ItmUtils.buildInternalTunnel(srcDpnId, dstDpnId, trunkInterfaceName); + .child(InternalTunnel.class, new InternalTunnelKey( dstDpnId, srcDpnId, tunType)); + InternalTunnel tnl = ItmUtils.buildInternalTunnel(srcDpnId, dstDpnId, tunType, trunkInterfaceName); //ItmUtils.asyncUpdate(LogicalDatastoreType.CONFIGURATION, path, tnl, dataBroker, DEFAULT_CALLBACK); t.merge(LogicalDatastoreType.CONFIGURATION,path, tnl, true) ; + ItmUtils.itmCache.addInternalTunnel(tnl); return true; } } diff --git a/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/confighelpers/ItmInternalTunnelDeleteWorker.java b/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/confighelpers/ItmInternalTunnelDeleteWorker.java index ed065b6e..210622f7 100644 --- a/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/confighelpers/ItmInternalTunnelDeleteWorker.java +++ b/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/confighelpers/ItmInternalTunnelDeleteWorker.java @@ -19,6 +19,7 @@ import org.opendaylight.vpnservice.itm.impl.ItmUtils; import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.interfaces.rev140508.interfaces.Interface; import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.idmanager.rev150403.IdManagerService; import org.opendaylight.vpnservice.mdsalutil.interfaces.IMdsalApiManager; +import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.interfacemgr.rev150331.TunnelTypeBase; import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.op.rev150701.DpnEndpoints; import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.op.rev150701.TunnelList; import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.op.rev150701.dpn.endpoints.DPNTEPsInfo; @@ -53,7 +54,12 @@ public class ItmInternalTunnelDeleteWorker { } for (DPNTEPsInfo srcDpn : dpnTepsList) { logger.trace("Processing srcDpn " + srcDpn); - List meshedEndPtCache = new ArrayList(srcDpn.getTunnelEndPoints()) ; + List meshedEndPtCache = new ArrayList(ItmUtils.getTEPsForDpn(srcDpn.getDPNID(), meshedDpnList)) ; + if(meshedEndPtCache == null ) { + logger.debug("No Tunnel End Point configured for this DPN {}", srcDpn.getDPNID()); + continue ; + } + logger.debug( "Entries in meshEndPointCache {} ", meshedEndPtCache.size() ); for (TunnelEndPoints srcTep : srcDpn.getTunnelEndPoints()) { logger.trace("Processing srcTep " + srcTep); String srcTZone = srcTep.getTransportZone(); @@ -64,7 +70,7 @@ public class ItmInternalTunnelDeleteWorker { for (TunnelEndPoints dstTep : dstDpn.getTunnelEndPoints()) { logger.trace("Processing dstTep " + dstTep); if (dstTep.getTransportZone().equals(srcTZone)) { - if( checkIfTrunkExists(dstDpn.getDPNID(), srcDpn.getDPNID(), dataBroker)) { + if( checkIfTrunkExists(dstDpn.getDPNID(), srcDpn.getDPNID(), srcTep.getTunnelType(),dataBroker)) { // remove all trunk interfaces logger.trace("Invoking removeTrunkInterface between source TEP {} , Destination TEP {} " ,srcTep , dstTep); removeTrunkInterface(dataBroker, idManagerService, srcTep, dstTep, srcDpn.getDPNID(), dstDpn.getDPNID(), t, futures); @@ -79,7 +85,7 @@ public class ItmInternalTunnelDeleteWorker { InstanceIdentifier.builder(DpnEndpoints.class).child(DPNTEPsInfo.class, srcDpn.getKey()) .child(TunnelEndPoints.class, srcTep.getKey()).build(); - logger.trace("Tep Removal from DPNTEPSINFO CONFIG DS " + srcTep); + logger.trace("Tep Removal of TEP {} from DPNTEPSINFO CONFIG DS with Key {} " + srcTep, srcTep.getKey()); t.delete(LogicalDatastoreType.CONFIGURATION, tepPath); // remove the tep from the cache meshedEndPtCache.remove(srcTep) ; @@ -128,28 +134,31 @@ public class ItmInternalTunnelDeleteWorker { TunnelEndPoints srcTep, TunnelEndPoints dstTep, BigInteger srcDpnId, BigInteger dstDpnId, WriteTransaction t, List> futures) { String trunkfwdIfName = - ItmUtils.getTrunkInterfaceName(idManagerService, srcTep.getInterfaceName(), srcTep.getIpAddress() - .getIpv4Address().getValue(), dstTep.getIpAddress().getIpv4Address() - .getValue()); + ItmUtils.getTrunkInterfaceName( idManagerService, srcTep.getInterfaceName(), + srcTep.getIpAddress().getIpv4Address().getValue(), + dstTep.getIpAddress().getIpv4Address().getValue(), + srcTep.getTunnelType().getName()); logger.trace("Removing forward Trunk Interface " + trunkfwdIfName); InstanceIdentifier trunkIdentifier = ItmUtils.buildId(trunkfwdIfName); logger.debug( " Removing Trunk Interface Name - {} , Id - {} from Config DS ", trunkfwdIfName, trunkIdentifier ) ; t.delete(LogicalDatastoreType.CONFIGURATION, trunkIdentifier); - + ItmUtils.itmCache.removeInterface(trunkfwdIfName); // also update itm-state ds -- Delete the forward tunnel-interface from the tunnel list InstanceIdentifier path = InstanceIdentifier.create( TunnelList.class) - .child(InternalTunnel.class, new InternalTunnelKey( srcDpnId, dstDpnId)); + .child(InternalTunnel.class, new InternalTunnelKey( dstDpnId, srcDpnId, srcTep.getTunnelType())); t.delete(LogicalDatastoreType.CONFIGURATION,path) ; + ItmUtils.itmCache.removeInternalTunnel(trunkfwdIfName); // Release the Ids for the forward trunk interface Name ItmUtils.releaseIdForTrunkInterfaceName(idManagerService,srcTep.getInterfaceName(), srcTep.getIpAddress() .getIpv4Address().getValue(), dstTep.getIpAddress().getIpv4Address() - .getValue() ); + .getValue(), srcTep.getTunnelType().getName() ); String trunkRevIfName = - ItmUtils.getTrunkInterfaceName(idManagerService, dstTep.getInterfaceName(), dstTep.getIpAddress() - .getIpv4Address().getValue(), srcTep.getIpAddress().getIpv4Address() - .getValue()); + ItmUtils.getTrunkInterfaceName( idManagerService, dstTep.getInterfaceName(), + dstTep.getIpAddress().getIpv4Address().getValue(), + srcTep.getIpAddress().getIpv4Address().getValue(), + srcTep.getTunnelType().getName()); logger.trace("Removing Reverse Trunk Interface " + trunkRevIfName); trunkIdentifier = ItmUtils.buildId(trunkRevIfName); logger.debug( " Removing Trunk Interface Name - {} , Id - {} from Config DS ", trunkRevIfName, trunkIdentifier ) ; @@ -158,19 +167,19 @@ public class ItmInternalTunnelDeleteWorker { // also update itm-state ds -- Delete the reverse tunnel-interface from the tunnel list path = InstanceIdentifier.create( TunnelList.class) - .child(InternalTunnel.class, new InternalTunnelKey(dstDpnId, srcDpnId)); + .child(InternalTunnel.class, new InternalTunnelKey(dstDpnId, srcDpnId, srcTep.getTunnelType())); t.delete(LogicalDatastoreType.CONFIGURATION,path) ; // Release the Ids for the reverse trunk interface Name ItmUtils.releaseIdForTrunkInterfaceName(idManagerService, dstTep.getInterfaceName(), dstTep.getIpAddress() .getIpv4Address().getValue(), srcTep.getIpAddress().getIpv4Address() - .getValue()); + .getValue(),dstTep.getTunnelType().getName()); } - private static boolean checkIfTrunkExists( BigInteger srcDpnId, BigInteger dstDpnId, DataBroker dataBroker) { + private static boolean checkIfTrunkExists(BigInteger srcDpnId, BigInteger dstDpnId, Class tunType, DataBroker dataBroker) { boolean existsFlag = false ; InstanceIdentifier path = InstanceIdentifier.create( TunnelList.class) - .child(InternalTunnel.class, new InternalTunnelKey( srcDpnId, dstDpnId)); + .child(InternalTunnel.class, new InternalTunnelKey( dstDpnId, srcDpnId, tunType)); Optional internalTunnels = ItmUtils.read(LogicalDatastoreType.CONFIGURATION,path, dataBroker) ; if( internalTunnels.isPresent()) existsFlag = true ; diff --git a/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/confighelpers/ItmMonitorIntervalWorker.java b/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/confighelpers/ItmMonitorIntervalWorker.java new file mode 100644 index 00000000..f2b64e6e --- /dev/null +++ b/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/confighelpers/ItmMonitorIntervalWorker.java @@ -0,0 +1,80 @@ +/* + * Copyright (c) 2016 Ericsson India Global Services Pvt Ltd. and others. All rights reserved. + * + * This program and the accompanying materials are made available under the + * terms of the Eclipse Public License v1.0 which accompanies this distribution, + * and is available at http://www.eclipse.org/legal/epl-v10.html + */ +package org.opendaylight.vpnservice.itm.confighelpers; + +import com.google.common.util.concurrent.ListenableFuture; +import org.opendaylight.controller.md.sal.binding.api.DataBroker; +import org.opendaylight.controller.md.sal.binding.api.WriteTransaction; +import org.opendaylight.controller.md.sal.common.api.data.LogicalDatastoreType; +import org.opendaylight.vpnservice.itm.impl.ItmUtils; +import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.interfaces.rev140508.interfaces.Interface; +import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.interfaces.rev140508.interfaces.InterfaceBuilder; +import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.interfaces.rev140508.interfaces.InterfaceKey; +import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.interfacemgr.rev150331.IfTunnel; +import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.interfacemgr.rev150331.IfTunnelBuilder; +import org.opendaylight.yangtools.yang.binding.InstanceIdentifier; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; + +import java.util.ArrayList; +import java.util.List; +import java.util.concurrent.Callable; + +/** + * Created by eanraju on 23-Mar-16. + */ +public class ItmMonitorIntervalWorker implements Callable>> { + private static final Logger logger = LoggerFactory.getLogger(ItmMonitorIntervalWorker.class) ; + private DataBroker dataBroker; + private String tzone; + private Integer interval; + private List hwVteps; + private Boolean exists; + + public ItmMonitorIntervalWorker(List hwVteps,String tzone,Integer interval, DataBroker dataBroker, Boolean exists){ + this.dataBroker = dataBroker; + this.tzone = tzone; + this.interval = interval; + this.hwVteps = hwVteps; + this.exists = exists; + logger.trace("ItmMonitorToggleWorker initialized with tzone {} and Interval {}",tzone,interval ); + } + + @Override public List> call() throws Exception { + List> futures = new ArrayList<>() ; + logger.debug("Invoking Tunnel Monitor Worker tzone = {} Interval= {}",tzone,interval ); + WriteTransaction t = dataBroker.newWriteOnlyTransaction(); + toggleTunnelMonitoring(hwVteps,interval,tzone,t,exists); + futures.add(t.submit()); + return futures; + } + + private void toggleTunnelMonitoring(List hwVteps,Integer interval, String tzone, WriteTransaction t,Boolean exists) { + //exists means hwVteps exist for this tzone + + //List TunnelList = ItmUtils.getTunnelsofTzone(hwVteps, tzone, dataBroker, exists); + List TunnelList = ItmUtils.getInternalTunnelsofTzone(tzone,dataBroker); + if(TunnelList !=null &&!TunnelList.isEmpty()) { + for (String tunnel : TunnelList) + toggle(tunnel, interval,t); + } + } + + private void toggle(String tunnelInterfaceName, Integer interval, WriteTransaction t) { + if (tunnelInterfaceName != null) { + logger.debug("tunnel {} will have monitor interval {}", tunnelInterfaceName, interval); + InstanceIdentifier trunkIdentifier = ItmUtils.buildId(tunnelInterfaceName); + IfTunnel tunnel = new IfTunnelBuilder().setMonitorInterval(interval.longValue() * 1000).build(); + InterfaceBuilder builder = new InterfaceBuilder().setKey(new InterfaceKey(tunnelInterfaceName)) + .addAugmentation(IfTunnel.class, tunnel); + t.merge(LogicalDatastoreType.CONFIGURATION, trunkIdentifier, builder.build()); + } + } +} + + diff --git a/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/confighelpers/ItmMonitorToggleWorker.java b/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/confighelpers/ItmMonitorToggleWorker.java new file mode 100644 index 00000000..de363d81 --- /dev/null +++ b/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/confighelpers/ItmMonitorToggleWorker.java @@ -0,0 +1,85 @@ +/* + * Copyright (c) 2015, 2016 Ericsson India Global Services Pvt Ltd. and others. All rights reserved. + * + * This program and the accompanying materials are made available under the + * terms of the Eclipse Public License v1.0 which accompanies this distribution, + * and is available at http://www.eclipse.org/legal/epl-v10.html + */ +package org.opendaylight.vpnservice.itm.confighelpers; + +import com.google.common.base.Optional; +import com.google.common.util.concurrent.ListenableFuture; +import org.opendaylight.controller.md.sal.binding.api.DataBroker; +import org.opendaylight.controller.md.sal.binding.api.WriteTransaction; +import org.opendaylight.controller.md.sal.common.api.data.LogicalDatastoreType; +import org.opendaylight.vpnservice.itm.impl.ItmUtils; +import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.interfaces.rev140508.interfaces.Interface; +import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.interfaces.rev140508.interfaces.InterfaceBuilder; +import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.interfaces.rev140508.interfaces.InterfaceKey; +import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.interfacemgr.rev150331.IfTunnel; +import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.interfacemgr.rev150331.IfTunnelBuilder; +import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.op.rev150701.ExternalTunnelList; +import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.op.rev150701.TunnelList; +import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.op.rev150701.external.tunnel.list.ExternalTunnel; +import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.op.rev150701.tunnel.list.InternalTunnel; +import org.opendaylight.yangtools.yang.binding.InstanceIdentifier; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; + +import java.util.ArrayList; +import java.util.List; +import java.util.concurrent.Callable; + +/** + * Created by eanraju on 23-Mar-16. + */ +public class ItmMonitorToggleWorker implements Callable>> { + private static final Logger logger = LoggerFactory.getLogger(ItmMonitorToggleWorker.class) ; + private DataBroker dataBroker; + private String tzone; + private boolean enabled; + private List hwVteps; + private Boolean exists; + + public ItmMonitorToggleWorker(List hwVteps,String tzone,boolean enabled, DataBroker dataBroker, Boolean exists){ + this.dataBroker = dataBroker; + this.tzone = tzone; + this.enabled = enabled; + this.hwVteps = hwVteps; + this.exists = exists; + logger.trace("ItmMonitorToggleWorker initialized with tzone {} and toggleBoolean {}",tzone,enabled ); + } + + @Override public List> call() throws Exception { + List> futures = new ArrayList<>() ; + logger.debug("Invoking Tunnel Monitor Worker tzone = {} enabled {}",tzone,enabled ); + WriteTransaction t = dataBroker.newWriteOnlyTransaction(); + toggleTunnelMonitoring(hwVteps,enabled,tzone,t,exists); + futures.add(t.submit()); + return futures; + } + + private void toggleTunnelMonitoring(List hwVteps,Boolean enabled, String tzone, WriteTransaction t,Boolean exists) { + //exists means hwVteps exist for this tzone + + List TunnelList = ItmUtils.getTunnelsofTzone(hwVteps,tzone,dataBroker,exists); + if(TunnelList !=null &&!TunnelList.isEmpty()) { + for (String tunnel : TunnelList) + toggle(tunnel, enabled,t); + } + } + + private void toggle(String tunnelInterfaceName, boolean enabled, WriteTransaction t) { + if(tunnelInterfaceName!=null) { + InstanceIdentifier trunkIdentifier = ItmUtils.buildId(tunnelInterfaceName); + IfTunnel tunnel = new IfTunnelBuilder().setMonitorEnabled(enabled).build(); + InterfaceBuilder builder = new InterfaceBuilder().setKey(new InterfaceKey(tunnelInterfaceName)) + .addAugmentation(IfTunnel.class, tunnel); + t.merge(LogicalDatastoreType.CONFIGURATION, trunkIdentifier, builder.build()); + } + } +} + + + + diff --git a/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/impl/ItmCache.java b/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/impl/ItmCache.java new file mode 100644 index 00000000..8366e2e1 --- /dev/null +++ b/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/impl/ItmCache.java @@ -0,0 +1,71 @@ +/* + * Copyright (c) 2016 Ericsson India Global Services Pvt Ltd. and others. All rights reserved. + * + * This program and the accompanying materials are made available under the + * terms of the Eclipse Public License v1.0 which accompanies this distribution, + * and is available at http://www.eclipse.org/legal/epl-v10.html + */ + +package org.opendaylight.vpnservice.itm.impl; + +import java.util.Collection; +import java.util.HashMap; +import java.util.Map; +import java.util.concurrent.ConcurrentHashMap; + +import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.interfaces.rev140508.interfaces.Interface; +import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.op.rev150701.external.tunnel.list.ExternalTunnel; +import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.op.rev150701.tunnel.list.InternalTunnel; + +public class ItmCache { + private ConcurrentHashMap interfaces = null; + private ConcurrentHashMap externalTunnels = null; + private ConcurrentHashMap internalTunnels = null; + + public ItmCache() { + this.interfaces = new ConcurrentHashMap<>(); + this.internalTunnels = new ConcurrentHashMap<>(); + this.externalTunnels = new ConcurrentHashMap<>(); + } + + public void addInterface(Interface iface) { + this.interfaces.put(iface.getName(), iface); + } + + public Interface getInterface(String name) { + return this.interfaces.get(name); + } + + public Interface removeInterface(String name) { + return this.interfaces.remove(name); + } + + public Collection getAllInterfaces() { + return this.interfaces.values(); + } + + public void addExternalTunnel(ExternalTunnel tunnel) { + this.externalTunnels.put(tunnel.getTunnelInterfaceName(), tunnel); + } + + public ExternalTunnel getExternalTunnel(String name) { + return this.externalTunnels.get(name); + } + + public ExternalTunnel removeExternalTunnel(String name) { + return this.externalTunnels.remove(name); + } + + public void addInternalTunnel(InternalTunnel tunnel) { + this.internalTunnels.put(tunnel.getTunnelInterfaceName(), tunnel); + } + + public InternalTunnel getInternalTunnel(String name) { + return this.internalTunnels.get(name); + } + + public InternalTunnel removeInternalTunnel(String name) { + return this.internalTunnels.remove(name); + } + +} diff --git a/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/impl/ItmProvider.java b/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/impl/ItmProvider.java index 57ed05ae..413cf3f8 100644 --- a/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/impl/ItmProvider.java +++ b/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/impl/ItmProvider.java @@ -24,9 +24,12 @@ import org.opendaylight.vpnservice.interfacemgr.interfaces.IInterfaceManager; import org.opendaylight.vpnservice.itm.api.IITMProvider; import org.opendaylight.vpnservice.itm.cli.TepCommandHelper; import org.opendaylight.vpnservice.itm.globals.ITMConstants; -import org.opendaylight.vpnservice.itm.impl.ItmUtils; +import org.opendaylight.vpnservice.itm.listeners.InterfaceStateListener; import org.opendaylight.vpnservice.itm.listeners.TransportZoneListener; +import org.opendaylight.vpnservice.itm.listeners.TunnelMonitorChangeListener; +import org.opendaylight.vpnservice.itm.listeners.TunnelMonitorIntervalListener; import org.opendaylight.vpnservice.itm.listeners.VtepConfigSchemaListener; +import org.opendaylight.vpnservice.itm.monitoring.ItmTunnelEventListener; import org.opendaylight.vpnservice.itm.rpc.ItmManagerRpcService; import org.opendaylight.vpnservice.itm.snd.ITMStatusMonitor; import org.opendaylight.vpnservice.mdsalutil.MDSALUtil; @@ -40,8 +43,8 @@ import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.config.rev15 import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.idmanager.rev150403.CreateIdPoolInput; import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.idmanager.rev150403.CreateIdPoolInputBuilder; import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.idmanager.rev150403.IdManagerService; -import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.interfacemgr.rpcs.rev151003.OdlInterfaceRpcService; import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.rpcs.rev151217.ItmRpcService; +import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.op.rev150701.TunnelList ; import org.opendaylight.yangtools.yang.common.RpcResult; import org.slf4j.Logger; import org.slf4j.LoggerFactory; @@ -62,9 +65,13 @@ public class ItmProvider implements BindingAwareProvider, AutoCloseable, IITMPro private NotificationService notificationService; private TepCommandHelper tepCommandHelper; private TransportZoneListener tzChangeListener; + private TunnelMonitorChangeListener tnlToggleListener; + private TunnelMonitorIntervalListener tnlIntervalListener; private VtepConfigSchemaListener vtepConfigSchemaListener; + private InterfaceStateListener ifStateListener; private RpcProviderRegistry rpcProviderRegistry; private static final ITMStatusMonitor itmStatusMonitor = ITMStatusMonitor.getInstance(); + private ItmTunnelEventListener itmStateListener; static short flag = 0; public ItmProvider() { @@ -92,6 +99,9 @@ public class ItmProvider implements BindingAwareProvider, AutoCloseable, IITMPro tzChangeListener = new TransportZoneListener(dataBroker, idManager) ; itmRpcService = new ItmManagerRpcService(dataBroker, idManager); vtepConfigSchemaListener = new VtepConfigSchemaListener(dataBroker); + this.ifStateListener = new InterfaceStateListener(dataBroker); + tnlToggleListener = new TunnelMonitorChangeListener(dataBroker); + tnlIntervalListener = new TunnelMonitorIntervalListener(dataBroker); tepCommandHelper = new TepCommandHelper(dataBroker); final BindingAwareBroker.RpcRegistration rpcRegistration = getRpcProviderRegistry().addRpcImplementation(ItmRpcService.class, itmRpcService); itmRpcService.setMdsalManager(mdsalManager); @@ -101,8 +111,11 @@ public class ItmProvider implements BindingAwareProvider, AutoCloseable, IITMPro tzChangeListener.setMdsalManager(mdsalManager); tzChangeListener.setItmManager(itmManager); tzChangeListener.registerListener(LogicalDatastoreType.CONFIGURATION, dataBroker); + tnlIntervalListener.registerListener(LogicalDatastoreType.CONFIGURATION, dataBroker); + tnlToggleListener.registerListener(LogicalDatastoreType.CONFIGURATION, dataBroker); tepCommandHelper = new TepCommandHelper(dataBroker); tepCommandHelper.setInterfaceManager(interfaceManager); + itmStateListener =new ItmTunnelEventListener(dataBroker); createIdPool(); itmStatusMonitor.reportStatus("OPERATIONAL"); } catch (Exception e) { @@ -134,7 +147,12 @@ public class ItmProvider implements BindingAwareProvider, AutoCloseable, IITMPro if (tzChangeListener != null) { tzChangeListener.close(); } - + if (tnlIntervalListener != null) { + tnlIntervalListener.close(); + } + if(tnlToggleListener!= null){ + tnlToggleListener.close(); + } LOG.info("ItmProvider Closed"); } @@ -183,6 +201,12 @@ public class ItmProvider implements BindingAwareProvider, AutoCloseable, IITMPro tepCommandHelper.showTeps(itmManager.getTunnelMonitorEnabledFromConfigDS(), itmManager.getTunnelMonitorIntervalFromConfigDS()); } + public void showState(TunnelList tunnels) { + if (tunnels != null) + tepCommandHelper.showState(tunnels, itmManager.getTunnelMonitorEnabledFromConfigDS()); + else + LOG.debug("No tunnels available"); + } public void deleteVtep(BigInteger dpnId, String portName, Integer vlanId, String ipAddress, String subnetMask, String gatewayIp, String transportZone) { @@ -272,21 +296,27 @@ public class ItmProvider implements BindingAwareProvider, AutoCloseable, IITMPro this); if (ItmUtils.getDpnIdList(schema.getDpnIds()) == null) { VtepConfigSchemaBuilder builder = new VtepConfigSchemaBuilder(schema); + if (ItmUtils.getDpnIdList(schema.getDpnIds()).isEmpty()) { builder.setDpnIds(schema.getDpnIds()); schema = builder.build(); } else { if (lstDpnsForAdd != null && !lstDpnsForAdd.isEmpty()) { - ItmUtils.getDpnIdList(schema.getDpnIds()).addAll(lstDpnsForAdd); + List originalDpnList = ItmUtils.getDpnIdList(schema.getDpnIds()) ; + originalDpnList.addAll(lstDpnsForAdd) ; + builder.setDpnIds(ItmUtils.getDpnIdsListFromBigInt(originalDpnList)); } if (lstDpnsForDelete != null && !lstDpnsForDelete.isEmpty()) { - ItmUtils.getDpnIdList(schema.getDpnIds()).removeAll(lstDpnsForDelete); + List originalDpnList = ItmUtils.getDpnIdList(schema.getDpnIds()) ; + originalDpnList.removeAll(lstDpnsForAdd) ; + builder.setDpnIds(ItmUtils.getDpnIdsListFromBigInt(originalDpnList)) ; } } + schema = builder.build(); MDSALUtil.syncWrite(this.dataBroker, LogicalDatastoreType.CONFIGURATION, ItmUtils.getVtepConfigSchemaIdentifier(schemaName), schema); LOG.debug("Vtep config schema {} updated to config DS with DPN's {}", schemaName, ItmUtils.getDpnIdList(schema.getDpnIds())); } - + } /* * (non-Javadoc) * diff --git a/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/impl/ItmUtils.java b/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/impl/ItmUtils.java index 7aa7fa99..c86cbe0c 100644 --- a/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/impl/ItmUtils.java +++ b/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/impl/ItmUtils.java @@ -31,6 +31,8 @@ import org.opendaylight.vpnservice.itm.confighelpers.HwVtep; import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.interfaces.rev140508.interfaces.InterfaceBuilder; import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.interfaces.rev140508.interfaces.InterfaceKey; import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.iana._if.type.rev140508.Tunnel; +import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.config.rev151102.TunnelMonitorEnabled; +import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.config.rev151102.TunnelMonitorInterval; import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.config.rev151102.VtepConfigSchemas; import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.config.rev151102.VtepIpPools; import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.config.rev151102.vtep.config.schemas.VtepConfigSchema; @@ -50,6 +52,8 @@ import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.interfacemgr.rev import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.interfacemgr.rev150331.interfaces._interface.NodeIdentifierKey; import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.op.rev150701.DpnEndpoints; import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.op.rev150701.DpnEndpointsBuilder; +import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.op.rev150701.ExternalTunnelList; +import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.op.rev150701.TunnelList; import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.op.rev150701.dpn.endpoints.DPNTEPsInfo; import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.op.rev150701.dpn.endpoints.DPNTEPsInfoBuilder; import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.op.rev150701.dpn.endpoints.DPNTEPsInfoKey; @@ -62,6 +66,7 @@ import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.op.rev150701 import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.op.rev150701.tunnel.list.InternalTunnel; import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.op.rev150701.tunnel.list.InternalTunnelBuilder; import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.op.rev150701.tunnel.list.InternalTunnelKey; +import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.op.rev150701.tunnels_state.StateTunnelListKey; import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.interfacemgr.rev150331.TunnelTypeGre; import org.opendaylight.vpnservice.mdsalutil.interfaces.IMdsalApiManager; import org.opendaylight.vpnservice.itm.globals.ITMConstants; @@ -69,15 +74,19 @@ import org.opendaylight.vpnservice.mdsalutil.MDSALUtil; import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.inet.types.rev100924.IpAddress; import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.inet.types.rev100924.IpPrefix; import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.interfaces.rev140508.InterfaceType; +import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.interfaces.rev140508.InterfacesState; import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.interfaces.rev140508.interfaces.Interface; import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.types.rev131026.instruction.list.Instruction; import org.opendaylight.yang.gen.v1.urn.opendaylight.l2.types.rev130827.VlanId; import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.config.rev151102.vtep.config.schemas.vtep.config.schema.DpnIds ; //import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice._interface.service.rev150602._interface.service.info.ServiceInfo; +import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.rev150701.TransportZones; import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.rev150701.transport.zones.TransportZone; import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.config.rev151102.vtep.config.schemas.vtep.config.schema.DpnIdsBuilder; import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.config.rev151102.vtep.config.schemas.vtep.config.schema.DpnIdsKey; -import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.config.rev151102.vtep.config.schemas.vtep.config.schema.DpnIds; +import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.rev150701.transport.zones.TransportZoneKey; +import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.rev150701.transport.zones.transport.zone.Subnets; +import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.rev150701.transport.zones.transport.zone.subnets.Vteps; import org.opendaylight.yangtools.yang.binding.DataObject; import org.opendaylight.yangtools.yang.binding.InstanceIdentifier; import org.opendaylight.yangtools.yang.binding.InstanceIdentifier.InstanceIdentifierBuilder; @@ -107,6 +116,7 @@ public class ItmUtils { public static final String TUNNEL_TYPE_VXLAN = "VXLAN"; public static final String TUNNEL_TYPE_GRE = "GRE"; public static final String TUNNEL = "TUNNEL"; + public static ItmCache itmCache = new ItmCache(); private static final Logger LOG = LoggerFactory.getLogger(ItmUtils.class); @@ -176,14 +186,29 @@ public class ItmUtils { return dpnId; } - public static String getTrunkInterfaceName(IdManagerService idManager, String parentInterfaceName, String localHostName, String remoteHostName) { - String trunkInterfaceName = String.format("%s:%s:%s", parentInterfaceName, localHostName, remoteHostName); + public static String getTrunkInterfaceName(IdManagerService idManager, String parentInterfaceName, + String localHostName, String remoteHostName, String tunnelType) { + String tunnelTypeStr; + if(tunnelType.contains("TunnelTypeGre")) { + tunnelTypeStr = ITMConstants.TUNNEL_TYPE_GRE; + } else { + tunnelTypeStr = ITMConstants.TUNNEL_TYPE_VXLAN; + } + String trunkInterfaceName = String.format( "%s:%s:%s:%s", parentInterfaceName, localHostName, + remoteHostName, tunnelTypeStr); + LOG.trace("trunk interface name is {}", trunkInterfaceName); trunkInterfaceName = String.format("%s:%s", TUNNEL, getUniqueId(idManager, trunkInterfaceName)); return trunkInterfaceName; } - public static void releaseIdForTrunkInterfaceName(IdManagerService idManager, String parentInterfaceName, String localHostName, String remoteHostName) { - String trunkInterfaceName = String.format("%s:%s:%s", parentInterfaceName, localHostName, remoteHostName); + public static void releaseIdForTrunkInterfaceName(IdManagerService idManager, String parentInterfaceName, String localHostName, String remoteHostName, String tunnelType) { + String tunnelTypeStr; + if(tunnelType.contains("TunnelTypeGre")) { + tunnelTypeStr = ITMConstants.TUNNEL_TYPE_GRE; + } else { + tunnelTypeStr = ITMConstants.TUNNEL_TYPE_VXLAN; + } + String trunkInterfaceName = String.format("%s:%s:%s:%s", parentInterfaceName, localHostName, remoteHostName, tunnelTypeStr); LOG.trace("Releasing Id for trunkInterface - {}", trunkInterfaceName ); releaseId(idManager, trunkInterfaceName) ; } @@ -194,7 +219,8 @@ public class ItmUtils { public static InstanceIdentifier getDPNTEPInstance(BigInteger dpIdKey) { InstanceIdentifier.InstanceIdentifierBuilder dpnTepInfoBuilder = - InstanceIdentifier.builder(DpnEndpoints.class).child(DPNTEPsInfo.class, new DPNTEPsInfoKey(dpIdKey)); + InstanceIdentifier.builder(DpnEndpoints.class).child(DPNTEPsInfo.class, + new DPNTEPsInfoKey(dpIdKey)); InstanceIdentifier dpnInfo = dpnTepInfoBuilder.build(); return dpnInfo; } @@ -207,7 +233,7 @@ public class ItmUtils { public static TunnelEndPoints createTunnelEndPoints(BigInteger dpnId, IpAddress ipAddress, String portName, int vlanId, IpPrefix prefix, IpAddress gwAddress, String zoneName, Class tunnel_type) { // when Interface Mgr provides support to take in Dpn Id - return new TunnelEndPointsBuilder().setKey(new TunnelEndPointsKey(ipAddress, portName, vlanId)) + return new TunnelEndPointsBuilder().setKey(new TunnelEndPointsKey(ipAddress, portName,tunnel_type, vlanId)) .setSubnetMask(prefix).setGwIpAddress(gwAddress).setTransportZone(zoneName) .setInterfaceName(ItmUtils.getInterfaceName(dpnId, portName, vlanId)).setTunnelType(tunnel_type).build(); } @@ -224,7 +250,7 @@ public class ItmUtils { } public static Interface buildTunnelInterface(BigInteger dpn, String ifName, String desc, boolean enabled, Class tunType, - IpAddress localIp, IpAddress remoteIp, IpAddress gatewayIp,Integer vlanId, boolean internal, boolean monitorEnabled, Long monitorInterval) { + IpAddress localIp, IpAddress remoteIp, IpAddress gatewayIp,Integer vlanId, boolean internal, Boolean monitorEnabled, Integer monitorInterval) { InterfaceBuilder builder = new InterfaceBuilder().setKey(new InterfaceKey(ifName)).setName(ifName) .setDescription(desc).setEnabled(enabled).setType(Tunnel.class); ParentRefs parentRefs = new ParentRefsBuilder().setDatapathNodeIdentifier(dpn).build(); @@ -233,21 +259,25 @@ public class ItmUtils { IfL2vlan l2vlan = new IfL2vlanBuilder().setVlanId(new VlanId(vlanId)).build(); builder.addAugmentation(IfL2vlan.class, l2vlan); } - //use default monitoring value from Global Constants - Long monitoringInterval = 10000L; + Long monitoringInterval = (long) ITMConstants.DEFAULT_MONITOR_INTERVAL; + Boolean monitoringEnabled = true; if(monitorInterval!= null) - monitoringInterval = monitorInterval; - IfTunnel tunnel = new IfTunnelBuilder().setTunnelDestination(remoteIp).setTunnelGateway(gatewayIp).setTunnelSource(localIp) - .setTunnelInterfaceType(tunType).setInternal(internal).setMonitorEnabled(monitorEnabled).setMonitorInterval(monitoringInterval).build(); + monitoringInterval = monitorInterval.longValue(); + if(monitorEnabled!=null ) + monitoringEnabled = monitorEnabled; + IfTunnel tunnel = new IfTunnelBuilder().setTunnelDestination(remoteIp).setTunnelGateway( + gatewayIp).setTunnelSource(localIp) + .setTunnelInterfaceType(tunType).setInternal(internal).setMonitorEnabled( + monitoringEnabled).setMonitorInterval(monitoringInterval).build(); builder.addAugmentation(IfTunnel.class, tunnel); return builder.build(); } - public static Interface buildHwTunnelInterface(String tunnelIfName, String desc , boolean enabled, String topo_id, String node_id, - Class tunType, IpAddress srcIp , IpAddress destIp, IpAddress gWIp, - boolean monitor_enabled - ){ - InterfaceBuilder builder = new InterfaceBuilder().setKey(new InterfaceKey(tunnelIfName)).setName(tunnelIfName).setDescription(desc). + public static Interface buildHwTunnelInterface(String tunnelIfName, String desc, boolean enabled, String topo_id, + String node_id, Class tunType, IpAddress srcIp, IpAddress destIp, + IpAddress gWIp, Boolean monitor_enabled, Integer monitor_interval){ + InterfaceBuilder builder = new InterfaceBuilder().setKey(new InterfaceKey(tunnelIfName)).setName( + tunnelIfName).setDescription(desc). setEnabled(enabled).setType(Tunnel.class); List nodeIds = new ArrayList(); NodeIdentifier hWnode = new NodeIdentifierBuilder().setKey(new NodeIdentifierKey(topo_id)).setTopologyId( @@ -256,24 +286,38 @@ public class ItmUtils { nodeIds.add(hWnode); ParentRefs parent = new ParentRefsBuilder().setNodeIdentifier(nodeIds).build(); builder.addAugmentation(ParentRefs.class , parent); + Long monitoringInterval = (long) ITMConstants.DEFAULT_MONITOR_INTERVAL; + Boolean monitoringEnabled = true; + if(monitor_interval!= null) + monitoringInterval = monitor_interval.longValue(); + if(monitor_enabled!=null ) + monitoringEnabled = monitor_enabled; IfTunnel tunnel = new IfTunnelBuilder().setTunnelDestination(destIp).setTunnelGateway(gWIp).setTunnelSource( - srcIp).setMonitorEnabled(monitor_enabled).setTunnelInterfaceType(tunType).setInternal(false).build(); + srcIp).setMonitorEnabled(monitoringEnabled).setMonitorInterval(100L). + setTunnelInterfaceType(tunType).setInternal(false).build(); builder.addAugmentation(IfTunnel.class, tunnel); LOG.trace("iftunnel {} built from hwvtep {} ",tunnel,node_id); return builder.build(); } - public static InternalTunnel buildInternalTunnel( BigInteger srcDpnId, BigInteger dstDpnId, String trunkInterfaceName) { - InternalTunnel tnl = new InternalTunnelBuilder().setKey(new InternalTunnelKey(dstDpnId,srcDpnId)).setDestinationDPN(dstDpnId) - .setSourceDPN(srcDpnId) + public static InternalTunnel buildInternalTunnel( BigInteger srcDpnId, BigInteger dstDpnId, + Class tunType, + String trunkInterfaceName) { + InternalTunnel tnl = new InternalTunnelBuilder().setKey(new InternalTunnelKey(dstDpnId, srcDpnId, tunType)).setDestinationDPN(dstDpnId) + .setSourceDPN(srcDpnId).setTransportType(tunType) .setTunnelInterfaceName(trunkInterfaceName).build(); return tnl ; } - public static ExternalTunnel buildExternalTunnel(String srcNode, String dstNode, String trunkInterfaceName) { + public static ExternalTunnel buildExternalTunnel(String srcNode, String dstNode, + Class tunType, + String trunkInterfaceName) { ExternalTunnel extTnl = new ExternalTunnelBuilder().setKey( - new ExternalTunnelKey(dstNode, srcNode)).setSourceDevice(srcNode).setDestinationDevice(dstNode).setTunnelInterfaceName(trunkInterfaceName).build(); + new ExternalTunnelKey(dstNode, srcNode, tunType)) + .setSourceDevice(srcNode).setDestinationDevice(dstNode) + .setTunnelInterfaceName(trunkInterfaceName) + .setTransportType(tunType).build(); return extTnl ; } @@ -671,5 +715,259 @@ public class ItmUtils { return dpnIdList; } + public static InstanceIdentifier buildStateInterfaceId(String interfaceName) { + InstanceIdentifierBuilder idBuilder = + InstanceIdentifier.builder(InterfacesState.class) + .child(org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.interfaces.rev140508.interfaces.state.Interface.class, + new org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.interfaces.rev140508.interfaces.state.InterfaceKey( + interfaceName)); + InstanceIdentifier id = idBuilder.build(); + return id; +} + public static Boolean readMonitoringStateFromDS(DataBroker dataBroker) { + InstanceIdentifier iid = InstanceIdentifier.create(TunnelMonitorEnabled.class); + Optional tunnelMonitorEnabledOptional = ItmUtils.read(LogicalDatastoreType.CONFIGURATION, + iid, dataBroker); + if(tunnelMonitorEnabledOptional.isPresent()) + return tunnelMonitorEnabledOptional.get().isEnabled(); + return null; + } + + public static Integer readMonitorIntervalfromDS(DataBroker dataBroker) { + InstanceIdentifier iid = InstanceIdentifier.create(TunnelMonitorInterval.class); + Optional tunnelMonitorIOptional = ItmUtils.read(LogicalDatastoreType.CONFIGURATION, iid, dataBroker); + if(tunnelMonitorIOptional.isPresent()) + return tunnelMonitorIOptional.get().getInterval(); + return null; + } + public static List getTunnelsofTzone(List hwVteps, String tzone, DataBroker dataBroker, Boolean hwVtepsExist) { + List tunnels = new ArrayList(); + InstanceIdentifier path = InstanceIdentifier.builder(TransportZones.class). + child(TransportZone.class, new TransportZoneKey(tzone)).build(); + Optional tZoneOptional = ItmUtils.read(LogicalDatastoreType.CONFIGURATION, path, dataBroker); + Class tunType = tZoneOptional.get().getTunnelType(); + if (tZoneOptional.isPresent()) { + if (tZoneOptional.get().getSubnets() != null && !tZoneOptional.get().getSubnets().isEmpty()) { + for (Subnets sub : tZoneOptional.get().getSubnets()) { + if (sub.getVteps() != null && !sub.getVteps().isEmpty()) { + for (Vteps vtepLocal : sub.getVteps()) { + for (Vteps vtepRemote : sub.getVteps()) { + if (!vtepLocal.equals(vtepRemote)) { + InternalTunnelKey key = new InternalTunnelKey(vtepRemote.getDpnId(), vtepLocal.getDpnId(), tunType); + InstanceIdentifier intIID = + InstanceIdentifier.builder(TunnelList.class). + child(InternalTunnel.class, key).build(); + Optional TunnelsOptional = + ItmUtils.read(LogicalDatastoreType.CONFIGURATION, intIID, dataBroker); + if (TunnelsOptional.isPresent()) { + LOG.trace("Internal Tunnel added {}",TunnelsOptional.get().getTunnelInterfaceName()); + tunnels.add(TunnelsOptional.get().getTunnelInterfaceName()); + } + } + } + if(hwVteps!= null && !hwVteps.isEmpty()) { + for (HwVtep hwVtep : hwVteps) { + tunnels.add(getExtTunnel(hwVtep.getNode_id(), vtepLocal.getDpnId().toString(), + tunType, dataBroker)); + tunnels.add(getExtTunnel(vtepLocal.getDpnId().toString(), hwVtep.getNode_id(), + tunType, dataBroker)); + } + } + } + } + } + } + } + if (hwVtepsExist) { + for (HwVtep hwVtep : hwVteps) { + for (HwVtep hwVtepOther : hwVteps) { + if (!hwVtep.getHwIp().equals(hwVtepOther.getHwIp())) { + tunnels.add(getExtTunnel(hwVtep.getNode_id(), hwVtepOther.getNode_id(), tunType, dataBroker)); + tunnels.add(getExtTunnel(hwVtepOther.getNode_id(), hwVtep.getNode_id(), tunType, dataBroker)); + } + } + } + } + return tunnels; + } + public static List getInternalTunnelsofTzone(String tzone, DataBroker dataBroker) { + List tunnels = new ArrayList(); + LOG.trace("Getting internal tunnels of {}",tzone); + InstanceIdentifier path = InstanceIdentifier.builder(TransportZones.class). + child(TransportZone.class, new TransportZoneKey(tzone)).build(); + Optional tZoneOptional = ItmUtils.read(LogicalDatastoreType.CONFIGURATION, path, dataBroker); + if (tZoneOptional.isPresent()) { + if (tZoneOptional.get().getSubnets() != null && !tZoneOptional.get().getSubnets().isEmpty()) { + for (Subnets sub : tZoneOptional.get().getSubnets()) { + if (sub.getVteps() != null && !sub.getVteps().isEmpty()) { + for (Vteps vtepLocal : sub.getVteps()) { + for (Vteps vtepRemote : sub.getVteps()) { + if (!vtepLocal.equals(vtepRemote)) { + InternalTunnelKey key = new InternalTunnelKey(vtepRemote.getDpnId(), vtepLocal.getDpnId(), tZoneOptional.get().getTunnelType()); + InstanceIdentifier intIID = + InstanceIdentifier.builder(TunnelList.class). + child(InternalTunnel.class, key).build(); + Optional TunnelsOptional = + ItmUtils.read(LogicalDatastoreType.CONFIGURATION, intIID, dataBroker); + if (TunnelsOptional.isPresent()) { + LOG.trace("Internal Tunnel added {}", + TunnelsOptional.get().getTunnelInterfaceName()); + tunnels.add(TunnelsOptional.get().getTunnelInterfaceName()); + } + } + } + } + } + } + } + } + return tunnels; + } + private static String getExtTunnel(String node_id, String dpId,Class tunType, DataBroker dataBroker) { + LOG.trace("getting ext tunnel for {} and dpId {}",node_id,dpId); + ExternalTunnelKey key = getExternalTunnelKey(dpId,node_id, tunType); + InstanceIdentifier intIID = InstanceIdentifier.builder(ExternalTunnelList.class). + child(ExternalTunnel.class, key).build(); + Optional TunnelsOptional = + ItmUtils.read(LogicalDatastoreType.CONFIGURATION, intIID, dataBroker); + if (TunnelsOptional.isPresent()) { + LOG.trace("ext tunnel returned {} ",TunnelsOptional.get().getTunnelInterfaceName()); + return TunnelsOptional.get().getTunnelInterfaceName(); + } + return null; + } + public static ExternalTunnelKey getExternalTunnelKey(String dst , String src, Class tunType) { + if (src.indexOf("physicalswitch") > 0) { + src = src.substring(0, src.indexOf("physicalswitch") - 1); + } + if (dst.indexOf("physicalswitch") > 0) { + dst = dst.substring(0, dst.indexOf("physicalswitch") - 1); + } + return new ExternalTunnelKey(dst, src, tunType); + } + public static List getTEPsForDpn( BigInteger srcDpn, List dpnList) { + for (DPNTEPsInfo dpn : dpnList) { + if( dpn.getDPNID().equals(srcDpn)) { + return dpn.getTunnelEndPoints() ; + } + } + return null ; + } + public static TunnelList getAllInternalTunnels(DataBroker broker) { + InstanceIdentifier tunnelListInstanceIdentifier = InstanceIdentifier.builder(TunnelList.class).build(); + Optional tunnelList = read(LogicalDatastoreType.CONFIGURATION, tunnelListInstanceIdentifier, broker); + if (tunnelList.isPresent()) { + return tunnelList.get(); + } + return null; + } + public static InternalTunnel getInternalTunnel(String interfaceName, DataBroker broker) { + InternalTunnel internalTunnel = null; + TunnelList tunnelList = getAllInternalTunnels(broker); + if (tunnelList != null && tunnelList.getInternalTunnel() != null) { + List internalTunnels = tunnelList.getInternalTunnel(); + for (InternalTunnel tunnel : internalTunnels) { + if (tunnel.getTunnelInterfaceName().equalsIgnoreCase(interfaceName)) { + internalTunnel = tunnel; + break; + } + } + } + return internalTunnel; + } + public static ExternalTunnel getExternalTunnel(String interfaceName, DataBroker broker) { + ExternalTunnel externalTunnel = null; + List externalTunnels = getAllExternalTunnels(broker); + for (ExternalTunnel tunnel : externalTunnels) { + if (StringUtils.equalsIgnoreCase(interfaceName, tunnel.getTunnelInterfaceName())) { + externalTunnel = tunnel; + break; + } + } + return externalTunnel; + } + public static List getAllExternalTunnels(DataBroker broker) { + List result = null; + InstanceIdentifier id = InstanceIdentifier.builder(ExternalTunnelList.class).build(); + Optional tunnelList = read(LogicalDatastoreType.CONFIGURATION, id, broker); + if (tunnelList.isPresent()) { + result = tunnelList.get().getExternalTunnel(); + } + if (result == null) { + result = Collections.emptyList(); + } + return result; + } + public static String convertTunnelTypetoString(Class tunType ) { + String tunnelType = ITMConstants.TUNNEL_TYPE_VXLAN; + if( tunType.equals(TunnelTypeVxlan.class)) + tunnelType = ITMConstants.TUNNEL_TYPE_VXLAN ; + else if( tunType.equals(TunnelTypeGre.class) ) + tunnelType = ITMConstants.TUNNEL_TYPE_GRE ; + else if (tunnelType.equals(TunnelTypeMplsOverGre.class)) + tunnelType = ITMConstants.TUNNEL_TYPE_MPLS_OVER_GRE; + return tunnelType ; + } + public static boolean isItmIfType(Class ifType) { + if( (ifType != null) && (ifType.isAssignableFrom(Tunnel.class)) ) { + return true; + } + return false; + } + public static StateTunnelListKey getTunnelStateKey( org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.interfaces.rev140508.interfaces.state.Interface iface) { + StateTunnelListKey key = null; + if(isItmIfType(iface.getType())) { + key = new StateTunnelListKey(iface.getName()); + } + return key; + } + public static void updateTunnelsCache(DataBroker broker) { + List internalTunnels = getAllInternalTunnels(broker, LogicalDatastoreType.CONFIGURATION); + for (InternalTunnel tunnel : internalTunnels) { + itmCache.addInternalTunnel(tunnel); + } + List externalTunnels = getAllExternalTunnels(broker, LogicalDatastoreType.CONFIGURATION); + for (ExternalTunnel tunnel : externalTunnels) { + itmCache.addExternalTunnel(tunnel); + } + } + public static List getAllExternalTunnels(DataBroker dataBroker, LogicalDatastoreType datastoreType) { + List result = null; + InstanceIdentifier iid = InstanceIdentifier.builder(ExternalTunnelList.class).build(); + Optional tunnelList = read(LogicalDatastoreType.CONFIGURATION, iid, dataBroker); + if (tunnelList.isPresent()) { + result = tunnelList.get().getExternalTunnel(); + } + if (result == null) { + result = Collections.emptyList(); + } + return result; + } + public static List getAllInternalTunnels(DataBroker dataBroker, LogicalDatastoreType datastoreType) { + List result = null; + InstanceIdentifier iid = InstanceIdentifier.builder(TunnelList.class).build(); + Optional tunnelList = read(LogicalDatastoreType.CONFIGURATION, iid, dataBroker); + if (tunnelList.isPresent()) { + result = tunnelList.get().getInternalTunnel(); + } + if (result == null) { + result = Collections.emptyList(); + } + return result; + } + public static Interface getInterface( + String name, DataBroker broker) { + Interface result = itmCache.getInterface(name); + if (result == null) { + InstanceIdentifier iid = + InstanceIdentifier.builder(Interfaces.class) + .child(Interface.class, new InterfaceKey(name)).build(); + Optional optInterface = read(LogicalDatastoreType.CONFIGURATION, iid, broker); + if (optInterface.isPresent()) { + result = optInterface.get(); + itmCache.addInterface(result); + } + } + return result; + } } - diff --git a/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/listeners/InterfaceStateListener.java b/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/listeners/InterfaceStateListener.java new file mode 100644 index 00000000..49c9bda8 --- /dev/null +++ b/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/listeners/InterfaceStateListener.java @@ -0,0 +1,210 @@ +/* + * Copyright (c) 2016 Ericsson India Global Services Pvt Ltd. and others. All rights reserved. + * + * This program and the accompanying materials are made available under the + * terms of the Eclipse Public License v1.0 which accompanies this distribution, + * and is available at http://www.eclipse.org/legal/epl-v10.html + */ + +package org.opendaylight.vpnservice.itm.listeners; + +import org.opendaylight.controller.md.sal.binding.api.DataBroker; +import org.opendaylight.controller.md.sal.binding.api.DataChangeListener; +import org.opendaylight.controller.md.sal.common.api.data.AsyncDataBroker.DataChangeScope; +import org.opendaylight.controller.md.sal.common.api.data.LogicalDatastoreType; +import org.opendaylight.vpnservice.itm.impl.ItmUtils; +import org.opendaylight.vpnservice.mdsalutil.AbstractDataChangeListener; +import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.interfaces.rev140508.InterfacesState; +import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.interfaces.rev140508.interfaces.state.Interface; +import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.interfaces.rev140508.interfaces.state.Interface.OperStatus; +import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.interfacemgr.rev150331.IfTunnel; +import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.interfacemgr.rev150331.ParentRefs; +import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.op.rev150701.TepTypeBase; +import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.op.rev150701.TepTypeExternal; +import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.op.rev150701.TepTypeHwvtep; +import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.op.rev150701.TepTypeInternal; +import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.op.rev150701.TunnelsState; +import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.op.rev150701.external.tunnel.list.ExternalTunnel; +import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.op.rev150701.tunnel.list.InternalTunnel; +import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.op.rev150701.tunnels_state.StateTunnelList; +import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.op.rev150701.tunnels_state.StateTunnelListBuilder; +import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.op.rev150701.tunnels_state.StateTunnelListKey; +import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.op.rev150701.tunnels_state.state.tunnel.list.DstInfoBuilder; +import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.op.rev150701.tunnels_state.state.tunnel.list.SrcInfoBuilder; +import org.opendaylight.yangtools.concepts.ListenerRegistration; +import org.opendaylight.yangtools.yang.binding.InstanceIdentifier; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; + +import com.google.common.base.Optional; +import com.google.common.net.InetAddresses; + +public class InterfaceStateListener extends AbstractDataChangeListener implements AutoCloseable { + private static final Logger LOG = LoggerFactory.getLogger(InterfaceStateListener.class); + + private ListenerRegistration listenerRegistration; + private final DataBroker broker; + + public InterfaceStateListener(final DataBroker db) { + super(Interface.class); + broker = db; + registerListener(db); + } + + @Override + public void close() throws Exception { + if (listenerRegistration != null) { + try { + listenerRegistration.close(); + } catch (final Exception e) { + LOG.error("Error when cleaning up interface state listener", e); + } + listenerRegistration = null; + } + LOG.info("Interface state listener Closed"); + } + + private void registerListener(final DataBroker db) { + try { + listenerRegistration = db.registerDataChangeListener(LogicalDatastoreType.OPERATIONAL, + getWildCardPath(), InterfaceStateListener.this, DataChangeScope.SUBTREE); + } catch (final Exception e) { + LOG.error("ITM Interfaces State listener registration fail!", e); + throw new IllegalStateException("ITM Interfaces State listener registration failed.", e); + } + } + + private InstanceIdentifier getWildCardPath() { + return InstanceIdentifier.create(InterfacesState.class).child(Interface.class); + } + + @Override + protected void add(InstanceIdentifier identifier, Interface iface) { + LOG.trace("Interface added: {}", iface); + if(ItmUtils.isItmIfType(iface.getType())) { + LOG.debug("Interface of type Tunnel added: {}", iface.getName()); + updateItmState(iface); + } + } + + @Override + protected void remove(InstanceIdentifier identifier, + Interface iface) { + LOG.trace("Interface deleted: {}", iface); + if(ItmUtils.isItmIfType(iface.getType())) { + LOG.debug("Tunnel interface deleted: {}", iface.getName()); + StateTunnelListKey tlKey = null; + tlKey = ItmUtils.getTunnelStateKey(iface); + InstanceIdentifier stListId = buildStateTunnelListId(tlKey); + LOG.trace("Deleting tunnel_state for Id: {}", stListId); + ItmUtils.asyncDelete(LogicalDatastoreType.OPERATIONAL, stListId, broker, ItmUtils.DEFAULT_CALLBACK); + } + } + + @Override + protected void update(InstanceIdentifier identifier, + Interface original, Interface update) { + /* + * update contains only delta, may not include iftype + * Note: This assumes type can't be edited on the fly + */ + if(ItmUtils.isItmIfType(original.getType())) { + LOG.trace("Interface updated. Old: {} New: {}", original, update); + OperStatus operStatus = update.getOperStatus(); + if( operStatus != null ) { + LOG.debug("Tunnel Interface {} changed state to {}", original.getName(), operStatus); + updateItmState(update); + } + } + } + + private void updateItmState(Interface iface) { + StateTunnelListKey tlKey = null; + tlKey = ItmUtils.getTunnelStateKey(iface); + LOG.trace("TunnelStateKey: {} for interface: {}", tlKey, iface.getName()); + InstanceIdentifier stListId = buildStateTunnelListId(tlKey); + Optional tunnelsState = ItmUtils.read(LogicalDatastoreType.OPERATIONAL, stListId, broker); + StateTunnelList tunnelStateList; + StateTunnelListBuilder stlBuilder; + boolean tunnelState = (iface.getOperStatus().equals(OperStatus.Up)) ? (true):(false); + if(tunnelsState.isPresent()) { + tunnelStateList = tunnelsState.get(); + stlBuilder = new StateTunnelListBuilder(tunnelStateList); + stlBuilder.setTunnelState(tunnelState); + StateTunnelList stList = stlBuilder.build(); + LOG.trace("Updating tunnel_state: {} for Id: {}",stList, stListId); + ItmUtils.asyncUpdate(LogicalDatastoreType.OPERATIONAL, stListId, stList, broker, ItmUtils.DEFAULT_CALLBACK); + } else { + // Create new Tunnel State + try { + /*FIXME: + * A defensive try-catch to find issues without disrupting existing behavior. + */ + tunnelStateList = buildStateTunnelList(tlKey, iface.getName(), tunnelState); + LOG.trace("Creating tunnel_state: {} for Id: {}", tunnelStateList, stListId); + ItmUtils.asyncUpdate(LogicalDatastoreType.OPERATIONAL, stListId, tunnelStateList, broker, + ItmUtils.DEFAULT_CALLBACK); + } catch (Exception e) { + LOG.warn("Exception trying to create tunnel state for {}", iface.getName(), e); + } + } + } + + private StateTunnelList buildStateTunnelList(StateTunnelListKey tlKey, String name, boolean state) { + StateTunnelListBuilder stlBuilder = new StateTunnelListBuilder(); + org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.interfaces.rev140508.interfaces.Interface iface = + ItmUtils.getInterface(name, broker); + IfTunnel ifTunnel = iface.getAugmentation(IfTunnel.class); + ParentRefs parentRefs = iface.getAugmentation(ParentRefs.class); + if(ifTunnel == null && parentRefs == null) { + return null; + } + DstInfoBuilder dstInfoBuilder = new DstInfoBuilder(); + SrcInfoBuilder srcInfoBuilder = new SrcInfoBuilder(); + dstInfoBuilder.setTepIp(ifTunnel.getTunnelDestination()); + srcInfoBuilder.setTepIp(ifTunnel.getTunnelSource()); + //TODO: Add/Improve logic for device type + InternalTunnel internalTunnel = ItmUtils.itmCache.getInternalTunnel(name); + ExternalTunnel externalTunnel = ItmUtils.itmCache.getExternalTunnel(name); + if(internalTunnel == null && externalTunnel == null) { + // both not present in cache. let us update and try again. + ItmUtils.updateTunnelsCache(broker); + internalTunnel = ItmUtils.itmCache.getInternalTunnel(name); + externalTunnel = ItmUtils.itmCache.getExternalTunnel(name); + } + if(internalTunnel != null) { + srcInfoBuilder.setTepDeviceId(internalTunnel.getSourceDPN().toString()).setTepDeviceType(TepTypeInternal.class); + dstInfoBuilder.setTepDeviceId(internalTunnel.getDestinationDPN().toString()) + .setTepDeviceType(TepTypeInternal.class); + stlBuilder.setTransportType(internalTunnel.getTransportType()); + } else if(externalTunnel != null) { + ExternalTunnel tunnel = ItmUtils.itmCache.getExternalTunnel(name); + srcInfoBuilder.setTepDeviceId(tunnel.getSourceDevice()) + .setTepDeviceType(getDeviceType(tunnel.getSourceDevice())); + dstInfoBuilder.setTepDeviceId(tunnel.getDestinationDevice()) + .setTepDeviceType(getDeviceType(tunnel.getSourceDevice())) + .setTepIp(ifTunnel.getTunnelDestination()); + stlBuilder.setTransportType(tunnel.getTransportType()); + } + stlBuilder.setKey(tlKey).setTunnelInterfaceName(name).setTunnelState(state) + .setDstInfo(dstInfoBuilder.build()).setSrcInfo(srcInfoBuilder.build()); + return stlBuilder.build(); + } + + private Class getDeviceType(String device) { + if(device.startsWith("hwvtep")) { + return TepTypeHwvtep.class; + } else if(InetAddresses.isInetAddress(device)) { + return TepTypeExternal.class; + } else { + return TepTypeInternal.class; + } + } + + private InstanceIdentifier buildStateTunnelListId(StateTunnelListKey tlKey) { + InstanceIdentifier stListId = + InstanceIdentifier.builder(TunnelsState.class).child(StateTunnelList.class, tlKey).build(); + return stListId; + } + +} diff --git a/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/listeners/TransportZoneListener.java b/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/listeners/TransportZoneListener.java index fae12dc6..26c8f806 100644 --- a/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/listeners/TransportZoneListener.java +++ b/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/listeners/TransportZoneListener.java @@ -110,7 +110,7 @@ public class TransportZoneListener extends AsyncDataTreeChangeListenerBase0 || hwVtepList.size()>0) { LOG.trace("Delete: Invoking ItmManager"); - LOG.trace("Add: Invoking ItmManager with hwVtep List {} " , hwVtepList); + LOG.trace("Delete: Invoking ItmManager with hwVtep List {} " , hwVtepList); // itmManager.deleteTunnels(opDpnList); DataStoreJobCoordinator coordinator = DataStoreJobCoordinator.getInstance(); ItmTepRemoveWorker removeWorker = new ItmTepRemoveWorker(opDpnList,hwVtepList, dataBroker, idManagerService, mdsalManager); @@ -220,12 +220,15 @@ public class TransportZoneListener extends AsyncDataTreeChangeListenerBase vtepsList = subnet.getVteps(); + if(vtepsList!=null && !vtepsList.isEmpty()) { for (Vteps vteps : vtepsList) { BigInteger dpnID = vteps.getDpnId(); String port = vteps.getPortname(); IpAddress ipAddress = vteps.getIpAddress(); LOG.trace("DpnID: {}, port: {}, ipAddress: {}", dpnID, port, ipAddress); - TunnelEndPoints tunnelEndPoints = ItmUtils.createTunnelEndPoints(dpnID, ipAddress, port, vlanID, ipPrefix, gatewayIP, zone_name, tunnel_type); + TunnelEndPoints tunnelEndPoints = + ItmUtils.createTunnelEndPoints(dpnID, ipAddress, port, vlanID, ipPrefix, + gatewayIP, zone_name, tunnel_type); List tunnelEndPointsList = mapDPNToTunnelEndpt.get(dpnID); if (tunnelEndPointsList != null) { LOG.trace("Existing DPN info list in the Map: {} ", dpnID); @@ -235,6 +238,7 @@ public class TransportZoneListener extends AsyncDataTreeChangeListenerBase(); tunnelEndPointsList.add(tunnelEndPoints); mapDPNToTunnelEndpt.put(dpnID, tunnelEndPointsList); + } } } } diff --git a/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/listeners/TunnelMonitorChangeListener.java b/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/listeners/TunnelMonitorChangeListener.java new file mode 100644 index 00000000..15aa0399 --- /dev/null +++ b/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/listeners/TunnelMonitorChangeListener.java @@ -0,0 +1,206 @@ +/* + * Copyright (c) 2016 Ericsson India Global Services Pvt Ltd. and others. All rights reserved. + * + * This program and the accompanying materials are made available under the + * terms of the Eclipse Public License v1.0 which accompanies this distribution, + * and is available at http://www.eclipse.org/legal/epl-v10.html + */ +package org.opendaylight.vpnservice.itm.listeners; + +import com.google.common.base.Optional; +import org.opendaylight.controller.md.sal.binding.api.DataBroker; +import org.opendaylight.controller.md.sal.binding.api.DataChangeListener; +import org.opendaylight.controller.md.sal.binding.api.WriteTransaction; +import org.opendaylight.controller.md.sal.common.api.data.LogicalDatastoreType; +import org.opendaylight.controller.md.sal.common.api.data.AsyncDataBroker.DataChangeScope; +import org.opendaylight.vpnservice.datastoreutils.AsyncDataTreeChangeListenerBase; +import org.opendaylight.vpnservice.datastoreutils.DataStoreJobCoordinator; +import org.opendaylight.vpnservice.interfacemgr.interfaces.IInterfaceManager; +import org.opendaylight.vpnservice.itm.confighelpers.HwVtep; +import org.opendaylight.vpnservice.itm.confighelpers.ItmMonitorToggleWorker; +import org.opendaylight.vpnservice.itm.confighelpers.ItmTepAddWorker; +import org.opendaylight.vpnservice.itm.globals.ITMConstants; +import org.opendaylight.vpnservice.itm.impl.ItmUtils; +import org.opendaylight.vpnservice.mdsalutil.AbstractDataChangeListener; +import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.interfaces.rev140508.interfaces.Interface; +import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.interfaces.rev140508.interfaces.InterfaceBuilder; +import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.interfaces.rev140508.interfaces.InterfaceKey; +import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.interfacemgr.rev150331.IfTunnel; +import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.interfacemgr.rev150331.IfTunnelBuilder; +import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.config.rev151102.*; +import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.op.rev150701.ExternalTunnelList; +import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.op.rev150701.TunnelList; +import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.op.rev150701.external.tunnel.list.ExternalTunnel; +import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.op.rev150701.tunnel.list.InternalTunnel; +import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.rev150701.TransportZones; +import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.rev150701.transport.zones.TransportZone; +import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.rev150701.transport.zones.transport.zone.Subnets; +import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.rev150701.transport.zones.transport.zone.subnets.DeviceVteps; +import org.opendaylight.yangtools.concepts.ListenerRegistration; +import org.opendaylight.yangtools.yang.binding.InstanceIdentifier; +import org.opendaylight.yangtools.yang.data.api.YangInstanceIdentifier; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; + +import java.util.ArrayList; +import java.util.List; + +public class TunnelMonitorChangeListener extends AsyncDataTreeChangeListenerBase + implements AutoCloseable { + private static final Logger LOG = LoggerFactory.getLogger(TunnelMonitorChangeListener.class); + private final DataBroker broker; + // private final IInterfaceManager interfaceManager; + + public TunnelMonitorChangeListener(final DataBroker db) { + super(TunnelMonitorEnabled.class, TunnelMonitorChangeListener.class); + broker = db; + // interfaceManager = ifManager; + // registerListener(db); + } + + /* private void registerListener(final DataBroker db) { + try { + TunnelMonitorChangeListener monitorEnabledChangeListener = new TunnelMonitorChangeListener(); + monitorEnabledListenerRegistration = db.registerDataChangeListener(LogicalDatastoreType.CONFIGURATION, + monitorEnabledChangeListener.getWildCardPath(), monitorEnabledChangeListener, DataChangeScope.SUBTREE); + } catch (final Exception e) { + LOG.error("ITM Monitor Interfaces DataChange listener registration fail!", e); + throw new IllegalStateException("ITM Monitor registration Listener failed.", e); + } + } +*/ @Override + public void close() throws Exception { + /* if (monitorEnabledListenerRegistration != null) { + try { + monitorEnabledListenerRegistration.close(); + } catch (final Exception e) { + LOG.error("Error when cleaning up DataChangeListener.", e); + } + monitorEnabledListenerRegistration = null; + } + + if (monitorIntervalListenerRegistration != null) { + try { + monitorIntervalListenerRegistration.close(); + } catch (final Exception e) { + LOG.error("Error when cleaning up DataChangeListener.", e); + } + monitorIntervalListenerRegistration = null; + } +*/ + LOG.info("Tunnel Monitor listeners Closed"); + } + + @Override protected InstanceIdentifier getWildCardPath() { + return InstanceIdentifier.create(TunnelMonitorEnabled.class); + } + + @Override + protected void remove(InstanceIdentifier key, TunnelMonitorEnabled dataObjectModification) { + List hwVteps = new ArrayList(); + Boolean hwVtepsExist = false; + DataStoreJobCoordinator coordinator = DataStoreJobCoordinator.getInstance(); + InstanceIdentifier path = InstanceIdentifier.builder(TransportZones.class).build(); + Optional tZonesOptional = ItmUtils.read(LogicalDatastoreType.CONFIGURATION, path, broker); + if (tZonesOptional.isPresent()) { + TransportZones tZones = tZonesOptional.get(); + for (TransportZone tzone : tZones.getTransportZone()) { + hwVtepsExist = false; + hwVteps = new ArrayList(); + if (tzone.getSubnets() != null && !tzone.getSubnets().isEmpty()) { + for (Subnets sub : tzone.getSubnets()) { + if (sub.getDeviceVteps() != null && !sub.getDeviceVteps().isEmpty()) { + hwVtepsExist = true; + for (DeviceVteps deviceVtep : sub.getDeviceVteps()) { + HwVtep hwVtep = ItmUtils.createHwVtepObject(deviceVtep.getTopologyId(), deviceVtep.getNodeId(), + deviceVtep.getIpAddress(), sub.getPrefix(), sub.getGatewayIp(), sub.getVlanId(), + tzone.getTunnelType(), tzone); + hwVteps.add(hwVtep); + } + } + } + } + LOG.debug("Remove:Calling TunnelMonitorToggleWorker with tzone = {} and {}",tzone.getZoneName(),dataObjectModification.isEnabled()); + ItmMonitorToggleWorker toggleWorker = new ItmMonitorToggleWorker(hwVteps, tzone.getZoneName(), + false, broker, hwVtepsExist); + coordinator.enqueueJob(tzone.getZoneName(), toggleWorker); + } + } + } + + + @Override protected void update(InstanceIdentifier key, + TunnelMonitorEnabled dataObjectModificationBefore, + TunnelMonitorEnabled dataObjectModificationAfter) { + LOG.debug("update TunnelMonitorChangeListener called with {}",dataObjectModificationAfter.isEnabled()); + List hwVteps = new ArrayList(); + Boolean hwVtepsExist = false; + DataStoreJobCoordinator coordinator = DataStoreJobCoordinator.getInstance(); + InstanceIdentifier path = InstanceIdentifier.builder(TransportZones.class).build(); + Optional tZonesOptional = ItmUtils.read(LogicalDatastoreType.CONFIGURATION, path, broker); + if (tZonesOptional.isPresent()) { + TransportZones tZones = tZonesOptional.get(); + for (TransportZone tzone : tZones.getTransportZone()) { + hwVtepsExist = false; + hwVteps = new ArrayList(); + if (tzone.getSubnets() != null && !tzone.getSubnets().isEmpty()) { + for (Subnets sub : tzone.getSubnets()) { + if (sub.getDeviceVteps() != null && !sub.getDeviceVteps().isEmpty()) { + hwVtepsExist = true;//gets set to true only if this particular tzone has + LOG.debug("Update:Calling TunnelMonitorToggleWorker with tzone = {} and hwtepExist",tzone.getZoneName()); + for (DeviceVteps deviceVtep : sub.getDeviceVteps()) { + HwVtep hwVtep = ItmUtils.createHwVtepObject(deviceVtep.getTopologyId(), deviceVtep.getNodeId(), + deviceVtep.getIpAddress(), sub.getPrefix(), sub.getGatewayIp(), sub.getVlanId(), + tzone.getTunnelType(), tzone); + hwVteps.add(hwVtep); + } + } + } + } + LOG.debug("Update:Calling TunnelMonitorToggleWorker with tzone = {} and {}",tzone.getZoneName(),dataObjectModificationAfter.isEnabled()); + ItmMonitorToggleWorker toggleWorker = new ItmMonitorToggleWorker(hwVteps, tzone.getZoneName(), + dataObjectModificationAfter.isEnabled(), broker, hwVtepsExist); + coordinator.enqueueJob(tzone.getZoneName(), toggleWorker); + } + } + } + + @Override + protected void add(InstanceIdentifier key, TunnelMonitorEnabled dataObjectModification) { + LOG.debug("add TunnelMonitorChangeListener called with {}",dataObjectModification.isEnabled()); + List hwVteps = new ArrayList(); + Boolean hwVtepsExist = false; + DataStoreJobCoordinator coordinator = DataStoreJobCoordinator.getInstance(); + InstanceIdentifier path = InstanceIdentifier.builder(TransportZones.class).build(); + Optional tZonesOptional = ItmUtils.read(LogicalDatastoreType.CONFIGURATION, path, broker); + if (tZonesOptional.isPresent()) { + TransportZones tZones = tZonesOptional.get(); + for (TransportZone tzone : tZones.getTransportZone()) { + hwVtepsExist = false; + hwVteps = new ArrayList(); + if (tzone.getSubnets() != null && !tzone.getSubnets().isEmpty()) { + for (Subnets sub : tzone.getSubnets()) { + if (sub.getDeviceVteps() != null && !sub.getDeviceVteps().isEmpty()) { + hwVtepsExist = true; + for (DeviceVteps deviceVtep : sub.getDeviceVteps()) { + HwVtep hwVtep = ItmUtils.createHwVtepObject(deviceVtep.getTopologyId(), deviceVtep.getNodeId(), + deviceVtep.getIpAddress(), sub.getPrefix(), sub.getGatewayIp(), sub.getVlanId(), + tzone.getTunnelType(), tzone); + hwVteps.add(hwVtep); + } + } + } + } + LOG.debug("Add:Calling TunnelMonitorToggleWorker with tzone = {} and {}",tzone.getZoneName(),dataObjectModification.isEnabled()); + ItmMonitorToggleWorker toggleWorker = new ItmMonitorToggleWorker(hwVteps, tzone.getZoneName(), + dataObjectModification.isEnabled(), broker, hwVtepsExist); + coordinator.enqueueJob(tzone.getZoneName(), toggleWorker); + } + } + } + + @Override protected TunnelMonitorChangeListener getDataTreeChangeListener() { + return TunnelMonitorChangeListener.this; + } + +} diff --git a/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/listeners/TunnelMonitorIntervalListener.java b/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/listeners/TunnelMonitorIntervalListener.java new file mode 100644 index 00000000..42b0d70e --- /dev/null +++ b/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/listeners/TunnelMonitorIntervalListener.java @@ -0,0 +1,175 @@ +/* + * Copyright (c) 2016 Ericsson India Global Services Pvt Ltd. and others. All rights reserved. + * + * This program and the accompanying materials are made available under the + * terms of the Eclipse Public License v1.0 which accompanies this distribution, + * and is available at http://www.eclipse.org/legal/epl-v10.html + */ +package org.opendaylight.vpnservice.itm.listeners; + +import com.google.common.base.Optional; +import org.opendaylight.controller.md.sal.binding.api.DataBroker; +import org.opendaylight.controller.md.sal.binding.api.DataChangeListener; +import org.opendaylight.controller.md.sal.binding.api.WriteTransaction; +import org.opendaylight.controller.md.sal.common.api.data.AsyncDataBroker.DataChangeScope; +import org.opendaylight.controller.md.sal.common.api.data.LogicalDatastoreType; +import org.opendaylight.vpnservice.datastoreutils.AsyncDataTreeChangeListenerBase; +import org.opendaylight.vpnservice.datastoreutils.DataStoreJobCoordinator; +import org.opendaylight.vpnservice.interfacemgr.interfaces.IInterfaceManager; +import org.opendaylight.vpnservice.itm.confighelpers.HwVtep; +import org.opendaylight.vpnservice.itm.confighelpers.ItmMonitorIntervalWorker; +import org.opendaylight.vpnservice.itm.confighelpers.ItmMonitorToggleWorker; +import org.opendaylight.vpnservice.itm.confighelpers.ItmTepAddWorker; +import org.opendaylight.vpnservice.itm.globals.ITMConstants; +import org.opendaylight.vpnservice.itm.impl.ItmUtils; +import org.opendaylight.vpnservice.mdsalutil.AbstractDataChangeListener; +import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.interfaces.rev140508.interfaces.Interface; +import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.interfaces.rev140508.interfaces.InterfaceBuilder; +import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.interfaces.rev140508.interfaces.InterfaceKey; +import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.interfacemgr.rev150331.IfTunnel; +import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.interfacemgr.rev150331.IfTunnelBuilder; +import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.config.rev151102.TunnelMonitorEnabled; +import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.config.rev151102.TunnelMonitorInterval; +import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.op.rev150701.ExternalTunnelList; +import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.op.rev150701.TunnelList; +import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.op.rev150701.external.tunnel.list.ExternalTunnel; +import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.op.rev150701.tunnel.list.InternalTunnel; +import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.rev150701.TransportZones; +import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.rev150701.transport.zones.TransportZone; +import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.rev150701.transport.zones.transport.zone.Subnets; +import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.rev150701.transport.zones.transport.zone.subnets.DeviceVteps; +import org.opendaylight.yangtools.concepts.ListenerRegistration; +import org.opendaylight.yangtools.yang.binding.InstanceIdentifier; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; + +import java.util.ArrayList; +import java.util.List; + +public class TunnelMonitorIntervalListener extends AsyncDataTreeChangeListenerBase + implements AutoCloseable { + private static final Logger LOG = LoggerFactory.getLogger(TunnelMonitorIntervalListener.class); + private ListenerRegistration monitorIntervalListenerRegistration; + private final DataBroker broker; + + public TunnelMonitorIntervalListener(DataBroker db) { + super(TunnelMonitorInterval.class, TunnelMonitorIntervalListener.class); + broker = db; + } + + @Override protected InstanceIdentifier getWildCardPath() { + return InstanceIdentifier.create(TunnelMonitorInterval.class); + } + + @Override + protected void remove(InstanceIdentifier key, TunnelMonitorInterval dataObjectModification) { + LOG.debug("remove TunnelMonitorIntervalListener called with {}",dataObjectModification.getInterval()); + List hwVteps = new ArrayList(); + Boolean hwVtepsExist = false; + DataStoreJobCoordinator coordinator = DataStoreJobCoordinator.getInstance(); + InstanceIdentifier path = InstanceIdentifier.builder(TransportZones.class).build(); + Optional tZonesOptional = ItmUtils.read(LogicalDatastoreType.CONFIGURATION, path, broker); + if (tZonesOptional.isPresent()) { + TransportZones tZones = tZonesOptional.get(); + for (TransportZone tzone : tZones.getTransportZone()) { + /* hwVtepsExist = false; + hwVteps = new ArrayList(); + if (tzone.getSubnets() != null && !tzone.getSubnets().isEmpty()) { + for (Subnets sub : tzone.getSubnets()) { + if (sub.getDeviceVteps() != null && !sub.getDeviceVteps().isEmpty()) { + hwVtepsExist = true; + LOG.debug("Remove:Calling TunnelMonitorIntervalWorker with tzone = {} and hwtepExist",tzone.getZoneName()); + for (DeviceVteps deviceVtep : sub.getDeviceVteps()) { + HwVtep hwVtep = ItmUtils.createHwVtepObject(deviceVtep.getTopologyId(), deviceVtep.getNodeId(), + deviceVtep.getIpAddress(), sub.getPrefix(), sub.getGatewayIp(), sub.getVlanId(), + tzone.getTunnelType(), tzone); + hwVteps.add(hwVtep); + } + } + } + }*/ + //if you remove configuration, the last configured interval is only set i.e no change + LOG.debug("Remove:Calling TunnelMonitorIntervalWorker with tzone = {} and {}",tzone.getZoneName(),dataObjectModification.getInterval()); + ItmMonitorIntervalWorker toggleWorker = new ItmMonitorIntervalWorker(hwVteps, tzone.getZoneName(), + dataObjectModification.getInterval(), broker, hwVtepsExist); + coordinator.enqueueJob(tzone.getZoneName(), toggleWorker); + } + } + } + + @Override protected void update(InstanceIdentifier key, + TunnelMonitorInterval dataObjectModificationBefore, + TunnelMonitorInterval dataObjectModificationAfter) { + LOG.debug("update TunnelMonitorIntervalListener called with {}",dataObjectModificationAfter.getInterval()); + List hwVteps = new ArrayList(); + Boolean hwVtepsExist = false; + DataStoreJobCoordinator coordinator = DataStoreJobCoordinator.getInstance(); + InstanceIdentifier path = InstanceIdentifier.builder(TransportZones.class).build(); + Optional tZonesOptional = ItmUtils.read(LogicalDatastoreType.CONFIGURATION, path, broker); + if (tZonesOptional.isPresent()) { + TransportZones tZones = tZonesOptional.get(); + for (TransportZone tzone : tZones.getTransportZone()) { + /*hwVtepsExist = false; + hwVteps = new ArrayList(); + if (tzone.getSubnets() != null && !tzone.getSubnets().isEmpty()) { + for (Subnets sub : tzone.getSubnets()) { + if (sub.getDeviceVteps() != null && !sub.getDeviceVteps().isEmpty()) { + hwVtepsExist = true;//gets set to true only if this particular tzone has + LOG.debug("Update:Calling TunnelMonitorIntervalWorker with tzone = {} and hwtepExist",tzone.getZoneName()); + for (DeviceVteps deviceVtep : sub.getDeviceVteps()) { + HwVtep hwVtep = ItmUtils.createHwVtepObject(deviceVtep.getTopologyId(), deviceVtep.getNodeId(), + deviceVtep.getIpAddress(), sub.getPrefix(), sub.getGatewayIp(), sub.getVlanId(), + tzone.getTunnelType(), tzone); + hwVteps.add(hwVtep); + } + } + } + }*/ + LOG.debug("Update:Calling TunnelMonitorIntervalWorker with tzone = {} and {}",tzone.getZoneName(),dataObjectModificationAfter.getInterval()); + ItmMonitorIntervalWorker intervalWorker = new ItmMonitorIntervalWorker(hwVteps, tzone.getZoneName(), + dataObjectModificationAfter.getInterval(), broker, hwVtepsExist); + coordinator.enqueueJob(tzone.getZoneName(), intervalWorker); + } + } + } + + @Override + protected void add(InstanceIdentifier key, TunnelMonitorInterval dataObjectModification) { + LOG.debug("Add TunnelMonitorIntervalListener called with {}",dataObjectModification.getInterval()); + List hwVteps = new ArrayList(); + Boolean hwVtepsExist = false; + DataStoreJobCoordinator coordinator = DataStoreJobCoordinator.getInstance(); + InstanceIdentifier path = InstanceIdentifier.builder(TransportZones.class).build(); + Optional tZonesOptional = ItmUtils.read(LogicalDatastoreType.CONFIGURATION, path, broker); + if (tZonesOptional.isPresent()) { + TransportZones tZones = tZonesOptional.get(); + for (TransportZone tzone : tZones.getTransportZone()) { + /*hwVtepsExist = false; + hwVteps = new ArrayList(); + if (tzone.getSubnets() != null && !tzone.getSubnets().isEmpty()) { + for (Subnets sub : tzone.getSubnets()) { + if (sub.getDeviceVteps() != null && !sub.getDeviceVteps().isEmpty()) { + hwVtepsExist = true; + LOG.debug("Add:Calling TunnelMonitorIntervalWorker with tzone = {} and hwtepExist",tzone.getZoneName()); + for (DeviceVteps deviceVtep : sub.getDeviceVteps()) { + HwVtep hwVtep = ItmUtils.createHwVtepObject(deviceVtep.getTopologyId(), deviceVtep.getNodeId(), + deviceVtep.getIpAddress(), sub.getPrefix(), sub.getGatewayIp(), sub.getVlanId(), + tzone.getTunnelType(), tzone); + hwVteps.add(hwVtep); + } + } + } + }*/ + LOG.debug("Add:Calling TunnelMonitorIntervalWorker with tzone = {} and {}",tzone.getZoneName(),dataObjectModification.getInterval()); + ItmMonitorIntervalWorker intervalWorker = new ItmMonitorIntervalWorker(hwVteps, tzone.getZoneName(), + dataObjectModification.getInterval(), broker, hwVtepsExist); + //conversion to milliseconds done while writing to i/f-mgr config DS + coordinator.enqueueJob(tzone.getZoneName(), intervalWorker); + } + } + } + + @Override protected TunnelMonitorIntervalListener getDataTreeChangeListener() { + return TunnelMonitorIntervalListener.this; + } +} diff --git a/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/listeners/VtepConfigSchemaListener.java b/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/listeners/VtepConfigSchemaListener.java index 9b8b138c..cc9af90a 100644 --- a/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/listeners/VtepConfigSchemaListener.java +++ b/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/listeners/VtepConfigSchemaListener.java @@ -5,7 +5,6 @@ * terms of the Eclipse Public License v1.0 which accompanies this distribution, * and is available at http://www.eclipse.org/legal/epl-v10.html */ - package org.opendaylight.vpnservice.itm.listeners; import java.math.BigInteger; diff --git a/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/monitoring/DataPathAlarm.java b/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/monitoring/DataPathAlarm.java new file mode 100644 index 00000000..99fbd9a9 --- /dev/null +++ b/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/monitoring/DataPathAlarm.java @@ -0,0 +1,66 @@ +/* + * Copyright (c) 2016 Ericsson India Global Services Pvt Ltd. and others. All rights reserved. + * + * This program and the accompanying materials are made available under the + * terms of the Eclipse Public License v1.0 which accompanies this distribution, + * and is available at http://www.eclipse.org/legal/epl-v10.html + */ +package org.opendaylight.vpnservice.itm.monitoring; + +import javax.management.AttributeChangeNotification; +import javax.management.Notification; +import javax.management.NotificationBroadcasterSupport; +import java.util.ArrayList; + +/** + * Created by emnqrrw on 10/27/2015. + */ +public class DataPathAlarm extends NotificationBroadcasterSupport implements DataPathAlarmMBean { + + ArrayList raiseAlarmObject = new ArrayList(); + ArrayList clearAlarmObject = new ArrayList(); + private long sequenceNumber = 1; + + public void setRaiseAlarmObject(ArrayList raiseAlarmObject) { + this.raiseAlarmObject = raiseAlarmObject; + + Notification n = new AttributeChangeNotification(this, + sequenceNumber++, System.currentTimeMillis(), + "raise alarm object notified ", "raiseAlarmObject", "ArrayList", + "", this.raiseAlarmObject); + sendNotification(n); + } + + public ArrayList getRaiseAlarmObject() { + return raiseAlarmObject; + } + + public void setClearAlarmObject(ArrayList clearAlarmObject) { + this.clearAlarmObject = clearAlarmObject; + + Notification n = new AttributeChangeNotification(this, + sequenceNumber++, System.currentTimeMillis(), + "clear alarm object notified ", "clearAlarmObject", "ArrayList", + "", this.clearAlarmObject); + sendNotification(n); + } + + public ArrayList getClearAlarmObject() { + return clearAlarmObject; + } + + public synchronized void raiseAlarm(String alarmName, String additionalText, String source){ + raiseAlarmObject.add(alarmName); + raiseAlarmObject.add(additionalText); + raiseAlarmObject.add(source); + setRaiseAlarmObject(raiseAlarmObject); + raiseAlarmObject.clear(); + } + public synchronized void clearAlarm(String alarmName, String additionalText, String source){ + clearAlarmObject.add(alarmName); + clearAlarmObject.add(additionalText); + clearAlarmObject.add(source); + setClearAlarmObject(clearAlarmObject); + clearAlarmObject.clear(); + } +} diff --git a/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/monitoring/DataPathAlarmMBean.java b/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/monitoring/DataPathAlarmMBean.java new file mode 100644 index 00000000..8c3f21ad --- /dev/null +++ b/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/monitoring/DataPathAlarmMBean.java @@ -0,0 +1,22 @@ +/* + * Copyright (c) 2016 Ericsson India Global Services Pvt Ltd. and others. All rights reserved. + * + * This program and the accompanying materials are made available under the + * terms of the Eclipse Public License v1.0 which accompanies this distribution, + * and is available at http://www.eclipse.org/legal/epl-v10.html + */ +package org.opendaylight.vpnservice.itm.monitoring; + +import java.util.ArrayList; + +/** + * Created by emnqrrw on 10/27/2015. + */ +public interface DataPathAlarmMBean { + public void setRaiseAlarmObject(ArrayList raiseAlarmObject); + public ArrayList getRaiseAlarmObject(); + public void setClearAlarmObject(ArrayList clearAlarmObject); + public ArrayList getClearAlarmObject(); + public void raiseAlarm(String alarmName, String additionalText, String source); + public void clearAlarm(String alarmName, String additionalText, String source); +} diff --git a/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/monitoring/ItmTunnelEventListener.java b/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/monitoring/ItmTunnelEventListener.java new file mode 100644 index 00000000..7ff0f0dd --- /dev/null +++ b/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/monitoring/ItmTunnelEventListener.java @@ -0,0 +1,217 @@ +/* + * Copyright (c) 2016 Ericsson India Global Services Pvt Ltd. and others. All rights reserved. + * + * This program and the accompanying materials are made available under the + * terms of the Eclipse Public License v1.0 which accompanies this distribution, + * and is available at http://www.eclipse.org/legal/epl-v10.html + */ +package org.opendaylight.vpnservice.itm.monitoring; + +import org.opendaylight.controller.md.sal.binding.api.DataBroker; +import org.opendaylight.controller.md.sal.binding.api.DataChangeListener; +import org.opendaylight.controller.md.sal.common.api.data.AsyncDataBroker; +import org.opendaylight.controller.md.sal.common.api.data.LogicalDatastoreType; +import org.opendaylight.vpnservice.itm.impl.ItmUtils; +import org.opendaylight.vpnservice.mdsalutil.AbstractDataChangeListener; +import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.interfaces.rev140508.InterfacesState; +import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.interfaces.rev140508.interfaces.state.Interface; +import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.iana._if.type.rev140508.Tunnel; +import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.op.rev150701.TunnelList; +import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.op.rev150701.external.tunnel.list.ExternalTunnel; +import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.op.rev150701.tunnel.list.InternalTunnel; +import org.opendaylight.yangtools.concepts.ListenerRegistration; +import org.opendaylight.yangtools.yang.binding.InstanceIdentifier; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; + +import java.math.BigInteger; + +/** + * Created by emnqrrw on 11/2/2015. + */ +public class ItmTunnelEventListener extends AbstractDataChangeListener implements AutoCloseable { + + private static final Logger logger = LoggerFactory.getLogger(ItmTunnelEventListener.class); + private final DataBroker broker; + private ListenerRegistration listenerRegistration; + public static final JMXAlarmAgent alarmAgent = new JMXAlarmAgent(); + + public ItmTunnelEventListener(final DataBroker db){ + super(Interface.class); + broker = db; + registerListener(db); + alarmAgent.registerMbean(); + } + + private void registerListener(final DataBroker db) { + try { + listenerRegistration = broker.registerDataChangeListener(LogicalDatastoreType.OPERATIONAL, + getWildCardPath(), ItmTunnelEventListener.this, AsyncDataBroker.DataChangeScope.SUBTREE); + } catch (final Exception e) { + logger.error("ITM Monitor Interfaces DataChange listener registration fail!", e); + throw new IllegalStateException("ITM Monitor registration Listener failed.", e); + } + } + + private InstanceIdentifier getWildCardPath() { + return InstanceIdentifier.create(InterfacesState.class).child(Interface.class); + } + + @Override + protected void remove(InstanceIdentifier identifier, Interface del) { + String ifName = del.getName() ; + if( del.getType() != null && del.getType().equals(Tunnel.class)) { + InternalTunnel internalTunnel = ItmUtils.getInternalTunnel(ifName,broker); + if( internalTunnel != null) { + BigInteger srcDpId = internalTunnel.getSourceDPN(); + BigInteger dstDpId = internalTunnel.getDestinationDPN(); + String tunnelType = ItmUtils.convertTunnelTypetoString(internalTunnel.getTransportType()); + logger.trace("ITM Tunnel removed b/w srcDpn: {} and dstDpn: {} for tunnelType: {}", srcDpId, dstDpId, tunnelType); + clearInternalDataPathAlarm(srcDpId.toString(),dstDpId.toString(),tunnelType); + }else { + ExternalTunnel externalTunnel = ItmUtils.getExternalTunnel(ifName,broker); + if( externalTunnel != null) { + String srcNode = externalTunnel.getSourceDevice(); + String dstNode = externalTunnel.getDestinationDevice(); + String tunnelType = ItmUtils.convertTunnelTypetoString(externalTunnel.getTransportType()); + logger.trace("ITM Tunnel removed b/w srcNode: {} and dstNode: {} for tunnelType: {}", srcNode, dstNode, tunnelType); + clearExternalDataPathAlarm(srcNode,dstNode,tunnelType); + } + } + } + } + + @Override + protected void update(InstanceIdentifier identifier, Interface original, Interface update) { + String ifName = update.getName() ; + if( update.getType() != null && update.getType().equals(Tunnel.class)) { + InternalTunnel internalTunnel = ItmUtils.getInternalTunnel(ifName,broker); + if( internalTunnel != null) { + BigInteger srcDpId = internalTunnel.getSourceDPN(); + BigInteger dstDpId = internalTunnel.getDestinationDPN(); + String tunnelType = ItmUtils.convertTunnelTypetoString(internalTunnel.getTransportType()); + logger.trace("ITM Tunnel state event changed from :{} to :{} for Tunnel Interface - {}", isTunnelInterfaceUp(original), isTunnelInterfaceUp(update), ifName); + if(isTunnelInterfaceUp(update)) { + logger.trace("ITM Tunnel State is UP b/w srcDpn: {} and dstDpn: {} for tunnelType {} ", srcDpId, dstDpId, tunnelType); + clearInternalDataPathAlarm(srcDpId.toString(),dstDpId.toString(),tunnelType); + }else { + logger.trace("ITM Tunnel State is DOWN b/w srcDpn: {} and dstDpn: {}", srcDpId, dstDpId); + StringBuilder alarmText = new StringBuilder(); + alarmText.append("Data Path Connectivity is lost between ").append("openflow:").append(srcDpId).append(" and openflow:") + .append(dstDpId).append(" for tunnelType:").append(tunnelType); + raiseInternalDataPathAlarm(srcDpId.toString(), dstDpId.toString(), tunnelType,alarmText.toString()); + } + }else{ + ExternalTunnel externalTunnel = ItmUtils.getExternalTunnel(ifName,broker); + if( externalTunnel != null) { + String srcNode = externalTunnel.getSourceDevice(); + String dstNode = externalTunnel.getDestinationDevice(); + String tunnelType = ItmUtils.convertTunnelTypetoString(externalTunnel.getTransportType()); + logger.trace("ITM Tunnel state event changed from :{} to :{} for Tunnel Interface - {}", isTunnelInterfaceUp(original), isTunnelInterfaceUp(update), ifName); + if(isTunnelInterfaceUp(update)) { + logger.trace("ITM Tunnel State is UP b/w srcNode: {} and dstNode: {} for tunnelType: {}", srcNode, dstNode, tunnelType); + clearExternalDataPathAlarm(srcNode.toString(),dstNode.toString(),tunnelType); + }else { + logger.trace("ITM Tunnel State is DOWN b/w srcNode: {} and dstNode: {}", srcNode, dstNode); + StringBuilder alarmText = new StringBuilder(); + alarmText.append("Data Path Connectivity is lost between ").append(srcNode).append(dstNode).append(" for tunnelType:").append(tunnelType); + raiseExternalDataPathAlarm(srcNode, dstNode, tunnelType,alarmText.toString()); + } + } + } + } + } + + @Override + protected void add(InstanceIdentifier identifier, Interface add) { + String ifName = add.getName() ; + if( add.getType() != null && add.getType().equals(Tunnel.class)) { + InternalTunnel internalTunnel = ItmUtils.getInternalTunnel(ifName,broker); + if( internalTunnel != null) { + BigInteger srcDpId = internalTunnel.getSourceDPN(); + BigInteger dstDpId = internalTunnel.getDestinationDPN(); + String tunnelType = ItmUtils.convertTunnelTypetoString(internalTunnel.getTransportType()); + if(!isTunnelInterfaceUp(add)) { + logger.trace("ITM Tunnel State during tep add is DOWN b/w srcDpn: {} and dstDpn: {} for tunnelType: {}", srcDpId, dstDpId, tunnelType); + StringBuilder alarmText = new StringBuilder(); + alarmText.append("Data Path Connection is down between ").append("openflow:").append(srcDpId).append(" and openflow:") + .append(dstDpId).append(" for tunnelType:").append(tunnelType).append(" during initial state"); + raiseInternalDataPathAlarm(srcDpId.toString(), dstDpId.toString(), tunnelType, alarmText.toString()); + } + }else { + ExternalTunnel externalTunnel = ItmUtils.getExternalTunnel(ifName,broker); + if( externalTunnel != null) { + String srcNode = externalTunnel.getSourceDevice(); + String dstNode = externalTunnel.getDestinationDevice(); + String tunnelType = ItmUtils.convertTunnelTypetoString(externalTunnel.getTransportType()); + if(!isTunnelInterfaceUp(add)) { + logger.trace("ITM Tunnel State during tep add is DOWN b/w srcNode: {} and dstNode: {} for tunnelType: {}", srcNode, dstNode, tunnelType); + StringBuilder alarmText = new StringBuilder(); + alarmText.append("Data Path Connection is down between ").append(srcNode).append(dstNode).append(" for tunnelType:").append(tunnelType).append(" during initial state"); + raiseExternalDataPathAlarm(srcNode, dstNode, tunnelType,alarmText.toString()); + } + } + } + } + } + + @Override + public void close() throws Exception { + if (listenerRegistration != null) { + try { + listenerRegistration.close(); + } catch (final Exception e) { + logger.error("Error when cleaning up DataChangeListener.", e); + } + listenerRegistration = null; + } + } + + public void raiseInternalDataPathAlarm(String srcDpnId,String dstDpnId,String tunnelType,String alarmText) { + + StringBuilder source = new StringBuilder(); + source.append("srcDpn=openflow:").append(srcDpnId).append("-dstDpn=openflow:").append(dstDpnId).append("-tunnelType").append(tunnelType); + + logger.trace("Raising DataPathConnectionFailure alarm... alarmText {} source {} ", alarmText, source); + //Invokes JMX raiseAlarm method + alarmAgent.invokeFMraisemethod("DataPathConnectionFailure", alarmText, source.toString()); + } + + public void clearInternalDataPathAlarm(String srcDpnId,String dstDpnId,String tunnelType) { + StringBuilder source = new StringBuilder(); + + source.append("srcDpn=openflow:").append(srcDpnId).append("-dstDpn=openflow:").append(dstDpnId).append("-tunnelType").append(tunnelType); + logger.trace("Clearing DataPathConnectionFailure alarm of source {} ", source); + //Invokes JMX clearAlarm method + alarmAgent.invokeFMclearmethod("DataPathConnectionFailure", "Clearing ITM Tunnel down alarm", source.toString()); + } + + public void raiseExternalDataPathAlarm(String srcDevice,String dstDevice,String tunnelType, String alarmText) { + + StringBuilder source = new StringBuilder(); + source.append("srcDevice=").append(srcDevice).append("-dstDevice=").append(dstDevice).append("-tunnelType").append(tunnelType); + + logger.trace("Raising DataPathConnectionFailure alarm... alarmText {} source {} ", alarmText, source); + //Invokes JMX raiseAlarm method + alarmAgent.invokeFMraisemethod("DataPathConnectionFailure", alarmText, source.toString()); + } + + + public void clearExternalDataPathAlarm(String srcDevice,String dstDevice,String tunnelType) { + + StringBuilder source = new StringBuilder(); + + source.append("srcDevice=").append(srcDevice).append("-dstDevice=").append(dstDevice).append("-tunnelType").append(tunnelType); + + //logger.trace("Clearing DataPathConnectionFailure alarm of source {} ", source); + //Invokes JMX clearAlarm method + alarmAgent.invokeFMclearmethod("DataPathConnectionFailure", "Clearing ITM Tunnel down alarm", source.toString()); + + } + + private boolean isTunnelInterfaceUp( Interface intf) { + boolean interfaceUp = (intf.getOperStatus().equals(Interface.OperStatus.Up)) ? true :false ; + return interfaceUp ; + } + +} diff --git a/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/monitoring/JMXAlarmAgent.java b/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/monitoring/JMXAlarmAgent.java new file mode 100644 index 00000000..ec35d241 --- /dev/null +++ b/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/monitoring/JMXAlarmAgent.java @@ -0,0 +1,75 @@ +/* + * Copyright (c) 2016 Ericsson India Global Services Pvt Ltd. and others. All rights reserved. + * + * This program and the accompanying materials are made available under the + * terms of the Eclipse Public License v1.0 which accompanies this distribution, + * and is available at http://www.eclipse.org/legal/epl-v10.html + */ +package org.opendaylight.vpnservice.itm.monitoring; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; + +import javax.management.*; +import java.lang.management.ManagementFactory; +/** + * Created by emnqrrw on 11/2/2015. + */ +public class JMXAlarmAgent { + static Logger s_logger = LoggerFactory.getLogger(JMXAlarmAgent.class); + private MBeanServer mbs = null; + private ObjectName alarmName = null; + private static final String BEANNAME = "SDNC.FM:name=DataPathAlarmBean"; + private static DataPathAlarm alarmBean= new DataPathAlarm(); + + public JMXAlarmAgent() { + // Get the platform MBeanServer + mbs = ManagementFactory.getPlatformMBeanServer(); + try { + alarmName = new ObjectName(BEANNAME); + } catch (MalformedObjectNameException e) { + s_logger.error("ObjectName instance creation failed for BEANAME {} : {}",BEANNAME, e); + } + } + + public void registerMbean() { + // Unique identification of MBeans + try { + // Uniquely identify the MBeans and register them with the platform MBeanServer + if(!mbs.isRegistered(alarmName)) { + mbs.registerMBean(alarmBean, alarmName); + s_logger.debug("Registered Mbean {} successfully", alarmName); + } + } catch(Exception e) { + s_logger.error("Registeration failed for Mbean {} :{}", alarmName,e); + } + } + + public void unregisterMbean() { + try { + if(mbs.isRegistered(alarmName)) { + mbs.unregisterMBean(alarmName); + s_logger.debug("Unregistered Mbean {} successfully", alarmName); + } + } catch (Exception e) { + s_logger.error("UnRegisteration failed for Mbean {} :{}", alarmName,e); + } + } + + public void invokeFMraisemethod(String alarmId,String text,String src) { + try { + mbs.invoke(alarmName, "raiseAlarm", new Object[]{alarmId, text, src}, new String[]{String.class.getName(), String.class.getName(), String.class.getName()}); + s_logger.trace("Invoked raiseAlarm function for Mbean {} with source {}", BEANNAME, src); + } catch (Exception e) { + s_logger.error("Invoking raiseAlarm method failed for Mbean {} :{}", alarmName,e); + } + } + + public void invokeFMclearmethod(String alarmId,String text,String src) { + try { + mbs.invoke(alarmName, "clearAlarm", new Object[]{alarmId, text, src}, new String[]{String.class.getName(), String.class.getName(), String.class.getName()}); + s_logger.trace("Invoked clearAlarm function for Mbean {} with source {}",BEANNAME,src); + } catch (Exception e) { + s_logger.error("Invoking clearAlarm method failed for Mbean {} :{}", alarmName,e); + } + } +} diff --git a/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/rpc/ItmManagerRpcService.java b/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/rpc/ItmManagerRpcService.java index a373472b..26b007a9 100644 --- a/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/rpc/ItmManagerRpcService.java +++ b/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/rpc/ItmManagerRpcService.java @@ -1,5 +1,5 @@ /* - * Copyright (c) 2015, 2016 Ericsson India Global Services Pvt Ltd. and others. All rights reserved. + * Copyright (c) 2015 Ericsson India Global Services Pvt Ltd. and others. All rights reserved. * * This program and the accompanying materials are made available under the * terms of the Eclipse Public License v1.0 which accompanies this distribution, @@ -15,6 +15,7 @@ import java.util.concurrent.Future; import org.opendaylight.controller.md.sal.binding.api.WriteTransaction; import org.opendaylight.vpnservice.mdsalutil.*; import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.idmanager.rev150403.IdManagerService; +import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.interfacemgr.rev150331.TunnelTypeMplsOverGre; import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.rev150701.TransportZones; import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.rev150701.transport.zones.TransportZone; import org.opendaylight.yang.gen.v1.urn.opendaylight.vpnservice.itm.rev150701.transport.zones.TransportZoneKey; @@ -81,7 +82,7 @@ public class ItmManagerRpcService implements ItmRpcService { BigInteger destinationDpn = input.getDestinationDpid() ; InstanceIdentifier path = InstanceIdentifier.create( TunnelList.class) - .child(InternalTunnel.class, new InternalTunnelKey( destinationDpn,sourceDpn)); + .child(InternalTunnel.class, new InternalTunnelKey(destinationDpn, sourceDpn, input.getTunnelType())); Optional tnl = ItmUtils.read(LogicalDatastoreType.CONFIGURATION, path, dataBroker); @@ -170,7 +171,7 @@ public class ItmManagerRpcService implements ItmRpcService { String dstNode = input.getDestinationNode(); InstanceIdentifier path = InstanceIdentifier.create( ExternalTunnelList.class) - .child(ExternalTunnel.class, new ExternalTunnelKey(dstNode, sourceNode)); + .child(ExternalTunnel.class, new ExternalTunnelKey(dstNode, sourceNode, input.getTunnelType())); Optional ext = ItmUtils.read(LogicalDatastoreType.CONFIGURATION, path, dataBroker); @@ -193,7 +194,7 @@ public class ItmManagerRpcService implements ItmRpcService { LOG.info("create terminatingServiceAction on DpnId = {} for service id {} and instructions {}", input.getDpnId() , input.getServiceId(), input.getInstruction()); final SettableFuture> result = SettableFuture.create(); int serviceId = input.getServiceId() ; - List mkMatches = new ArrayList(); + List mkMatches = getTunnelMatchesForServiceId(serviceId); byte[] vxLANHeader = new byte[] {0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00}; // Flags Byte byte Flags = (byte) 0x08; @@ -205,9 +206,9 @@ public class ItmManagerRpcService implements ItmRpcService { vxLANHeader[6] = (byte) (serviceId >> 0); // Matching metadata - mkMatches.add(new MatchInfo(MatchFieldType.tunnel_id, new BigInteger[] { - new BigInteger(1, vxLANHeader), - MetaDataUtil.METADA_MASK_VALID_TUNNEL_ID_BIT_AND_TUNNEL_ID })); +// mkMatches.add(new MatchInfo(MatchFieldType.tunnel_id, new BigInteger[] { +// new BigInteger(1, vxLANHeader), +// MetaDataUtil.METADA_MASK_VALID_TUNNEL_ID_BIT_AND_TUNNEL_ID })); Flow terminatingServiceTableFlow = MDSALUtil.buildFlowNew(NwConstants.INTERNAL_TUNNEL_TABLE, getFlowRef(NwConstants.INTERNAL_TUNNEL_TABLE,serviceId), 5, String.format("%s:%d","ITM Flow Entry ",serviceId), @@ -294,7 +295,7 @@ public class ItmManagerRpcService implements ItmRpcService { IpAddress dstIp = input.getDestinationIp() ; InstanceIdentifier path1 = InstanceIdentifier.create( ExternalTunnelList.class) - .child(ExternalTunnel.class, new ExternalTunnelKey(String.valueOf(dstIp), srcDpn.toString())); + .child(ExternalTunnel.class, new ExternalTunnelKey(String.valueOf(dstIp), srcDpn.toString(), TunnelTypeMplsOverGre.class)); Optional ext = ItmUtils.read(LogicalDatastoreType.CONFIGURATION, path1, dataBroker); @@ -312,7 +313,7 @@ public class ItmManagerRpcService implements ItmRpcService { if (dstIp.equals(firstEndPt.getIpAddress())) { InstanceIdentifier path = InstanceIdentifier.create( TunnelList.class) - .child(InternalTunnel.class, new InternalTunnelKey(teps.getDPNID(),srcDpn)); + .child(InternalTunnel.class, new InternalTunnelKey(teps.getDPNID(), srcDpn, input.getTunnelType())); Optional tnl = @@ -436,6 +437,10 @@ public class ItmManagerRpcService implements ItmRpcService { } }); } + else { + result.set(RpcResultBuilder.failed().withError(RpcError.ErrorType.APPLICATION, "No TransportZones configured").build()); + return result; + } return result; } catch (Exception e) { RpcResultBuilder resultBuilder = RpcResultBuilder.failed(). @@ -444,4 +449,123 @@ public class ItmManagerRpcService implements ItmRpcService { } } + @Override + public Future> addL2GwMlagDevice(AddL2GwMlagDeviceInput input) + { + final SettableFuture> result = SettableFuture.create(); + try { + final IpAddress hwIp = input.getIpAddress(); + final List node_id = input.getNodeId(); + InstanceIdentifier containerPath = InstanceIdentifier.create(TransportZones.class); + Optional tZonesOptional = ItmUtils.read(LogicalDatastoreType.CONFIGURATION, containerPath, dataBroker); + if (tZonesOptional.isPresent()) { + TransportZones tZones = tZonesOptional.get(); + if (tZones.getTransportZone() == null || tZones.getTransportZone().isEmpty()) { + LOG.error("No teps configured"); + result.set(RpcResultBuilder.failed().withError(RpcError.ErrorType.APPLICATION, "No teps Configured").build()); + return result; + } + String transportZone = tZones.getTransportZone().get(0).getZoneName(); + if (tZones.getTransportZone().get(0).getSubnets() == null || tZones.getTransportZone().get(0).getSubnets().isEmpty()) { + result.set(RpcResultBuilder.failed().withError(RpcError.ErrorType.APPLICATION, "No subnets Configured").build()); + return result; + } + SubnetsKey subnetsKey = tZones.getTransportZone().get(0).getSubnets().get(0).getKey(); + DeviceVtepsKey deviceVtepKey = new DeviceVtepsKey(hwIp, node_id.get(0)); + InstanceIdentifier path = + InstanceIdentifier.builder(TransportZones.class) + .child(TransportZone.class, new TransportZoneKey(transportZone)) + .child(Subnets.class, subnetsKey).child(DeviceVteps.class, deviceVtepKey).build(); + DeviceVteps deviceVtep = new DeviceVtepsBuilder().setKey(deviceVtepKey).setIpAddress(hwIp).setNodeId(node_id.get(0)).setTopologyId(input.getTopologyId()).build(); + WriteTransaction t = dataBroker.newWriteOnlyTransaction(); + LOG.trace("writing hWvtep{}",deviceVtep); + t.put(LogicalDatastoreType.CONFIGURATION, path, deviceVtep, true); + if(node_id.size() == 2) { + LOG.trace("second node-id {}",node_id.get(1)); + DeviceVtepsKey deviceVtepKey2 = new DeviceVtepsKey(hwIp, node_id.get(1)); + InstanceIdentifier path2 = InstanceIdentifier.builder(TransportZones.class) + .child(TransportZone.class, new TransportZoneKey(transportZone)) + .child(Subnets.class, subnetsKey).child(DeviceVteps.class, deviceVtepKey2).build(); + DeviceVteps deviceVtep2 = new DeviceVtepsBuilder().setKey(deviceVtepKey2).setIpAddress(hwIp).setNodeId(node_id.get(1)) + .setTopologyId(input.getTopologyId()).build(); + LOG.trace("writing {}",deviceVtep2); + t.put(LogicalDatastoreType.CONFIGURATION, path2, deviceVtep2, true); + }ListenableFuture futureCheck = t.submit(); + Futures.addCallback(futureCheck, new FutureCallback() { + @Override + public void onSuccess(Void aVoid) { + result.set(RpcResultBuilder.success().build()); + } + @Override + public void onFailure(Throwable error) { + String msg = String.format("Unable to write HwVtep {} to datastore", node_id); + LOG.error("Unable to write HwVtep {}, {} to datastore", node_id , hwIp); + result.set(RpcResultBuilder.failed().withError(RpcError.ErrorType.APPLICATION, msg, error).build()); + } + }); + } + return result; + } catch (Exception e) { + RpcResultBuilder resultBuilder = RpcResultBuilder.failed(). + withError(RpcError.ErrorType.APPLICATION, "Adding l2 Gateway to DS Failed", e); + return Futures.immediateFuture(resultBuilder.build()); + } + } + @Override + public Future> deleteL2GwMlagDevice(DeleteL2GwMlagDeviceInput input) { + final SettableFuture> result = SettableFuture.create(); + try { + final IpAddress hwIp = input.getIpAddress(); + final List node_id = input.getNodeId(); + InstanceIdentifier containerPath = InstanceIdentifier.create(TransportZones.class); + Optional tZonesOptional = ItmUtils.read(LogicalDatastoreType.CONFIGURATION, containerPath, dataBroker); + if (tZonesOptional.isPresent()) { + TransportZones tZones = tZonesOptional.get(); + if (tZones.getTransportZone() == null || tZones.getTransportZone().isEmpty()) { + LOG.error("No teps configured"); + result.set(RpcResultBuilder.failed().withError(RpcError.ErrorType.APPLICATION, "No teps Configured").build()); + return result; + } + String transportZone = tZones.getTransportZone().get(0).getZoneName(); + if (tZones.getTransportZone().get(0).getSubnets() == null || tZones.getTransportZone().get(0).getSubnets().isEmpty()) { + result.set(RpcResultBuilder.failed().withError(RpcError.ErrorType.APPLICATION, "No subnets Configured").build()); + return result; + } + SubnetsKey subnetsKey = tZones.getTransportZone().get(0).getSubnets().get(0).getKey(); + DeviceVtepsKey deviceVtepKey = new DeviceVtepsKey(hwIp, node_id.get(0)); + InstanceIdentifier path = + InstanceIdentifier.builder(TransportZones.class) + .child(TransportZone.class, new TransportZoneKey(transportZone)) + .child(Subnets.class, subnetsKey).child(DeviceVteps.class, + deviceVtepKey).build(); + WriteTransaction t = dataBroker.newWriteOnlyTransaction(); + t.delete(LogicalDatastoreType.CONFIGURATION, path); + DeviceVtepsKey deviceVtepKey2 = new DeviceVtepsKey(hwIp, node_id.get(1)); + InstanceIdentifier path2 = + InstanceIdentifier.builder(TransportZones.class) + .child(TransportZone.class, new TransportZoneKey(transportZone)) + .child(Subnets.class, subnetsKey).child(DeviceVteps.class, + deviceVtepKey2).build(); + t.delete(LogicalDatastoreType.CONFIGURATION, path2); + ListenableFuture futureCheck = t.submit(); + Futures.addCallback(futureCheck, new FutureCallback() { + @Override + public void onSuccess(Void aVoid) { + result.set(RpcResultBuilder.success().build()); + } + @Override + public void onFailure(Throwable error) { + String msg = String.format("Unable to write HwVtep {} to datastore", node_id); + LOG.error("Unable to write HwVtep {}, {} to datastore", node_id , hwIp); + result.set(RpcResultBuilder.failed().withError(RpcError.ErrorType.APPLICATION, msg, error).build()); + } + }); + } + return result; + } catch (Exception e) { + RpcResultBuilder resultBuilder = RpcResultBuilder.failed(). + withError(RpcError.ErrorType.APPLICATION, "Deleting l2 Gateway to DS Failed", e); + return Futures.immediateFuture(resultBuilder.build()); + } + } } diff --git a/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/snd/ITMStatusMonitor.java b/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/snd/ITMStatusMonitor.java index 03a4b87e..82138f42 100644 --- a/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/snd/ITMStatusMonitor.java +++ b/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/snd/ITMStatusMonitor.java @@ -1,5 +1,5 @@ /* - * Copyright (c) 2016 Ericsson India Global Services Pvt Ltd. and others. All rights reserved. + * Copyright (c) 2015 Ericsson India Global Services Pvt Ltd. and others. All rights reserved. * * This program and the accompanying materials are made available under the * terms of the Eclipse Public License v1.0 which accompanies this distribution, diff --git a/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/snd/ITMStatusMonitorMBean.java b/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/snd/ITMStatusMonitorMBean.java index e1557af1..0f82d2e2 100644 --- a/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/snd/ITMStatusMonitorMBean.java +++ b/itm/itm-impl/src/main/java/org/opendaylight/vpnservice/itm/snd/ITMStatusMonitorMBean.java @@ -1,5 +1,5 @@ /* - * Copyright (c) 2016 Ericsson India Global Services Pvt Ltd. and others. All rights reserved. + * Copyright (c) 2015 Ericsson India Global Services Pvt Ltd. and others. All rights reserved. * * This program and the accompanying materials are made available under the * terms of the Eclipse Public License v1.0 which accompanies this distribution, diff --git a/itm/itm-impl/src/main/java/org/opendaylight/yang/gen/v1/urn/opendaylight/vpnservice/itm/impl/rev141210/ItmModule.java b/itm/itm-impl/src/main/java/org/opendaylight/yang/gen/v1/urn/opendaylight/vpnservice/itm/impl/rev141210/ItmModule.java index 9ec91f52..58ec4627 100644 --- a/itm/itm-impl/src/main/java/org/opendaylight/yang/gen/v1/urn/opendaylight/vpnservice/itm/impl/rev141210/ItmModule.java +++ b/itm/itm-impl/src/main/java/org/opendaylight/yang/gen/v1/urn/opendaylight/vpnservice/itm/impl/rev141210/ItmModule.java @@ -17,7 +17,7 @@ public class ItmModule extends org.opendaylight.yang.gen.v1.urn.opendaylight.vpn @Override public java.lang.AutoCloseable createInstance() { - ItmProvider provider = new ItmProvider(); + ItmProvider provider = new ItmProvider(); provider.setMdsalApiManager(getMdsalutilDependency()); provider.setNotificationPublishService(getNotificationPublishServiceDependency()); provider.setNotificationService(getNotificationServiceDependency()); diff --git a/itm/itm-impl/src/main/resources/OSGI-INF/blueprint/commands.xml b/itm/itm-impl/src/main/resources/OSGI-INF/blueprint/commands.xml new file mode 100644 index 00000000..3da73376 --- /dev/null +++ b/itm/itm-impl/src/main/resources/OSGI-INF/blueprint/commands.xml @@ -0,0 +1,70 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + \ No newline at end of file