NETVIRT-1063 SNAT flows fails to install sporadically(conntrack SNAT) 73/67273/4
authorAswin Suryanarayanan <asuryana@redhat.com>
Thu, 18 Jan 2018 08:02:09 +0000 (13:32 +0530)
committerSam Hague <shague@redhat.com>
Sat, 10 Feb 2018 01:54:33 +0000 (01:54 +0000)
The vpind now retrieved using the subnet uuid from the router.

Change-Id: I6e8c0ce53349e40a336db12b247822f33c483c75
Signed-off-by: Aswin Suryanarayanan <asuryana@redhat.com>
vpnservice/natservice/natservice-impl/src/main/java/org/opendaylight/netvirt/natservice/internal/AbstractSnatService.java
vpnservice/natservice/natservice-impl/src/main/java/org/opendaylight/netvirt/natservice/internal/ConntrackBasedSnatService.java

index 300a5df947d1a51320bbab42574d0491b6fda8ec..0476f789ba5fa14a60eb3a28737e76aa1b782977 100644 (file)
@@ -35,6 +35,7 @@ import org.opendaylight.genius.mdsalutil.matches.MatchIpv4Destination;
 import org.opendaylight.genius.mdsalutil.matches.MatchMetadata;
 import org.opendaylight.genius.mdsalutil.matches.MatchTunnelId;
 import org.opendaylight.netvirt.natservice.api.SnatServiceListener;
+import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.yang.types.rev130715.Uuid;
 import org.opendaylight.yang.gen.v1.urn.opendaylight.genius.idmanager.rev160406.AllocateIdInput;
 import org.opendaylight.yang.gen.v1.urn.opendaylight.genius.idmanager.rev160406.AllocateIdInputBuilder;
 import org.opendaylight.yang.gen.v1.urn.opendaylight.genius.idmanager.rev160406.AllocateIdOutput;
@@ -139,9 +140,15 @@ public abstract class AbstractSnatService implements SnatServiceListener {
                     routerId);
             return;
         }
+        //The logic now handle only one external IP per router, others if present will be ignored.
         String externalIp = externalIps.get(0).getIpAddress();
