2 * Copyright (c) 2016 Ericsson India Global Services Pvt Ltd. and others. All rights reserved.
4 * This program and the accompanying materials are made available under the
5 * terms of the Eclipse Public License v1.0 which accompanies this distribution,
6 * and is available at http://www.eclipse.org/legal/epl-v10.html
8 package org.opendaylight.netvirt.natservice.internal;
10 import static org.opendaylight.genius.infra.Datastore.CONFIGURATION;
12 import com.google.common.base.Optional;
13 import java.math.BigInteger;
14 import java.util.Collection;
15 import java.util.Collections;
16 import java.util.List;
18 import java.util.concurrent.ExecutionException;
19 import javax.annotation.PostConstruct;
20 import javax.inject.Inject;
21 import javax.inject.Singleton;
22 import org.opendaylight.controller.md.sal.binding.api.DataBroker;
23 import org.opendaylight.controller.md.sal.common.api.data.LogicalDatastoreType;
24 import org.opendaylight.genius.datastoreutils.AsyncDataTreeChangeListenerBase;
25 import org.opendaylight.genius.datastoreutils.SingleTransactionDataBroker;
26 import org.opendaylight.genius.infra.Datastore.Configuration;
27 import org.opendaylight.genius.infra.ManagedNewTransactionRunner;
28 import org.opendaylight.genius.infra.ManagedNewTransactionRunnerImpl;
29 import org.opendaylight.genius.infra.TypedReadWriteTransaction;
30 import org.opendaylight.genius.mdsalutil.BucketInfo;
31 import org.opendaylight.genius.mdsalutil.FlowEntity;
32 import org.opendaylight.genius.mdsalutil.GroupEntity;
33 import org.opendaylight.genius.mdsalutil.MDSALUtil;
34 import org.opendaylight.genius.mdsalutil.NwConstants;
35 import org.opendaylight.genius.mdsalutil.interfaces.IMdsalApiManager;
36 import org.opendaylight.infrautils.jobcoordinator.JobCoordinator;
37 import org.opendaylight.infrautils.utils.concurrent.ListenableFutures;
38 import org.opendaylight.netvirt.elanmanager.api.IElanService;
39 import org.opendaylight.netvirt.natservice.api.SnatServiceManager;
40 import org.opendaylight.netvirt.neutronvpn.interfaces.INeutronVpnManager;
41 import org.opendaylight.serviceutils.upgrade.UpgradeState;
42 import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.yang.types.rev130715.Uuid;
43 import org.opendaylight.yang.gen.v1.urn.opendaylight.genius.idmanager.rev160406.IdManagerService;
44 import org.opendaylight.yang.gen.v1.urn.opendaylight.group.types.rev131018.GroupTypes;
45 import org.opendaylight.yang.gen.v1.urn.opendaylight.netvirt.l3vpn.rev130911.NeutronRouterDpns;
46 import org.opendaylight.yang.gen.v1.urn.opendaylight.netvirt.l3vpn.rev130911.neutron.router.dpns.RouterDpnList;
47 import org.opendaylight.yang.gen.v1.urn.opendaylight.netvirt.l3vpn.rev130911.neutron.router.dpns.router.dpn.list.DpnVpninterfacesList;
48 import org.opendaylight.yang.gen.v1.urn.opendaylight.netvirt.natservice.config.rev170206.NatserviceConfig;
49 import org.opendaylight.yang.gen.v1.urn.opendaylight.netvirt.natservice.config.rev170206.NatserviceConfig.NatMode;
50 import org.opendaylight.yang.gen.v1.urn.opendaylight.netvirt.natservice.rev160111.ProviderTypes;
51 import org.opendaylight.yang.gen.v1.urn.opendaylight.netvirt.natservice.rev160111.ext.routers.Routers;
52 import org.opendaylight.yangtools.yang.binding.InstanceIdentifier;
53 import org.slf4j.Logger;
54 import org.slf4j.LoggerFactory;
57 public class RouterDpnChangeListener
58 extends AsyncDataTreeChangeListenerBase<DpnVpninterfacesList, RouterDpnChangeListener> {
60 private static final Logger LOG = LoggerFactory.getLogger(RouterDpnChangeListener.class);
61 private final DataBroker dataBroker;
62 private final ManagedNewTransactionRunner txRunner;
63 private final IMdsalApiManager mdsalManager;
64 private final SNATDefaultRouteProgrammer snatDefaultRouteProgrammer;
65 private final NaptSwitchHA naptSwitchHA;
66 private final IdManagerService idManager;
67 private final INeutronVpnManager nvpnManager;
68 private final ExternalNetworkGroupInstaller extNetGroupInstaller;
69 private final IElanService elanManager;
70 private final JobCoordinator coordinator;
71 private final SnatServiceManager natServiceManager;
72 private final NatMode natMode;
73 private final UpgradeState upgradeState;
76 public RouterDpnChangeListener(final DataBroker dataBroker, final IMdsalApiManager mdsalManager,
77 final SNATDefaultRouteProgrammer snatDefaultRouteProgrammer,
78 final NaptSwitchHA naptSwitchHA,
79 final IdManagerService idManager,
80 final ExternalNetworkGroupInstaller extNetGroupInstaller,
81 final INeutronVpnManager nvpnManager,
82 final SnatServiceManager natServiceManager,
83 final NatserviceConfig config,
84 final IElanService elanManager,
85 final JobCoordinator coordinator,
86 final UpgradeState upgradeState) {
87 super(DpnVpninterfacesList.class, RouterDpnChangeListener.class);
88 this.dataBroker = dataBroker;
89 this.txRunner = new ManagedNewTransactionRunnerImpl(dataBroker);
90 this.mdsalManager = mdsalManager;
91 this.snatDefaultRouteProgrammer = snatDefaultRouteProgrammer;
92 this.naptSwitchHA = naptSwitchHA;
93 this.idManager = idManager;
94 this.extNetGroupInstaller = extNetGroupInstaller;
95 this.nvpnManager = nvpnManager;
96 this.elanManager = elanManager;
97 this.natServiceManager = natServiceManager;
98 this.coordinator = coordinator;
99 this.natMode = config != null ? config.getNatMode() : NatMode.Controller;
100 this.upgradeState = upgradeState;
106 LOG.info("{} init", getClass().getSimpleName());
107 registerListener(LogicalDatastoreType.OPERATIONAL, dataBroker);
111 protected RouterDpnChangeListener getDataTreeChangeListener() {
112 return RouterDpnChangeListener.this;
116 protected InstanceIdentifier<DpnVpninterfacesList> getWildCardPath() {
117 return InstanceIdentifier.create(NeutronRouterDpns.class).child(RouterDpnList.class)
118 .child(DpnVpninterfacesList.class);
122 protected void add(final InstanceIdentifier<DpnVpninterfacesList> identifier, final DpnVpninterfacesList dpnInfo) {
123 LOG.trace("add : key: {}, value: {}", dpnInfo.key(), dpnInfo);
124 final String routerUuid = identifier.firstKeyOf(RouterDpnList.class).getRouterId();
125 BigInteger dpnId = dpnInfo.getDpnId();
126 //check router is associated to external network
127 InstanceIdentifier<Routers> id = NatUtil.buildRouterIdentifier(routerUuid);
128 Optional<Routers> routerData =
129 SingleTransactionDataBroker.syncReadOptionalAndTreatReadFailedExceptionAsAbsentOptional(dataBroker,
130 LogicalDatastoreType.CONFIGURATION, id);
131 if (routerData.isPresent()) {
132 Routers router = routerData.get();
133 Uuid networkId = router.getNetworkId();
134 if (networkId != null) {
135 if (natMode == NatMode.Conntrack) {
136 BigInteger naptSwitch = NatUtil.getPrimaryNaptfromRouterName(dataBroker, router.getRouterName());
137 if (naptSwitch == null || naptSwitch.equals(BigInteger.ZERO)) {
138 LOG.warn("add : NAPT switch is not selected.");
141 //If it is for NAPT switch skip as the flows would be already programmed.
142 if (naptSwitch.equals(dpnId)) {
143 LOG.debug("Skipping the notification recived for NAPT switch {}", routerUuid);
146 ListenableFutures.addErrorLogging(txRunner.callWithNewReadWriteTransactionAndSubmit(CONFIGURATION,
148 natServiceManager.notify(confTx, router, null, naptSwitch, dpnId,
149 SnatServiceManager.Action.CNT_ROUTER_ENBL);
150 if (router.isEnableSnat()) {
151 natServiceManager.notify(confTx, router, null, naptSwitch, naptSwitch,
152 SnatServiceManager.Action.SNAT_ROUTER_ENBL);
154 }), LOG, "Error notifying NAT service manager");
156 Long routerId = NatUtil.getVpnId(dataBroker, routerUuid);
157 if (routerId == NatConstants.INVALID_ID) {
158 LOG.error("add : Invalid routerId returned for routerName {}", routerUuid);
161 ProviderTypes extNwProvType = NatEvpnUtil.getExtNwProvTypeFromRouterName(dataBroker,
162 routerUuid, networkId);
163 if (extNwProvType == ProviderTypes.FLAT || extNwProvType == ProviderTypes.VLAN) {
164 coordinator.enqueueJob(NatConstants.NAT_DJC_PREFIX + networkId, () -> {
165 extNetGroupInstaller.installExtNetGroupEntries(networkId, dpnId);
166 installDefaultNatRouteForRouterExternalSubnets(dpnId,
167 NatUtil.getExternalSubnetIdsFromExternalIps(router.getExternalIps()));
168 return Collections.emptyList();
171 coordinator.enqueueJob(NatConstants.NAT_DJC_PREFIX + router.getRouterName(), () -> {
172 LOG.debug("add : Router {} is associated with ext nw {}", routerUuid, networkId);
173 Uuid vpnName = NatUtil.getVpnForRouter(dataBroker, routerUuid);
174 return Collections.singletonList(
175 txRunner.callWithNewReadWriteTransactionAndSubmit(CONFIGURATION, confTx -> {
177 if (vpnName == null) {
178 LOG.debug("add : Internal vpn associated to router {}", routerUuid);
180 if (vpnId == NatConstants.INVALID_ID) {
181 LOG.error("add : Invalid vpnId returned for routerName {}", routerUuid);
184 LOG.debug("add : Retrieved vpnId {} for router {}", vpnId, routerUuid);
185 //Install default entry in FIB to SNAT table
187 "add : Installing default route in FIB on dpn {} for router {} with vpn {}",
188 dpnId, routerUuid, vpnId);
189 snatDefaultRouteProgrammer.installDefNATRouteInDPN(dpnId, vpnId, confTx);
191 LOG.debug("add : External BGP vpn associated to router {}", routerUuid);
192 vpnId = NatUtil.getVpnId(dataBroker, vpnName.getValue());
193 if (vpnId == NatConstants.INVALID_ID) {
194 LOG.error("add : Invalid vpnId returned for routerName {}", routerUuid);
197 LOG.debug("add : Retrieved vpnId {} for router {}", vpnId, routerUuid);
198 //Install default entry in FIB to SNAT table
199 LOG.debug("add : Installing default route in FIB on dpn {} for routerId {} with "
200 + "vpnId {}...", dpnId, routerUuid, vpnId);
201 snatDefaultRouteProgrammer.installDefNATRouteInDPN(dpnId, vpnId, routerId, confTx);
203 /* install V6 internet default fallback rule in FIB_TABLE if router
204 * is having V6 subnet
206 nvpnManager.programV6InternetFallbackFlow(new Uuid(routerUuid),
207 NatUtil.getVpnIdfromNetworkId(dataBroker, networkId), NwConstants.ADD_FLOW);
208 if (router.isEnableSnat()) {
209 LOG.info("add : SNAT enabled for router {}", routerUuid);
210 if (extNwProvType == null) {
211 LOG.error("add : External Network Provider Type missing");
214 handleSNATForDPN(dpnId, routerUuid, routerId, vpnId, confTx, extNwProvType);
216 LOG.info("add : SNAT is not enabled for router {} to handle addDPN event {}",
220 }, NatConstants.NAT_DJC_MAX_RETRIES);
221 } // end of controller based SNAT
224 LOG.debug("add : Router {} is not associated with External network", routerUuid);
229 protected void remove(InstanceIdentifier<DpnVpninterfacesList> identifier, DpnVpninterfacesList dpnInfo) {
230 LOG.trace("remove : key: {}, value: {}", dpnInfo.key(), dpnInfo);
231 final String routerUuid = identifier.firstKeyOf(RouterDpnList.class).getRouterId();
232 Long routerId = NatUtil.getVpnId(dataBroker, routerUuid);
233 if (routerId == NatConstants.INVALID_ID) {
234 LOG.error("REMOVE: Invalid routId returned for routerName {}",routerUuid);
237 BigInteger dpnId = dpnInfo.getDpnId();
238 //check router is associated to external network
239 InstanceIdentifier<Routers> id = NatUtil.buildRouterIdentifier(routerUuid);
240 Optional<Routers> routerData =
241 SingleTransactionDataBroker.syncReadOptionalAndTreatReadFailedExceptionAsAbsentOptional(dataBroker,
242 LogicalDatastoreType.CONFIGURATION, id);
243 if (routerData.isPresent()) {
244 Routers router = routerData.get();
245 Uuid networkId = router.getNetworkId();
246 if (networkId != null) {
247 if (natMode == NatMode.Conntrack) {
248 BigInteger naptSwitch = NatUtil.getPrimaryNaptfromRouterName(dataBroker, router.getRouterName());
249 if (naptSwitch == null || naptSwitch.equals(BigInteger.ZERO)) {
250 LOG.warn("remove : NAPT switch is not selected.");
253 //If it is for NAPT switch skip as the flows would be already programmed.
254 if (naptSwitch.equals(dpnId)) {
255 LOG.debug("Skipping the notification recived for NAPT switch {}", routerUuid);
258 ListenableFutures.addErrorLogging(txRunner.callWithNewReadWriteTransactionAndSubmit(CONFIGURATION,
260 natServiceManager.notify(confTx, router, null, naptSwitch, dpnId,
261 SnatServiceManager.Action.CNT_ROUTER_DISBL);
262 if (router.isEnableSnat()) {
263 natServiceManager.notify(confTx, router, null, naptSwitch, naptSwitch,
264 SnatServiceManager.Action.SNAT_ROUTER_DISBL);
266 }), LOG, "Error notifying NAT service manager");
268 coordinator.enqueueJob(NatConstants.NAT_DJC_PREFIX + routerUuid, () -> {
269 LOG.debug("remove : Router {} is associated with ext nw {}", routerUuid, networkId);
270 Uuid vpnName = NatUtil.getVpnForRouter(dataBroker, routerUuid);
271 return Collections.singletonList(
272 txRunner.callWithNewReadWriteTransactionAndSubmit(CONFIGURATION, confTx -> {
274 if (vpnName == null) {
275 LOG.debug("remove : Internal vpn associated to router {}", routerUuid);
277 if (vpnId == NatConstants.INVALID_ID) {
278 LOG.error("remove : Invalid vpnId returned for routerName {}", routerUuid);
281 LOG.debug("remove : Retrieved vpnId {} for router {}", vpnId, routerUuid);
282 //Remove default entry in FIB
283 LOG.debug("remove : Removing default route in FIB on dpn {} for vpn {} ...", dpnId,
285 snatDefaultRouteProgrammer.removeDefNATRouteInDPN(dpnId, vpnId, confTx);
287 LOG.debug("remove : External vpn associated to router {}", routerUuid);
288 vpnId = NatUtil.getVpnId(dataBroker, vpnName.getValue());
289 if (vpnId == NatConstants.INVALID_ID) {
290 LOG.error("remove : Invalid vpnId returned for routerName {}", routerUuid);
293 LOG.debug("remove : Retrieved vpnId {} for router {}", vpnId, routerUuid);
294 //Remove default entry in FIB
295 LOG.debug("remove : Removing default route in FIB on dpn {} for vpn {} ...", dpnId,
297 snatDefaultRouteProgrammer.removeDefNATRouteInDPN(dpnId, vpnId, routerId, confTx);
299 /* remove V6 internet default fallback rule in FIB_TABLE if router
300 * is having V6 subnet
302 nvpnManager.programV6InternetFallbackFlow(new Uuid(routerUuid),
303 NatUtil.getVpnIdfromNetworkId(dataBroker, networkId), NwConstants.DEL_FLOW);
304 if (router.isEnableSnat()) {
305 LOG.info("remove : SNAT enabled for router {}", routerUuid);
306 removeSNATFromDPN(dpnId, routerUuid, routerId, vpnId, networkId, confTx);
308 LOG.info("remove : SNAT is not enabled for router {} to handle removeDPN event {}",
312 }, NatConstants.NAT_DJC_MAX_RETRIES);
313 } // end of controller based SNAT
319 protected void update(InstanceIdentifier<DpnVpninterfacesList> identifier, DpnVpninterfacesList original,
320 DpnVpninterfacesList update) {
321 LOG.trace("Update key: {}, original: {}, update: {}", update.key(), original, update);
324 void handleSNATForDPN(BigInteger dpnId, String routerName, long routerId, Long routerVpnId,
325 TypedReadWriteTransaction<Configuration> confTx, ProviderTypes extNwProvType) {
326 //Check if primary and secondary switch are selected, If not select the role
327 //Install select group to NAPT switch
328 //Install default miss entry to NAPT switch
329 BigInteger naptSwitch;
331 BigInteger naptId = NatUtil.getPrimaryNaptfromRouterName(dataBroker, routerName);
332 if (naptId == null || naptId.equals(BigInteger.ZERO)
333 || !NatUtil.getSwitchStatus(dataBroker, naptId) && !upgradeState.isUpgradeInProgress()) {
334 LOG.debug("handleSNATForDPN : NaptSwitch is down or not selected for router {},naptId {}",
337 boolean naptstatus = naptSwitchHA.updateNaptSwitch(routerName, naptSwitch);
339 LOG.error("handleSNATForDPN : Failed to update newNaptSwitch {} for routername {}",
340 naptSwitch, routerName);
343 LOG.debug("handleSNATForDPN : Switch {} is elected as NaptSwitch for router {}", dpnId, routerName);
345 // When NAPT switch is elected during first VM comes up for the given Router
346 if (NatUtil.isOpenStackVniSemanticsEnforcedForGreAndVxlan(elanManager, extNwProvType)) {
347 NatOverVxlanUtil.validateAndCreateVxlanVniPool(dataBroker, nvpnManager,
348 idManager, NatConstants.ODL_VNI_POOL_NAME);
351 Routers extRouters = NatUtil.getRoutersFromConfigDS(dataBroker, routerName);
352 if (extRouters != null) {
353 NatUtil.createRouterIdsConfigDS(dataBroker, routerId, routerName);
354 naptSwitchHA.subnetRegisterMapping(extRouters, routerId);
357 naptSwitchHA.installSnatFlows(routerName, routerId, naptSwitch, routerVpnId, confTx);
359 // Install miss entry (table 26) pointing to table 46
360 FlowEntity flowEntity = naptSwitchHA.buildSnatFlowEntityForNaptSwitch(dpnId, routerName,
361 routerVpnId, NatConstants.ADD_FLOW);
362 if (flowEntity == null) {
363 LOG.error("handleSNATForDPN : Failed to populate flowentity for router {} with dpnId {}",
367 LOG.debug("handleSNATForDPN : Successfully installed flow for dpnId {} router {}", dpnId, routerName);
368 mdsalManager.addFlow(confTx, flowEntity);
369 //Removing primary flows from old napt switch
370 if (naptId != null && !naptId.equals(BigInteger.ZERO)) {
371 LOG.debug("handleSNATForDPN : Removing primary flows from old napt switch {} for router {}",
373 naptSwitchHA.removeSnatFlowsInOldNaptSwitch(routerName, routerId, naptId, null, confTx);
375 } else if (naptId.equals(dpnId)) {
376 LOG.debug("handleSNATForDPN : NaptSwitch {} gone down during cluster reboot came alive", naptId);
379 LOG.debug("handleSNATForDPN : Napt switch with Id {} is already elected for router {}",
383 List<BucketInfo> bucketInfo = naptSwitchHA.handleGroupInNeighborSwitches(dpnId,
384 routerName, routerId, naptSwitch);
385 naptSwitchHA.installSnatGroupEntry(dpnId, bucketInfo, routerName);
387 // Install miss entry (table 26) pointing to group
388 long groupId = NatUtil.createGroupId(NatUtil.getGroupIdKey(routerName), idManager);
389 FlowEntity flowEntity =
390 naptSwitchHA.buildSnatFlowEntity(dpnId, routerName, groupId,
391 routerVpnId, NatConstants.ADD_FLOW);
392 if (flowEntity == null) {
393 LOG.error("handleSNATForDPN : Failed to populate flowentity for router {} with dpnId {} groupId {}",
394 routerName, dpnId, groupId);
397 LOG.debug("handleSNATForDPN : Successfully installed flow for dpnId {} router {} group {}",
398 dpnId, routerName, groupId);
399 mdsalManager.addFlow(confTx, flowEntity);
402 } catch (InterruptedException | ExecutionException e) {
403 LOG.error("handleSNATForDPN : Exception in handleSNATForDPN", e);
407 // TODO Clean up the exception handling
408 @SuppressWarnings("checkstyle:IllegalCatch")
409 void removeSNATFromDPN(BigInteger dpnId, String routerName, long routerId, long routerVpnId,
410 Uuid extNetworkId, TypedReadWriteTransaction<Configuration> confTx) {
411 //irrespective of naptswitch or non-naptswitch, SNAT default miss entry need to be removed
412 //remove miss entry to NAPT switch
413 //if naptswitch elect new switch and install Snat flows and remove those flows in oldnaptswitch
415 Collection<String> externalIpCache = NatUtil.getExternalIpsForRouter(dataBroker, routerId);
416 ProviderTypes extNwProvType = NatEvpnUtil.getExtNwProvTypeFromRouterName(dataBroker, routerName, extNetworkId);
417 if (extNwProvType == null) {
420 //Get the external IP labels other than VXLAN provider type. Since label is not applicable for VXLAN
421 Map<String, Long> externalIpLabel;
422 if (extNwProvType == ProviderTypes.VXLAN) {
423 externalIpLabel = null;
425 externalIpLabel = NatUtil.getExternalIpsLabelForRouter(dataBroker, routerId);
427 BigInteger naptSwitch = NatUtil.getPrimaryNaptfromRouterName(dataBroker, routerName);
428 if (naptSwitch == null || naptSwitch.equals(BigInteger.ZERO)) {
429 LOG.error("removeSNATFromDPN : No naptSwitch is selected for router {}", routerName);
434 naptSwitchHA.isNaptSwitchDown(routerName, routerId, dpnId, naptSwitch, routerVpnId,
435 externalIpCache, confTx);
437 LOG.debug("removeSNATFromDPN: Switch with DpnId {} is not naptSwitch for router {}",
439 long groupId = NatUtil.createGroupId(NatUtil.getGroupIdKey(routerName), idManager);
440 FlowEntity flowEntity = null;
442 flowEntity = naptSwitchHA.buildSnatFlowEntity(dpnId, routerName, groupId, routerVpnId,
443 NatConstants.DEL_FLOW);
444 if (flowEntity == null) {
445 LOG.error("removeSNATFromDPN : Failed to populate flowentity for router:{} "
446 + "with dpnId:{} groupId:{}", routerName, dpnId, groupId);
449 LOG.debug("removeSNATFromDPN : Removing default SNAT miss entry flow entity {}", flowEntity);
450 mdsalManager.removeFlow(confTx, flowEntity);
452 } catch (Exception ex) {
453 LOG.error("removeSNATFromDPN : Failed to remove default SNAT miss entry flow entity {}",
457 LOG.debug("removeSNATFromDPN : Removed default SNAT miss entry flow for dpnID {} with routername {}",
461 GroupEntity groupEntity = null;
463 groupEntity = MDSALUtil.buildGroupEntity(dpnId, groupId, routerName,
464 GroupTypes.GroupAll, Collections.emptyList() /*listBucketInfo*/);
465 LOG.info("removeSNATFromDPN : Removing NAPT GroupEntity:{}", groupEntity);
466 mdsalManager.removeGroup(groupEntity);
467 } catch (Exception ex) {
468 LOG.error("removeSNATFromDPN : Failed to remove group entity {}", groupEntity, ex);
471 LOG.debug("removeSNATFromDPN : Removed default SNAT miss entry flow for dpnID {} with routerName {}",
474 naptSwitchHA.removeSnatFlowsInOldNaptSwitch(routerName, routerId, naptSwitch,
475 externalIpLabel, confTx);
476 //remove table 26 flow ppointing to table46
477 FlowEntity flowEntity = null;
479 flowEntity = naptSwitchHA.buildSnatFlowEntityForNaptSwitch(dpnId, routerName, routerVpnId,
480 NatConstants.DEL_FLOW);
481 if (flowEntity == null) {
482 LOG.error("removeSNATFromDPN : Failed to populate flowentity for router {} with dpnId {}",
486 LOG.debug("removeSNATFromDPN : Removing default SNAT miss entry flow entity for router {} with "
487 + "dpnId {} in napt switch {}", routerName, dpnId, naptSwitch);
488 mdsalManager.removeFlow(confTx, flowEntity);
490 } catch (Exception ex) {
491 LOG.error("removeSNATFromDPN : Failed to remove default SNAT miss entry flow entity {}",
495 LOG.debug("removeSNATFromDPN : Removed default SNAT miss entry flow for dpnID {} with routername {}",
498 //best effort to check IntExt model
499 naptSwitchHA.bestEffortDeletion(routerId, routerName, externalIpLabel, confTx);
501 } catch (InterruptedException | ExecutionException e) {
502 LOG.error("removeSNATFromDPN : Exception while handling naptSwitch down for router {}", routerName, e);
506 private void installDefaultNatRouteForRouterExternalSubnets(BigInteger dpnId, Collection<Uuid> externalSubnetIds) {
507 if (externalSubnetIds == null) {
508 LOG.error("installDefaultNatRouteForRouterExternalSubnets : No external subnets for router");
512 for (Uuid subnetId : externalSubnetIds) {
513 long vpnIdForSubnet = NatUtil.getExternalSubnetVpnId(dataBroker, subnetId);
514 if (vpnIdForSubnet != NatConstants.INVALID_ID) {
515 LOG.info("installDefaultNatRouteForRouterExternalSubnets : Installing default routes in FIB on dpn {} "
516 + "for subnetId {} with vpnId {}", dpnId, subnetId, vpnIdForSubnet);
517 snatDefaultRouteProgrammer.installDefNATRouteInDPN(dpnId, vpnIdForSubnet, subnetId.getValue());
519 LOG.debug("installDefaultNatRouteForRouterExternalSubnets : No vpnID for subnet {} found", subnetId);