X-Git-Url: https://git.opendaylight.org/gerrit/gitweb?a=blobdiff_plain;f=vpnservice%2Felanmanager%2Felanmanager-impl%2Fsrc%2Fmain%2Fjava%2Forg%2Fopendaylight%2Fnetvirt%2Felan%2Finternal%2FElanServiceProvider.java;h=0c1e70be9dccdd9f5df859b88d18d1c822c5c461;hb=a5680413291099aa2eb41af1b5e2c81c9eaa1484;hp=0e8c6248bc7c53760acb380755350c83e3f4823a;hpb=1e6786d860b01c65a849935383b0dd5a6020a05c;p=netvirt.git diff --git a/vpnservice/elanmanager/elanmanager-impl/src/main/java/org/opendaylight/netvirt/elan/internal/ElanServiceProvider.java b/vpnservice/elanmanager/elanmanager-impl/src/main/java/org/opendaylight/netvirt/elan/internal/ElanServiceProvider.java index 0e8c6248bc..0c1e70be9d 100644 --- a/vpnservice/elanmanager/elanmanager-impl/src/main/java/org/opendaylight/netvirt/elan/internal/ElanServiceProvider.java +++ b/vpnservice/elanmanager/elanmanager-impl/src/main/java/org/opendaylight/netvirt/elan/internal/ElanServiceProvider.java @@ -9,6 +9,7 @@ package org.opendaylight.netvirt.elan.internal; import com.google.common.base.Optional; + import java.math.BigInteger; import java.util.ArrayList; import java.util.Collection; @@ -20,11 +21,17 @@ import java.util.Set; import java.util.concurrent.Future; import java.util.function.BiFunction; import org.opendaylight.controller.md.sal.binding.api.DataBroker; +import org.opendaylight.controller.md.sal.common.api.clustering.CandidateAlreadyRegisteredException; +import org.opendaylight.controller.md.sal.common.api.clustering.EntityOwnershipService; import org.opendaylight.controller.md.sal.common.api.data.LogicalDatastoreType; import org.opendaylight.genius.interfacemanager.exceptions.InterfaceAlreadyExistsException; import org.opendaylight.genius.interfacemanager.globals.IfmConstants; import org.opendaylight.genius.interfacemanager.interfaces.IInterfaceManager; import org.opendaylight.genius.mdsalutil.MDSALUtil; +import org.opendaylight.genius.mdsalutil.NwConstants; +import org.opendaylight.genius.utils.ServiceIndex; +import org.opendaylight.genius.utils.clustering.EntityOwnerUtils; +import org.opendaylight.genius.utils.hwvtep.HwvtepSouthboundConstants; import org.opendaylight.netvirt.elan.statusanddiag.ElanStatusMonitor; import org.opendaylight.netvirt.elan.utils.ElanConstants; import org.opendaylight.netvirt.elan.utils.ElanUtils; @@ -46,7 +53,6 @@ import org.opendaylight.yang.gen.v1.urn.opendaylight.netvirt.elan.etree.rev16061 import org.opendaylight.yang.gen.v1.urn.opendaylight.netvirt.elan.rev150602.ElanInstances; import org.opendaylight.yang.gen.v1.urn.opendaylight.netvirt.elan.rev150602.ElanInterfaces; import org.opendaylight.yang.gen.v1.urn.opendaylight.netvirt.elan.rev150602.elan._interface.forwarding.entries.ElanInterfaceMac; -import org.opendaylight.yang.gen.v1.urn.opendaylight.netvirt.elan.rev150602.elan.dpn.interfaces.elan.dpn.interfaces.list.DpnInterfaces; import org.opendaylight.yang.gen.v1.urn.opendaylight.netvirt.elan.rev150602.elan.instances.ElanInstance; import org.opendaylight.yang.gen.v1.urn.opendaylight.netvirt.elan.rev150602.elan.instances.ElanInstanceBuilder; import org.opendaylight.yang.gen.v1.urn.opendaylight.netvirt.elan.rev150602.elan.instances.ElanInstanceKey; @@ -61,9 +67,10 @@ import org.opendaylight.yangtools.yang.common.RpcResult; import org.slf4j.Logger; import org.slf4j.LoggerFactory; + public class ElanServiceProvider implements IElanService { - private static final Logger logger = LoggerFactory.getLogger(ElanServiceProvider.class); + private static final Logger LOG = LoggerFactory.getLogger(ElanServiceProvider.class); private final IdManagerService idManager; private final IInterfaceManager interfaceManager; @@ -71,15 +78,17 @@ public class ElanServiceProvider implements IElanService { private final ElanBridgeManager bridgeMgr; private final DataBroker broker; private final ElanStatusMonitor elanStatusMonitor; - private static ElanUtils elanUtils; + private final ElanUtils elanUtils; private boolean generateIntBridgeMac = true; + private boolean isL2BeforeL3; public ElanServiceProvider(IdManagerService idManager, IInterfaceManager interfaceManager, ElanInstanceManager elanInstanceManager, ElanBridgeManager bridgeMgr, DataBroker dataBroker, ElanInterfaceManager elanInterfaceManager, - ElanStatusMonitor elanStatusMonitor, ElanUtils elanUtils) { + ElanStatusMonitor elanStatusMonitor, ElanUtils elanUtils, + EntityOwnershipService entityOwnershipService) { this.idManager = idManager; this.interfaceManager = interfaceManager; this.elanInstanceManager = elanInstanceManager; @@ -87,37 +96,36 @@ public class ElanServiceProvider implements IElanService { this.broker = dataBroker; this.elanStatusMonitor = elanStatusMonitor; this.elanUtils = elanUtils; - elanInstanceManager.setElanUtils(elanUtils); elanInterfaceManager.setElanUtils(elanUtils); + try { + EntityOwnerUtils.registerEntityCandidateForOwnerShip(entityOwnershipService, + HwvtepSouthboundConstants.ELAN_ENTITY_TYPE, HwvtepSouthboundConstants.ELAN_ENTITY_TYPE, + null/*listener*/); + } catch (CandidateAlreadyRegisteredException e) { + LOG.error("failed to register the entity"); + } } - public static ElanUtils getElanutils() { - return ElanServiceProvider.elanUtils; - } - - public void init() { - logger.info("Starting ElnaServiceProvider"); + @SuppressWarnings("checkstyle:IllegalCatch") + public void init() throws Exception { + LOG.info("Starting ElnaServiceProvider"); elanStatusMonitor.reportStatus("STARTING"); + setIsL2BeforeL3(); try { createIdPool(); - elanStatusMonitor.reportStatus("OPERATIONAL"); } catch (Exception e) { - logger.error("Error initializing services", e); elanStatusMonitor.reportStatus("ERROR"); + throw e; } } - private void createIdPool() { + private void createIdPool() throws Exception { CreateIdPoolInput createPool = new CreateIdPoolInputBuilder().setPoolName(ElanConstants.ELAN_ID_POOL_NAME) .setLow(ElanConstants.ELAN_ID_LOW_VALUE).setHigh(ElanConstants.ELAN_ID_HIGH_VALUE).build(); - try { - Future> result = idManager.createIdPool(createPool); - if (result != null && result.get().isSuccessful()) { - logger.debug("ELAN Id Pool is created successfully"); - } - } catch (Exception e) { - logger.error("Failed to create ELAN Id pool {}", e); + Future> result = idManager.createIdPool(createPool); + if (result != null && result.get().isSuccessful()) { + LOG.debug("ELAN Id Pool is created successfully"); } } @@ -127,7 +135,7 @@ public class ElanServiceProvider implements IElanService { boolean isSuccess = true; if (existingElanInstance != null) { if (compareWithExistingElanInstance(existingElanInstance, macTimeout, description)) { - logger.debug("Elan Instance is already present in the Operational DS {}", existingElanInstance); + LOG.debug("Elan Instance is already present in the Operational DS {}", existingElanInstance); return true; } else { ElanInstance updateElanInstance = new ElanInstanceBuilder().setElanInstanceName(elanInstanceName) @@ -135,7 +143,7 @@ public class ElanServiceProvider implements IElanService { .setKey(new ElanInstanceKey(elanInstanceName)).build(); MDSALUtil.syncWrite(broker, LogicalDatastoreType.CONFIGURATION, ElanUtils.getElanInstanceConfigurationDataPath(elanInstanceName), updateElanInstance); - logger.debug("Updating the Elan Instance {} with MAC TIME-OUT %l and Description %s ", + LOG.debug("Updating the Elan Instance {} with MAC TIME-OUT %l and Description %s ", updateElanInstance, macTimeout, description); } } else { @@ -144,7 +152,7 @@ public class ElanServiceProvider implements IElanService { .build(); MDSALUtil.syncWrite(broker, LogicalDatastoreType.CONFIGURATION, ElanUtils.getElanInstanceConfigurationDataPath(elanInstanceName), elanInstance); - logger.debug("Creating the new Elan Instance {}", elanInstance); + LOG.debug("Creating the new Elan Instance {}", elanInstance); } return isSuccess; } @@ -155,7 +163,7 @@ public class ElanServiceProvider implements IElanService { boolean isSuccess = true; if (existingElanInstance != null) { if (compareWithExistingElanInstance(existingElanInstance, macTimeout, description)) { - logger.warn("Etree Instance is already present in the Operational DS {}", existingElanInstance); + LOG.warn("Etree Instance is already present in the Operational DS {}", existingElanInstance); return true; } else { EtreeInstance etreeInstance = new EtreeInstanceBuilder().build(); @@ -165,7 +173,7 @@ public class ElanServiceProvider implements IElanService { .addAugmentation(EtreeInstance.class, etreeInstance).build(); MDSALUtil.syncWrite(broker, LogicalDatastoreType.CONFIGURATION, ElanUtils.getElanInstanceConfigurationDataPath(elanInstanceName), updateElanInstance); - logger.debug("Updating the Etree Instance {} with MAC TIME-OUT %l and Description %s ", + LOG.debug("Updating the Etree Instance {} with MAC TIME-OUT %l and Description %s ", updateElanInstance, macTimeout, description); } } else { @@ -175,11 +183,16 @@ public class ElanServiceProvider implements IElanService { .addAugmentation(EtreeInstance.class, etreeInstance).build(); MDSALUtil.syncWrite(broker, LogicalDatastoreType.CONFIGURATION, ElanUtils.getElanInstanceConfigurationDataPath(elanInstanceName), elanInstance); - logger.debug("Creating the new Etree Instance {}", elanInstance); + LOG.debug("Creating the new Etree Instance {}", elanInstance); } return isSuccess; } + @Override + public EtreeInterface getEtreeInterfaceByElanInterfaceName(String elanInterface) { + return ElanUtils.getEtreeInterfaceByElanInterfaceName(broker, elanInterface); + } + public static boolean compareWithExistingElanInstance(ElanInstance existingElanInstance, long macTimeOut, String description) { boolean isEqual = false; @@ -205,10 +218,10 @@ public class ElanServiceProvider implements IElanService { boolean isSuccess = false; ElanInstance existingElanInstance = elanInstanceManager.getElanInstanceByName(elanInstanceName); if (existingElanInstance == null) { - logger.debug("Elan Instance is not present {}", existingElanInstance); + LOG.debug("Elan Instance is not present {}", existingElanInstance); return isSuccess; } - logger.debug("Deletion of the existing Elan Instance {}", existingElanInstance); + LOG.debug("Deletion of the existing Elan Instance {}", existingElanInstance); ElanUtils.delete(broker, LogicalDatastoreType.CONFIGURATION, ElanUtils.getElanInstanceConfigurationDataPath(elanInstanceName)); isSuccess = true; @@ -235,7 +248,7 @@ public class ElanServiceProvider implements IElanService { } MDSALUtil.syncWrite(broker, LogicalDatastoreType.CONFIGURATION, ElanUtils.getElanInterfaceConfigurationDataPathId(interfaceName), elanInterface); - logger.debug("Creating the new Etree Interface {}", elanInterface); + LOG.debug("Creating the new Etree Interface {}", elanInterface); } } @@ -257,14 +270,14 @@ public class ElanServiceProvider implements IElanService { } MDSALUtil.syncWrite(broker, LogicalDatastoreType.CONFIGURATION, ElanUtils.getElanInterfaceConfigurationDataPathId(interfaceName), elanInterface); - logger.debug("Creating the new ELan Interface {}", elanInterface); + LOG.debug("Creating the new ELan Interface {}", elanInterface); } } @Override public void updateElanInterface(String elanInstanceName, String interfaceName, List updatedStaticMacAddresses, String newDescription) { - ElanInterface existingElanInterface = elanUtils.getElanInterfaceByElanInterfaceName(interfaceName); + ElanInterface existingElanInterface = ElanUtils.getElanInterfaceByElanInterfaceName(broker, interfaceName); if (existingElanInterface == null) { return; } @@ -272,7 +285,7 @@ public class ElanServiceProvider implements IElanService { List updatedMacAddresses = getPhysAddress(updatedStaticMacAddresses); List updatedPhysAddress = getUpdatedPhyAddress(existingMacAddress, updatedMacAddresses); if (updatedPhysAddress.size() > 0) { - logger.debug("updating the ElanInterface with new Mac Entries {}", updatedStaticMacAddresses); + LOG.debug("updating the ElanInterface with new Mac Entries {}", updatedStaticMacAddresses); ElanInterface elanInterface = new ElanInterfaceBuilder().setElanInstanceName(elanInstanceName) .setName(interfaceName).setDescription(newDescription).setStaticMacEntries(updatedPhysAddress) .setKey(new ElanInterfaceKey(interfaceName)).build(); @@ -284,22 +297,22 @@ public class ElanServiceProvider implements IElanService { @Override public void deleteEtreeInterface(String elanInstanceName, String interfaceName) { deleteElanInterface(elanInstanceName, interfaceName); - logger.debug("deleting the Etree Interface {}", interfaceName); + LOG.debug("deleting the Etree Interface {}", interfaceName); } @Override public void deleteElanInterface(String elanInstanceName, String interfaceName) { - ElanInterface existingElanInterface = elanUtils.getElanInterfaceByElanInterfaceName(interfaceName); + ElanInterface existingElanInterface = ElanUtils.getElanInterfaceByElanInterfaceName(broker, interfaceName); if (existingElanInterface != null) { ElanUtils.delete(broker, LogicalDatastoreType.CONFIGURATION, ElanUtils.getElanInterfaceConfigurationDataPathId(interfaceName)); - logger.debug("deleting the Elan Interface {}", existingElanInterface); + LOG.debug("deleting the Elan Interface {}", existingElanInterface); } } @Override public void addStaticMacAddress(String elanInstanceName, String interfaceName, String macAddress) { - ElanInterface existingElanInterface = elanUtils.getElanInterfaceByElanInterfaceName(interfaceName); + ElanInterface existingElanInterface = ElanUtils.getElanInterfaceByElanInterfaceName(broker, interfaceName); PhysAddress updateStaticMacAddress = new PhysAddress(macAddress); if (existingElanInterface != null) { List existingMacAddress = existingElanInterface.getStaticMacEntries(); @@ -319,7 +332,7 @@ public class ElanServiceProvider implements IElanService { @Override public void deleteStaticMacAddress(String elanInstanceName, String interfaceName, String macAddress) throws MacNotFoundException { - ElanInterface existingElanInterface = elanUtils.getElanInterfaceByElanInterfaceName(interfaceName); + ElanInterface existingElanInterface = ElanUtils.getElanInterfaceByElanInterfaceName(broker, interfaceName); PhysAddress physAddress = new PhysAddress(macAddress); if (existingElanInterface == null) { return; @@ -340,7 +353,7 @@ public class ElanServiceProvider implements IElanService { @Override public Collection getElanMacTable(String elanInstanceName) { - Elan elanInfo = elanUtils.getElanByName(elanInstanceName); + Elan elanInfo = ElanUtils.getElanByName(broker, elanInstanceName); List macAddress = new ArrayList<>(); if (elanInfo == null) { return macAddress; @@ -360,7 +373,7 @@ public class ElanServiceProvider implements IElanService { @Override public void flushMACTable(String elanInstanceName) { - Elan elanInfo = elanUtils.getElanByName(elanInstanceName); + Elan elanInfo = ElanUtils.getElanByName(broker, elanInstanceName); if (elanInfo == null) { return; } @@ -376,8 +389,7 @@ public class ElanServiceProvider implements IElanService { try { deleteStaticMacAddress(elanInstanceName, elanInterface, macEntry.getMacAddress().getValue()); } catch (MacNotFoundException e) { - logger.error("Mac Not Found Exception {}", e); - e.printStackTrace(); + LOG.error("Mac Not Found Exception {}", e); } } } @@ -408,20 +420,15 @@ public class ElanServiceProvider implements IElanService { @Override public ElanInstance getElanInstance(String elanName) { - return elanUtils.getElanInstanceByName(elanName); + return ElanUtils.getElanInstanceByName(broker, elanName); } @Override public List getElanInstances() { - List elanList = new ArrayList<>(); InstanceIdentifier elanInstancesIdentifier = InstanceIdentifier.builder(ElanInstances.class) .build(); - Optional elansOptional = elanUtils.read(broker, LogicalDatastoreType.CONFIGURATION, - elanInstancesIdentifier); - if (elansOptional.isPresent()) { - elanList.addAll(elansOptional.get().getElanInstance()); - } - return elanList; + return elanUtils.read(broker, LogicalDatastoreType.CONFIGURATION, elanInstancesIdentifier).transform( + ElanInstances::getElanInstance).or(Collections.emptyList()); } @Override @@ -467,6 +474,16 @@ public class ElanServiceProvider implements IElanService { }); } + private void createExternalElanNetwork(ElanInstance elanInstance, String interfaceName) { + if (interfaceName == null) { + LOG.trace("No physical interface is attached to {}", elanInstance.getPhysicalNetworkName()); + return; + } + + String elanInterfaceName = createIetfInterfaces(elanInstance, interfaceName); + addElanInterface(elanInstance.getElanInstanceName(), elanInterfaceName, null, null); + } + @Override public void deleteExternalElanNetworks(Node node) { handleExternalElanNetworks(node, (elanInstance, interfaceName) -> { @@ -483,6 +500,21 @@ public class ElanServiceProvider implements IElanService { }); } + private void deleteExternalElanNetwork(ElanInstance elanInstance, String interfaceName) { + if (interfaceName == null) { + LOG.trace("No physial interface is attached to {}", elanInstance.getPhysicalNetworkName()); + return; + } + + String elanInstanceName = elanInstance.getElanInstanceName(); + for (String elanInterface : getExternalElanInterfaces(elanInstanceName)) { + if (elanInterface.startsWith(interfaceName)) { + deleteIetfInterface(elanInterface); + deleteElanInterface(elanInstanceName, elanInterface); + } + } + } + @Override public void updateExternalElanNetworks(Node origNode, Node updatedNode) { if (!bridgeMgr.isIntegrationBridge(updatedNode)) { @@ -491,86 +523,65 @@ public class ElanServiceProvider implements IElanService { List elanInstances = getElanInstances(); if (elanInstances == null || elanInstances.isEmpty()) { - logger.trace("No ELAN instances found"); + LOG.trace("No ELAN instances found"); return; } - Optional> origProviderMapOpt = bridgeMgr.getOpenvswitchOtherConfigMap(origNode, + LOG.debug("updateExternalElanNetworks, orig bridge {} . updated bridge {}", origNode, updatedNode); + + Map origProviderMappping = getMapFromOtherConfig(origNode, ElanBridgeManager.PROVIDER_MAPPINGS_KEY); - Optional> updatedProviderMapOpt = bridgeMgr.getOpenvswitchOtherConfigMap(updatedNode, + Map updatedProviderMappping = getMapFromOtherConfig(updatedNode, ElanBridgeManager.PROVIDER_MAPPINGS_KEY); - Map origProviderMappping = origProviderMapOpt.or(Collections.emptyMap()); - Map updatedProviderMappping = updatedProviderMapOpt.or(Collections.emptyMap()); + + boolean hasDatapathIdOnOrigNode = bridgeMgr.hasDatapathID(origNode); + boolean hasDatapathIdOnUpdatedNode = bridgeMgr.hasDatapathID(updatedNode); for (ElanInstance elanInstance : elanInstances) { String physicalNetworkName = elanInstance.getPhysicalNetworkName(); if (physicalNetworkName != null) { String origPortName = origProviderMappping.get(physicalNetworkName); String updatedPortName = updatedProviderMappping.get(physicalNetworkName); - if (origPortName != null && !origPortName.equals(updatedPortName)) { - deleteExternalElanNetwork(elanInstance, getExtInterfaceName(origNode, physicalNetworkName)); + if (hasPortNameRemoved(origPortName, updatedPortName)) { + deleteExternalElanNetwork(elanInstance, + bridgeMgr.getProviderInterfaceName(origNode, physicalNetworkName)); } - if (updatedPortName != null && !updatedPortName.equals(origPortName)) { - createExternalElanNetwork(elanInstance, getExtInterfaceName(updatedNode, updatedPortName)); + if (hasPortNameUpdated(origPortName, updatedPortName) + || hasDatapathIdAdded(hasDatapathIdOnOrigNode, hasDatapathIdOnUpdatedNode)) { + createExternalElanNetwork(elanInstance, + bridgeMgr.getProviderInterfaceName(updatedNode, physicalNetworkName)); } } } } - private void createExternalElanNetwork(ElanInstance elanInstance, String interfaceName) { - if (interfaceName == null) { - logger.trace("No physial interface is attached to {}", elanInstance.getPhysicalNetworkName()); - return; - } - - String elanInterfaceName = createIetfInterfaces(elanInstance, interfaceName); - addElanInterface(elanInstance.getElanInstanceName(), elanInterfaceName, null, null); + private boolean hasDatapathIdAdded(boolean hasDatapathIdOnOrigNode, boolean hasDatapathIdOnUpdatedNode) { + return !hasDatapathIdOnOrigNode && hasDatapathIdOnUpdatedNode; } - private void deleteExternalElanNetwork(ElanInstance elanInstance, String interfaceName) { - if (interfaceName == null) { - logger.trace("No physial interface is attached to {}", elanInstance.getPhysicalNetworkName()); - return; - } - - String elanInstanceName = elanInstance.getElanInstanceName(); - for (String elanInterface : getExternalElanInterfaces(elanInstanceName)) { - if (elanInterface.startsWith(interfaceName)) { - deleteIetfInterface(elanInterface); - deleteElanInterface(elanInstanceName, elanInterface); - } - } + private boolean hasPortNameUpdated(String origPortName, String updatedPortName) { + return updatedPortName != null && !updatedPortName.equals(origPortName); } - @Override - public String getExternalElanInterface(String elanInstanceName, BigInteger dpnId) { - DpnInterfaces dpnInterfaces = elanUtils.getElanInterfaceInfoByElanDpn(elanInstanceName, dpnId); - if (dpnInterfaces == null || dpnInterfaces.getInterfaces() == null) { - logger.trace("Elan {} does not have interfaces in DPN {}", elanInstanceName, dpnId); - return null; - } - - for (String dpnInterface : dpnInterfaces.getInterfaces()) { - if (elanUtils.isExternal(dpnInterface)) { - return dpnInterface; - } - } + private boolean hasPortNameRemoved(String origPortName, String updatedPortName) { + return origPortName != null && !origPortName.equals(updatedPortName); + } - logger.trace("Elan {} does not have any external interace attached to DPN {}", elanInstanceName, dpnId); - return null; + private Map getMapFromOtherConfig(Node node, String otherConfigColumn) { + return bridgeMgr.getOpenvswitchOtherConfigMap(node, otherConfigColumn); } @Override public Collection getExternalElanInterfaces(String elanInstanceName) { List elanInterfaces = getElanInterfaces(elanInstanceName); if (elanInterfaces == null || elanInterfaces.isEmpty()) { - logger.trace("No ELAN interfaces defined for {}", elanInstanceName); + LOG.trace("No ELAN interfaces defined for {}", elanInstanceName); return Collections.emptySet(); } Set externalElanInterfaces = new HashSet<>(); for (String elanInterface : elanInterfaces) { - if (elanUtils.isExternal(elanInterface)) { + if (interfaceManager.isExternalInterface(elanInterface)) { externalElanInterfaces.add(elanInterface); } } @@ -578,9 +589,41 @@ public class ElanServiceProvider implements IElanService { return externalElanInterfaces; } + @Override + public String getExternalElanInterface(String elanInstanceName, BigInteger dpnId) { + return elanUtils.getExternalElanInterface(elanInstanceName, dpnId); + } + @Override public boolean isExternalInterface(String interfaceName) { - return elanUtils.isExternal(interfaceName); + return interfaceManager.isExternalInterface(interfaceName); + } + + @Override + public ElanInterface getElanInterfaceByElanInterfaceName(String interfaceName) { + return ElanUtils.getElanInterfaceByElanInterfaceName(broker, interfaceName); + } + + @Override + public void handleKnownL3DmacAddress(String macAddress, String elanInstanceName, int addOrRemove) { + if (!isL2BeforeL3) { + LOG.trace("ELAN service is after L3VPN in the Netvirt pipeline skip known L3DMAC flows installation"); + return; + } + ElanInstance elanInstance = ElanUtils.getElanInstanceByName(broker, elanInstanceName); + if (elanInstance == null) { + LOG.warn("Null elan instance {}", elanInstanceName); + return; + } + + List dpnsIdsForElanInstance = elanUtils.getParticipatingDpnsInElanInstance(elanInstanceName); + if (dpnsIdsForElanInstance == null || dpnsIdsForElanInstance.isEmpty()) { + LOG.warn("No DPNs for elan instance {}", elanInstance); + return; + } + + elanUtils.handleDmacRedirectToDispatcherFlows(elanInstance.getElanTag(), elanInstanceName, macAddress, + addOrRemove, dpnsIdsForElanInstance); } /** @@ -611,14 +654,17 @@ public class ElanServiceProvider implements IElanService { Long segmentationId = elanInstance.getSegmentationId(); interfaceName = parentRef + IfmConstants.OF_URI_SEPARATOR + segmentationId; String trunkName = parentRef + IfmConstants.OF_URI_SEPARATOR + "trunk"; - interfaceManager.createVLANInterface(trunkName, parentRef, null, null, null, - IfL2vlan.L2vlanMode.Trunk, true); - + // trunk interface may have been created by other vlan network + Interface trunkInterface = interfaceManager.getInterfaceInfoFromConfigDataStore(trunkName); + if (trunkInterface == null) { + interfaceManager.createVLANInterface(trunkName, parentRef, null, null, null, + IfL2vlan.L2vlanMode.Trunk, true); + } interfaceManager.createVLANInterface(interfaceName, trunkName, null, segmentationId.intValue(), null, IfL2vlan.L2vlanMode.TrunkMember, true); } } catch (InterfaceAlreadyExistsException e) { - logger.trace("Interface {} was already created", interfaceName); + LOG.trace("Interface {} was already created", interfaceName); } return interfaceName; @@ -629,23 +675,7 @@ public class ElanServiceProvider implements IElanService { InstanceIdentifier interfaceInstanceIdentifier = InstanceIdentifier.builder(Interfaces.class) .child(Interface.class, interfaceKey).build(); MDSALUtil.syncDelete(broker, LogicalDatastoreType.CONFIGURATION, interfaceInstanceIdentifier); - logger.debug("Deleting IETF interface {}", interfaceName); - } - - private String getExtInterfaceName(Node node, String physicalNetworkName) { - if (physicalNetworkName == null) { - return null; - } - - String providerMappingValue = bridgeMgr.getProviderMappingValue(node, physicalNetworkName); - if (providerMappingValue == null) { - logger.trace("No provider mapping found for physicalNetworkName {} node {}", physicalNetworkName, - node.getNodeId().getValue()); - return null; - } - - return bridgeMgr.southboundUtils.getDataPathId(node) + IfmConstants.OF_URI_SEPARATOR - + bridgeMgr.getIntBridgePortNameFor(node, providerMappingValue); + LOG.debug("Deleting IETF interface {}", interfaceName); } private void handleExternalElanNetworks(Node node, BiFunction function) { @@ -655,12 +685,12 @@ public class ElanServiceProvider implements IElanService { List elanInstances = getElanInstances(); if (elanInstances == null || elanInstances.isEmpty()) { - logger.trace("No ELAN instances found"); + LOG.trace("No ELAN instances found"); return; } for (ElanInstance elanInstance : elanInstances) { - String interfaceName = getExtInterfaceName(node, elanInstance.getPhysicalNetworkName()); + String interfaceName = bridgeMgr.getProviderInterfaceName(node, elanInstance.getPhysicalNetworkName()); if (interfaceName != null) { function.apply(elanInstance, interfaceName); } @@ -670,23 +700,36 @@ public class ElanServiceProvider implements IElanService { private void handleExternalElanNetwork(ElanInstance elanInstance, BiFunction function) { String elanInstanceName = elanInstance.getElanInstanceName(); if (elanInstance.getPhysicalNetworkName() == null) { - logger.trace("No physical network attached to {}", elanInstanceName); + LOG.trace("No physical network attached to {}", elanInstanceName); return; } List nodes = bridgeMgr.southboundUtils.getOvsdbNodes(); if (nodes == null || nodes.isEmpty()) { - logger.trace("No OVS nodes found while creating external network for ELAN {}", + LOG.trace("No OVS nodes found while creating external network for ELAN {}", elanInstance.getElanInstanceName()); return; } for (Node node : nodes) { if (bridgeMgr.isIntegrationBridge(node)) { - String interfaceName = getExtInterfaceName(node, elanInstance.getPhysicalNetworkName()); + String interfaceName = bridgeMgr.getProviderInterfaceName(node, elanInstance.getPhysicalNetworkName()); function.apply(elanInstance, interfaceName); } } } + private void setIsL2BeforeL3() { + short elanServiceRealIndex = ServiceIndex.getIndex(NwConstants.ELAN_SERVICE_NAME, + NwConstants.ELAN_SERVICE_INDEX); + short l3vpnServiceRealIndex = ServiceIndex.getIndex(NwConstants.L3VPN_SERVICE_NAME, + NwConstants.L3VPN_SERVICE_INDEX); + if (elanServiceRealIndex < l3vpnServiceRealIndex) { + LOG.info("ELAN service is set before L3VPN service in the Netvirt pipeline"); + isL2BeforeL3 = true; + } else { + LOG.info("ELAN service is set after L3VPN service in the Netvirt pipeline"); + isL2BeforeL3 = false; + } + } }