-        installInboundFibEntry(dpnId, externalIp, routerName, routerId, addOrRemove);
-        installInboundTerminatingServiceTblEntry(dpnId, routerId, externalIp, addOrRemove);
+        Uuid externalSubnetId = externalIps.get(0).getSubnetId();
+        long extSubnetId = NatConstants.INVALID_ID;
+        if (addOrRemove == NwConstants.ADD_FLOW) {
+            extSubnetId = NatUtil.getExternalSubnetVpnId(dataBroker,externalSubnetId);
+        }
+        installInboundFibEntry(dpnId, externalIp, routerName, routerId, extSubnetId, addOrRemove);
+        installInboundTerminatingServiceTblEntry(dpnId, routerId, routerName, externalIp, extSubnetId, addOrRemove);
     }
 
     protected void installSnatCommonEntriesForNonNaptSwitch(Routers routers, BigInteger primarySwitchId,
@@ -156,8 +163,14 @@ public abstract class AbstractSnatService implements SnatServiceListener {
             return;
         }
         String externalIp = externalIps.get(0).getIpAddress();
+        Uuid externalSubnetId = externalIps.get(0).getSubnetId();
+        long extSubnetId = NatConstants.INVALID_ID;
+        if (addOrRemove == NwConstants.ADD_FLOW) {
+            extSubnetId = NatUtil.getExternalSubnetVpnId(dataBroker,externalSubnetId);
+        }
+
         installDefaultFibRouteForSNAT(dpnId, routerId, addOrRemove);
-        installSnatMissEntry(dpnId, routerId, routerName, primarySwitchId, externalIp, addOrRemove);
+        installSnatMissEntry(dpnId, routerId, routerName, primarySwitchId, externalIp, extSubnetId, addOrRemove);
     }
 
     protected abstract void installSnatSpecificEntriesForNaptSwitch(Routers routers, BigInteger dpnId,
@@ -167,11 +180,10 @@ public abstract class AbstractSnatService implements SnatServiceListener {
             int addOrRemove);
 
     protected void installInboundFibEntry(BigInteger dpnId, String externalIp, String routerName, Long routerId,
-            int addOrRemove) {
+            long extSubnetId, int addOrRemove) {
         List<MatchInfo> matches = new ArrayList<>();
         matches.add(MatchEthernetType.IPV4);
         if (addOrRemove == NwConstants.ADD_FLOW) {
-            Long extSubnetId = NatUtil.getVpnIdFromExternalSubnet(dataBroker, routerName, externalIp);
             if (extSubnetId == NatConstants.INVALID_ID) {
                 LOG.error("ConntrackBasedSnatService : installInboundFibEntry : external subnet id is invalid.");
                 return;
@@ -193,7 +205,7 @@ public abstract class AbstractSnatService implements SnatServiceListener {
     }
 
     protected void installSnatMissEntry(BigInteger dpnId, Long routerId, String routerName, BigInteger primarySwitchId,
-            String externalIp, int addOrRemove) {
+            String externalIp, long extSubnetId, int addOrRemove) {
         LOG.debug("installSnatMissEntry : Installing SNAT miss entry in switch {}", dpnId);
         List<ActionInfo> listActionInfoPrimary = new ArrayList<>();
         String ifNamePrimary = getTunnelInterfaceName(dpnId, primarySwitchId);
@@ -234,7 +246,6 @@ public abstract class AbstractSnatService implements SnatServiceListener {
         actionsInfo = new ArrayList<>();
         matches.add(new MatchEthernetType(0x0800L));
         if (addOrRemove == NwConstants.ADD_FLOW) {
-            Long extSubnetId = NatUtil.getVpnIdFromExternalSubnet(dataBroker, routerName, externalIp);
             if (extSubnetId == NatConstants.INVALID_ID) {
                 LOG.error("installSnatMissEntry : external subnet id is invalid.");
                 return;
@@ -254,8 +265,8 @@ public abstract class AbstractSnatService implements SnatServiceListener {
                 NwConstants.COOKIE_SNAT_TABLE, matches, instructions, addOrRemove);
     }
 
-    protected void installInboundTerminatingServiceTblEntry(BigInteger dpnId, Long  routerId, String externalIp,
-            int addOrRemove) {
+    protected void installInboundTerminatingServiceTblEntry(BigInteger dpnId, Long  routerId, String routerName,
+            String externalIp,  long extSubnetId, int addOrRemove) {
         //Install the tunnel table entry in NAPT switch for inbound traffic to SNAP IP from a non a NAPT switch.
         LOG.info("installInboundTerminatingServiceTblEntry : creating entry for Terminating Service Table "
                 + "for switch {}, routerId {}", dpnId, routerId);
@@ -263,8 +274,6 @@ public abstract class AbstractSnatService implements SnatServiceListener {
         matches.add(MatchEthernetType.IPV4);
         List<ActionInfo> actionsInfos = new ArrayList<>();
         if (addOrRemove == NwConstants.ADD_FLOW) {
-            String routerName = NatUtil.getRouterName(dataBroker, routerId);
-            long extSubnetId = NatUtil.getVpnIdFromExternalSubnet(dataBroker, routerName, externalIp);
             if (extSubnetId == NatConstants.INVALID_ID) {
                 LOG.error("installInboundTerminatingServiceTblEntry : external subnet id is invalid.");
                 return;
index c821e8957421a2ce0dc06b52d9e015b9706c8207..f49b810f27e0d329482db4f956a4318d840575e6 100644 (file)
@@ -31,6 +31,7 @@ import org.opendaylight.genius.mdsalutil.matches.MatchMetadata;
 import org.opendaylight.genius.mdsalutil.matches.MatchTunnelId;
 import org.opendaylight.genius.mdsalutil.nxmatches.NxMatchCtState;
 import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.yang.types.rev130715.MacAddress;
+import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.yang.types.rev130715.Uuid;
 import org.opendaylight.yang.gen.v1.urn.opendaylight.genius.idmanager.rev160406.IdManagerService;
 import org.opendaylight.yang.gen.v1.urn.opendaylight.genius.interfacemanager.rpcs.rev160406.OdlInterfaceRpcService;
 import org.opendaylight.yang.gen.v1.urn.opendaylight.genius.itm.rpcs.rev160406.ItmRpcService;
@@ -70,15 +71,29 @@ public abstract class ConntrackBasedSnatService extends AbstractSnatService {
 
         installSnatMissEntryForPrimrySwch(dpnId, routerId, elanId, addOrRemove);
         installTerminatingServiceTblEntry(dpnId, routerId, elanId, addOrRemove);
-        List<ExternalIps> externalIps = routers.getExternalIps();
+
         String extGwMacAddress = NatUtil.getExtGwMacAddFromRouterName(getDataBroker(), routerName);
         createOutboundTblTrackEntry(dpnId, routerId, extGwMacAddress, addOrRemove);
-        createOutboundTblEntry(dpnId, routerId, externalIps, elanId, extGwMacAddress, addOrRemove);
-        installNaptPfibFlow(routers, dpnId, routerId, externalIps, routerName, addOrRemove);
+        List<ExternalIps> externalIps = routers.getExternalIps();
+        if (externalIps.isEmpty()) {
+            LOG.error("AbstractSnatService: installSnatCommonEntriesForNaptSwitch no externalIP present"
+                    + " for routerId {}",
+                    routerId);
+            return;
+        }
+        //The logic now handle only one external IP per router, others if present will be ignored.
+        String externalIp = externalIps.get(0).getIpAddress();
+        Uuid externalSubnetId = externalIps.get(0).getSubnetId();
+        long extSubnetId = NatConstants.INVALID_ID;
+        if (addOrRemove == NwConstants.ADD_FLOW) {
+            extSubnetId = NatUtil.getExternalSubnetVpnId(getDataBroker(),externalSubnetId);
+        }
+        createOutboundTblEntry(dpnId, routerId, externalIp, elanId, extGwMacAddress, addOrRemove);
+        installNaptPfibFlow(routers, dpnId, routerId, routerName, extSubnetId, addOrRemove);
 
         //Install Inbound NAT entries
         Long extNetId = NatUtil.getVpnId(getDataBroker(), routers.getNetworkId().getValue());
-        installInboundEntry(dpnId, routerId, extNetId, externalIps, elanId, addOrRemove);
+        installInboundEntry(dpnId, routerId, routerName, extNetId, externalIp, elanId, extSubnetId, addOrRemove);
         installNaptPfibEntry(dpnId, routerId, addOrRemove);
 
     }
@@ -158,19 +173,13 @@ public abstract class ConntrackBasedSnatService extends AbstractSnatService {
 
     }
 
-    protected void createOutboundTblEntry(BigInteger dpnId, long routerId, List<ExternalIps> externalIps,
+    protected void createOutboundTblEntry(BigInteger dpnId, long routerId, String externalIp,
             int elanId, String extGwMacAddress,  int addOrRemove) {
         LOG.info("createOutboundTblEntry : dpId {} and routerId {}", dpnId, routerId);
         List<MatchInfoBase> matches = new ArrayList<>();
         matches.add(MatchEthernetType.IPV4);
         matches.add(new NxMatchCtState(TRACKED_NEW_CT_STATE, TRACKED_NEW_CT_MASK));
         matches.add(new MatchMetadata(MetaDataUtil.getVpnIdMetadata(routerId), MetaDataUtil.METADATA_MASK_VRFID));
-        if (externalIps.isEmpty()) {
-            LOG.error("createOutboundTblEntry : no externalIP present for routerId {}", routerId);
-            return;
-        }
-        //The logic now handle only one external IP per router, others if present will be ignored.
-        String externalIp = externalIps.get(0).getIpAddress();
         List<ActionInfo> actionsInfos = new ArrayList<>();
         if (addOrRemove == NwConstants.ADD_FLOW) {
             actionsInfos.add(new ActionSetFieldEthernetSource(new MacAddress(extGwMacAddress)));
@@ -193,19 +202,16 @@ public abstract class ConntrackBasedSnatService extends AbstractSnatService {
                 flowRef, NwConstants.COOKIE_SNAT_TABLE, matches, instructions, addOrRemove);
     }
 
-    protected void installNaptPfibFlow(Routers routers, BigInteger dpnId, long routerId, List<ExternalIps> externalIps,
-            String routerName, int addOrRemove) {
+    protected void installNaptPfibFlow(Routers routers, BigInteger dpnId, long routerId,
+            String routerName, long extSubnetId, int addOrRemove) {
         Long extNetId = NatUtil.getVpnId(getDataBroker(), routers.getNetworkId().getValue());
-        LOG.info("installNaptPfibFlow : dpId {}, extNetId {}, srcIp {}", dpnId, extNetId, externalIps);
+        LOG.info("installNaptPfibFlow : dpId {}, extNetId {}", dpnId, extNetId);
         List<MatchInfoBase> matches = new ArrayList<>();
         matches.add(MatchEthernetType.IPV4);
         matches.add(new NxMatchCtState(SNAT_CT_STATE, SNAT_CT_STATE_MASK));
         matches.add(new MatchMetadata(MetaDataUtil.getVpnIdMetadata(routerId), MetaDataUtil.METADATA_MASK_VRFID));
         List<ActionInfo> listActionInfo = new ArrayList<>();
         if (addOrRemove == NwConstants.ADD_FLOW) {
-            //The logic now handle only one external IP per router, others if present will be ignored.
-            String externalIp = externalIps.get(0).getIpAddress();
-            long extSubnetId = NatUtil.getVpnIdFromExternalSubnet(getDataBroker(), routerName, externalIp);
             if (extSubnetId == NatConstants.INVALID_ID) {
                 LOG.error("installNaptPfibFlow : external subnet id is invalid.");
                 return;
@@ -224,20 +230,13 @@ public abstract class ConntrackBasedSnatService extends AbstractSnatService {
                 flowRef, NwConstants.COOKIE_SNAT_TABLE, matches, instructions, addOrRemove);
     }
 
-    protected void installInboundEntry(BigInteger dpnId, long routerId, Long extNetId, List<ExternalIps> externalIps,
-            int elanId, int addOrRemove) {
+    protected void installInboundEntry(BigInteger dpnId, long routerId, String routerName, Long extNetId,
+            String externalIp, int elanId, long extSubnetId, int addOrRemove) {
         LOG.info("installInboundEntry : dpId {} and routerId {}", dpnId, routerId);
         List<MatchInfoBase> matches = new ArrayList<>();
         matches.add(MatchEthernetType.IPV4);
-        if (externalIps.isEmpty()) {
-            LOG.error("installInboundEntry : no externalIP present for routerId {}", routerId);
-            return;
-        }
-        String externalIp = externalIps.get(0).getIpAddress();
         matches.add(new MatchIpv4Destination(externalIp,"32"));
-        String routerName = NatUtil.getRouterName(getDataBroker(), routerId);
         if (addOrRemove == NwConstants.ADD_FLOW) {
-            long extSubnetId = NatUtil.getVpnIdFromExternalSubnet(getDataBroker(), routerName, externalIp);
             if (extSubnetId == NatConstants.INVALID_ID) {
                 LOG.error("installInboundEntry : external subnet id is invalid.");
                 return;