diff --git a/server/src/com/cloud/network/router/VirtualNetworkApplianceManagerImpl.java b/server/src/com/cloud/network/router/VirtualNetworkApplianceManagerImpl.java index 1a57bce6998..a56ebb01f8c 100755 --- a/server/src/com/cloud/network/router/VirtualNetworkApplianceManagerImpl.java +++ b/server/src/com/cloud/network/router/VirtualNetworkApplianceManagerImpl.java @@ -1994,19 +1994,19 @@ public class VirtualNetworkApplianceManagerImpl implements VirtualNetworkApplian //Re-apply static nats s_logger.debug("Found " + staticNats.size() + " static nat(s) to apply as a part of domR " + router + " start."); if (!staticNats.isEmpty()) { - createApplyStaticNatCommands(staticNats, router, cmds, guestNetworkId); + createApplyStaticNatCommands(staticNats, router, cmds, guestNetworkId); } //Re-apply firewall rules s_logger.debug("Found " + staticNats.size() + " firewall rule(s) to apply as a part of domR " + router + " start."); if (!firewallRules.isEmpty()) { - createFirewallRulesCommands(firewallRules, router, cmds, guestNetworkId); + createFirewallRulesCommands(firewallRules, router, cmds, guestNetworkId); } // Re-apply port forwarding rules s_logger.debug("Found " + pfRules.size() + " port forwarding rule(s) to apply as a part of domR " + router + " start."); if (!pfRules.isEmpty()) { - createApplyPortForwardingRulesCommands(pfRules, router, cmds, guestNetworkId); + createApplyPortForwardingRulesCommands(pfRules, router, cmds, guestNetworkId); } // Re-apply static nat rules @@ -2016,7 +2016,7 @@ public class VirtualNetworkApplianceManagerImpl implements VirtualNetworkApplian for (FirewallRule rule : staticNatFirewallRules) { staticNatRules.add(_rulesMgr.buildStaticNatRule(rule, false)); } - createApplyStaticNatRulesCommands(staticNatRules, router, cmds, guestNetworkId); + createApplyStaticNatRulesCommands(staticNatRules, router, cmds, guestNetworkId); } // Re-apply vpn rules diff --git a/server/src/com/cloud/network/router/VpcVirtualNetworkApplianceManagerImpl.java b/server/src/com/cloud/network/router/VpcVirtualNetworkApplianceManagerImpl.java index f8388855e8f..d19a81e9b81 100644 --- a/server/src/com/cloud/network/router/VpcVirtualNetworkApplianceManagerImpl.java +++ b/server/src/com/cloud/network/router/VpcVirtualNetworkApplianceManagerImpl.java @@ -73,8 +73,11 @@ import com.cloud.network.dao.PhysicalNetworkDao; import com.cloud.network.firewall.NetworkACLService; import com.cloud.network.rules.NetworkACL; import com.cloud.network.vpc.PrivateGateway; +import com.cloud.network.vpc.StaticRoute; import com.cloud.network.vpc.StaticRouteProfile; import com.cloud.network.vpc.Vpc; +import com.cloud.network.vpc.VpcManager; +import com.cloud.network.vpc.Dao.StaticRouteDao; import com.cloud.network.vpc.Dao.VpcDao; import com.cloud.network.vpc.Dao.VpcOfferingDao; import com.cloud.user.Account; @@ -112,6 +115,10 @@ public class VpcVirtualNetworkApplianceManagerImpl extends VirtualNetworkApplian NetworkACLService _networkACLService = null; @Inject VMInstanceDao _vmDao; + @Inject + StaticRouteDao _staticRouteDao; + @Inject + VpcManager _vpcMgr; @Override public List deployVirtualRouterInVpc(Vpc vpc, DeployDestination dest, Account owner, @@ -788,7 +795,24 @@ public class VpcVirtualNetworkApplianceManagerImpl extends VirtualNetworkApplian return false; } - //3) REPROGRAM GUEST NETWORK + //3) RE-APPLY ALL STATIC ROUTE RULES + List routes = _staticRouteDao.listByVpcId(router.getVpcId()); + List staticRouteProfiles = new ArrayList(routes.size()); + Map gatewayMap = new HashMap(); + for (StaticRoute route : routes) { + PrivateGateway gateway = gatewayMap.get(route.getVpcGatewayId()); + if (gateway == null) { + gateway = _vpcMgr.getVpcPrivateGateway(route.getVpcGatewayId()); + gatewayMap.put(gateway.getId(), gateway); + } + staticRouteProfiles.add(new StaticRouteProfile(route, gateway)); + } + + s_logger.debug("Found " + staticRouteProfiles.size() + " static routes to apply as a part of vpc route " + + router + " start"); + createStaticRouteCommands(staticRouteProfiles, router, cmds); + + //4) REPROGRAM GUEST NETWORK boolean reprogramGuestNtwks = true; if (profile.getParameter(Param.ReProgramGuestNetworks) != null && (Boolean) profile.getParameter(Param.ReProgramGuestNetworks) == false) { diff --git a/server/src/com/cloud/network/vpc/Dao/StaticRouteDao.java b/server/src/com/cloud/network/vpc/Dao/StaticRouteDao.java index 9f5a33964d8..d5a7d35cd2c 100644 --- a/server/src/com/cloud/network/vpc/Dao/StaticRouteDao.java +++ b/server/src/com/cloud/network/vpc/Dao/StaticRouteDao.java @@ -28,4 +28,7 @@ public interface StaticRouteDao extends GenericDao{ List listByGatewayIdAndNotRevoked(long gatewayId); List listByVpcId(long vpcId); + + long countRoutesByGateway(long gatewayId); + } diff --git a/server/src/com/cloud/network/vpc/Dao/StaticRouteDaoImpl.java b/server/src/com/cloud/network/vpc/Dao/StaticRouteDaoImpl.java index 0f03a85ea97..d88b89f04f0 100644 --- a/server/src/com/cloud/network/vpc/Dao/StaticRouteDaoImpl.java +++ b/server/src/com/cloud/network/vpc/Dao/StaticRouteDaoImpl.java @@ -20,8 +20,10 @@ import com.cloud.network.vpc.StaticRoute; import com.cloud.network.vpc.StaticRouteVO; import com.cloud.utils.db.DB; import com.cloud.utils.db.GenericDaoBase; +import com.cloud.utils.db.GenericSearchBuilder; import com.cloud.utils.db.SearchBuilder; import com.cloud.utils.db.SearchCriteria; +import com.cloud.utils.db.SearchCriteria.Func; import com.cloud.utils.db.SearchCriteria.Op; /** @@ -33,6 +35,7 @@ import com.cloud.utils.db.SearchCriteria.Op; public class StaticRouteDaoImpl extends GenericDaoBase implements StaticRouteDao{ protected final SearchBuilder AllFieldsSearch; protected final SearchBuilder NotRevokedSearch; + protected final GenericSearchBuilder RoutesByGatewayCount; protected StaticRouteDaoImpl() { super(); @@ -48,6 +51,11 @@ public class StaticRouteDaoImpl extends GenericDaoBase impl NotRevokedSearch.and("gatewayId", NotRevokedSearch.entity().getVpcGatewayId(), Op.EQ); NotRevokedSearch.and("state", NotRevokedSearch.entity().getState(), Op.NEQ); NotRevokedSearch.done(); + + RoutesByGatewayCount = createSearchBuilder(Long.class); + RoutesByGatewayCount.select(null, Func.COUNT, RoutesByGatewayCount.entity().getId()); + RoutesByGatewayCount.and("gatewayId", RoutesByGatewayCount.entity().getVpcGatewayId(), Op.EQ); + RoutesByGatewayCount.done(); } @@ -77,4 +85,11 @@ public class StaticRouteDaoImpl extends GenericDaoBase impl sc.setParameters("vpcId", vpcId); return listBy(sc); } + + @Override + public long countRoutesByGateway(long gatewayId) { + SearchCriteria sc = RoutesByGatewayCount.create(); + sc.setParameters("gatewayId", gatewayId); + return customSearch(sc, null).get(0); + } } diff --git a/server/src/com/cloud/network/vpc/VpcManagerImpl.java b/server/src/com/cloud/network/vpc/VpcManagerImpl.java index 210fcb7f66f..93f17b84f9f 100644 --- a/server/src/com/cloud/network/vpc/VpcManagerImpl.java +++ b/server/src/com/cloud/network/vpc/VpcManagerImpl.java @@ -1036,12 +1036,20 @@ public class VpcManagerImpl implements VpcManager, Manager{ public boolean deletePrivateGateway(PrivateGateway gateway) { //check if there are ips allocted in the network long networkId = gateway.getNetworkId(); + + //don't allow to remove gateway when there are static routes associated with it + long routeCount = _staticRouteDao.countRoutesByGateway(gateway.getId()); + if (routeCount > 0) { + throw new CloudRuntimeException("Can't delete private gateway " + gateway + " as it has " + routeCount + + " static routes applied. Remove the routes first"); + } + boolean deleteNetwork = true; List privateIps = _privateIpDao.listByNetworkId(networkId); if (privateIps.size() > 1 || !privateIps.get(0).getIpAddress().equalsIgnoreCase(gateway.getIp4Address())) { s_logger.debug("Not removing network id=" + gateway.getNetworkId() + " as it has private ip addresses for other gateways"); deleteNetwork = false; - } + } Transaction txn = Transaction.currentTxn(); txn.start();